web-dev-qa-db-fra.com

Utilisation de Selenium avec Python et PhantomJS pour télécharger un fichier vers un système de fichiers

J'ai été aux prises avec l'utilisation de PhantomJS/Selenium/python-Selenium pour télécharger un fichier sur le système de fichiers. Je suis en mesure de naviguer facilement dans le DOM et de cliquer, survoler, etc. Le téléchargement d'un fichier s'avère cependant assez gênant. J'ai essayé une approche sans tête avec Firefox et pyvirtualdisplay mais cela ne fonctionnait pas bien non plus et était incroyablement lent. Je sais que CasperJS permet le téléchargement de fichiers. Quelqu'un sait-il comment intégrer CasperJS avec Python ou comment utiliser PhantomJS pour télécharger des fichiers. Très apprécié.

20
Encinoman818

Bien que cette question soit assez ancienne, le téléchargement de fichiers via PhantomJS reste un problème. Mais nous pouvons utiliser PhantomJS pour obtenir un lien de téléchargement et récupérer tous les cookies nécessaires tels que les jetons csrf, etc. Et puis nous pouvons utiliser requests pour le télécharger réellement:

import requests
from Selenium import webdriver

driver = webdriver.PhantomJS()
driver.get('page_with_download_link')
download_link = driver.find_element_by_id('download_link')
session = requests.Session()
cookies = driver.get_cookies()

for cookie in cookies: 
    session.cookies.set(cookie['name'], cookie['value'])
response = session.get(download_link)

Et maintenant dans response.content le contenu réel du fichier devrait apparaître. Nous pouvons ensuite l'écrire avec open ou faire ce que nous voulons.

18
valignatev

PhantomJS ne prend actuellement pas en charge le téléchargement de fichiers. Problèmes pertinents avec les solutions de contournement:

Pour autant que je comprends, vous avez au moins 3 options:

  • passez à casperjs (et vous devriez laisser python ici)
  • essayez avec headless sur xvfb
  • passer aux navigateurs normaux sans tête

Voici également quelques liens qui pourraient également vous aider:

11
alecxe

Mon cas d'utilisation nécessitait une soumission de formulaire pour récupérer le fichier. J'ai pu accomplir cela en utilisant la fonction execute_async_script() du pilote.

 js = '''
    var callback = arguments[0];
    var theForm = document.forms['theFormId'];
    data = new FormData();
    data.append('eventTarget', "''' + target + '''"); // this is the id of the file clicked
    data.append('otherFormField', theForm.otherFormField.value);

    var xhr = new XMLHttpRequest();
    xhr.open('POST', theForm.action, true);
'''

for cookie in driver.get_cookies():
    js += ' xhr.setRequestHeader("' + cookie['name'] + '", "' + cookie['value'] + '"); '

js += '''
    xhr.onload = function () {
        callback(this.responseText);
    };
    xhr.send(data);
'''

driver.set_script_timeout(30)
file = driver.execute_async_script(js)
3
dnbwise