web-dev-qa-db-fra.com

Barre de progression Python et téléchargements

J'ai un script python qui lance une URL qui est un fichier téléchargeable. Existe-t-il un moyen pour que python utilise la ligne de commande pour afficher la progression du téléchargement, par opposition au lancement du navigateur?

36
user1607549

Mis à jour pour votre exemple d'URL:

Je viens d'écrire une approche très simple (légèrement hacky) à ce sujet pour gratter des fichiers PDF d'un site donné. Notez que cela ne fonctionne correctement que sur les systèmes Unix (linux, mac os) car powershell ne gère pas "\ r"

import requests

link = "http://indy/abcde1245"
file_name = "download.data"
with open(file_name, "wb") as f:
        print "Downloading %s" % file_name
        response = requests.get(link, stream=True)
        total_length = response.headers.get('content-length')

        if total_length is None: # no content length header
            f.write(response.content)
        else:
            dl = 0
            total_length = int(total_length)
            for data in response.iter_content(chunk_size=4096):
                dl += len(data)
                f.write(data)
                done = int(50 * dl / total_length)
                sys.stdout.write("\r[%s%s]" % ('=' * done, ' ' * (50-done)) )    
                sys.stdout.flush()

Il utilise la bibliothèque demandes vous aurez donc besoin de l'installer. Cela produit quelque chose comme ce qui suit dans votre console:

> Téléchargement download.data

> [=============]

La barre de progression est large de 52 caractères dans le script (2 caractères sont simplement le [] donc 50 caractères de progression). Chaque = représente 2% du téléchargement.

62
Endophage

Vous pouvez utiliser le paquetage ' clint ' (écrit par le même auteur que 'request') pour ajouter une barre de progression simple à vos téléchargements, comme suit:

from clint.textui import progress

r = requests.get(url, stream=True)
path = '/some/path/for/file.txt'
with open(path, 'wb') as f:
    total_length = int(r.headers.get('content-length'))
    for chunk in progress.bar(r.iter_content(chunk_size=1024), expected_size=(total_length/1024) + 1): 
        if chunk:
            f.write(chunk)
            f.flush()

ce qui vous donnera une sortie dynamique qui ressemblera à ceci:

[################################] 5210/5210 - 00:00:01

Cela devrait également fonctionner sur plusieurs plateformes! Vous pouvez également changer la barre en points ou une roulette avec .dots et .mill au lieu de .bar.

Prendre plaisir!

51
Rich Jones

Je suis surpris que tqdm n'ait pas été suggéré!  enter image description here

12
kekkler

Je pense que vous pouvez également utiliser click , et il a aussi une bonne bibliothèque pour la barre de progression.

import click
with click.progressbar(length=total_size, label='Downloading files') as bar:
    for file in files:
        download(file)
        bar.update(file.size)

Prendre plaisir !

4
Tian Zhang

Python 3 avec TQDM

C'est la technique suggérée à partir de Documentation TQDM .

import urllib.request

from tqdm import tqdm


class DownloadProgressBar(tqdm):
    def update_to(self, b=1, bsize=1, tsize=None):
        if tsize is not None:
            self.total = tsize
        self.update(b * bsize - self.n)


def download_url(url, output_path):
    with DownloadProgressBar(unit='B', unit_scale=True,
                             miniters=1, desc=url.split('/')[-1]) as t:
        urllib.request.urlretrieve(url, filename=output_path, reporthook=t.update_to)
1
Chris Chute

Vous pouvez diffuser un téléchargement tel quel ici -> Diffuser un téléchargement .

Aussi, vous pouvez Stream Uploads .

Le plus important en streaming une demande est faite à moins que vous essayiez d'accéder au response.content Avec seulement 2 lignes

for line in r.iter_lines():    
    if line:
        print(line)

Demandes de flux

0
Vamsidhar Muggulla