web-dev-qa-db-fra.com

Comment obtenir un nom de fichier pdf avec les demandes Python?

J'utilise le Python demande lib pour obtenir un fichier PDF sur le Web. Cela fonctionne bien, mais maintenant je voulez le nom de fichier d'origine. Si je vais dans un fichier PDF dans Firefox et cliquez sur download il a déjà un nom de fichier défini pour enregistrer le pdf. Comment puis-je obtenir ce nom de fichier?

Par exemple:

import requests
r = requests.get('http://www.researchgate.net/profile/M_Gotic/publication/260197848_Mater_Sci_Eng_B47_%281997%29_33/links/0c9605301e48beda0f000000.pdf')
print r.headers['content-type']  # prints 'application/pdf'

J'ai vérifié le r.headers pour quelque chose d'intéressant, mais il n'y a pas de nom de fichier là-dedans. J'espérais en fait quelque chose comme r.filename ..

Est-ce que quelqu'un sait comment obtenir le nom de fichier d'un fichier PDF PDF téléchargé avec la bibliothèque de requêtes)?

23
kramer65

Il est spécifié dans un en-tête http content-disposition. Donc pour extraire le nom que vous feriez:

import re
d = r.headers['content-disposition']
fname = re.findall("filename=(.+)", d)

Nom extrait de la chaîne via une expression régulière (module re).

46
user3255354

Apparemment, pour cette ressource particulière, elle se trouve dans:

r.headers['content-disposition']

Je ne sais pas si c'est toujours le cas.

7
Maksim Solovjov

S'appuyant sur certaines des autres réponses, voici comment je le fais. S'il n'y a pas de Content-Disposition en-tête, je l'analyse à partir de l'URL de téléchargement.

import re
import requests
from request.exceptions import RequestException


url = 'http://www.example.com/downloads/sample.pdf'

try:
    with requests.get(url) as r:

        fname = ''
        if "Content-Disposition" in r.headers.keys():
            fname = re.findall("filename=(.+)", r.headers["Content-Disposition"])[0]
        else:
            fname = url.split("/")[-1]

        print(fname)
except RequestException as e:
    print(e)

Il existe sans doute de meilleures façons d'analyser la chaîne d'URL, mais pour simplifier, je ne voulais pas impliquer plus de bibliothèques.

2
Nilpo

Vous pouvez utiliser werkzeug pour les en-têtes d'options https://werkzeug.palletsprojects.com/en/0.15.x/http/#werkzeug.http.parse_options_header

>>> import werkzeug


>>> werkzeug.parse_options_header('text/html; charset=utf8')
('text/html', {'charset': 'utf8'})
0
myildirim