Question

J'apprends Python et j'essaie d'écrire un code pour synchroniser deux répertoires: l'un est sur FTP Server, l'autre est sur mon disque local. Jusqu'à présent, j'ai écrit un code de travail mais j'ai une question ou deux à ce sujet :)

import os
from ftplib import FTP

h_local_files = [] # create local dir list
h_remote_files = [] # create remote dir list

h_local = 'C:\\something\\bla\\' # local dir

ftp = FTP('ftp.server.com')
ftp.login('user', 'pass')

if os.listdir(h_local) == []:
    print 'LOCAL DIR IS EMPTY'
else:
    print 'BUILDING LOCAL DIR FILE LIST...'
    for file_name in os.listdir(h_local):
        h_local_files.append(file_name) # populate local dir list

ftp.sendcmd('CWD /some/ftp/directory')
print 'BUILDING REMOTE DIR FILE LIST...\n'
for rfile in ftp.nlst():
    if rfile.endswith('.jpg'): # i need only .jpg files
        h_remote_files.append(rfile) # populate remote dir list

h_diff = sorted(list(set(h_remote_files) - set(h_local_files))) # difference between two lists

for h in h_diff:
    with open(os.path.join(h_local,h), 'wb') as ftpfile:
        s = ftp.retrbinary('RETR ' + h, ftpfile.write) # retrieve file
        print 'PROCESSING', h
        if str(s).startswith('226'): # comes from ftp status: '226 Transfer complete.'
            print 'OK\n' # print 'OK' if transfer was successful
        else:
            print s # if error, print retrbinary's return

Ce morceau de code devrait faire deux listes Python: une liste de fichiers dans le répertoire local et une liste de fichiers dans le répertoire FTP. Après avoir supprimé les doublons des listes, le script doit télécharger des fichiers «manquants» dans mon répertoire local.

Pour l'instant, ce morceau de code fait ce dont j'ai besoin, mais j'ai remarqué que lorsque je l'exécute, ma sortie n'agit pas comment j'imagine qu'elle agirait :)

Par exemple, ma sortie actuelle va:

PROCESSING 2012-01-17_07.05.jpg
OK

# LONG PAUSE HERE

PROCESSING 2012-01-17_07.06.jpg
OK

# LONG PAUSE HERE

PROCESSING 2012-01-17_07.06.jpg
OK

etc...

Mais j'imagine que cela devrait fonctionner comme ceci:

PROCESSING 2012-01-17_07.05.jpg
# LONG PAUSE HERE (WHILE DOWNLOADING)
OK

PROCESSING 2012-01-17_07.06.jpg
# LONG PAUSE HERE (WHILE DOWNLOADING)
OK

PROCESSING 2012-01-17_07.06.jpg
# LONG PAUSE HERE (WHILE DOWNLOADING)
OK

etc...

Comme je l'ai dit, j'ai juste commencé à apprendre Python, et peut-être que je fais des trucs ici complètement mal (if str(s).startswith('226')????). Peut-être que je ne peux pas réaliser cela avecftplib seulement? Donc, à la fin, mes questions sont:

Qu'est-ce que je fais de mal ici? :)
Comment produire une sortie «appropriée» et existe-t-il un moyen d'imprimer une sorte de statut lors du téléchargement d'un fichier (au moins une ligne de points), par exemple:

PROCESSING 2012-01-17_07.05.jpg
..........
OK

PROCESSING 2012-01-17_07.06.jpg
......
OK

PROCESSING 2012-01-17_07.06.jpg
...............
OK

etc...

Merci beaucoup pour votre aide!

Était-ce utile?

La solution

Blocs rerybinary jusqu'à ce qu'il soit terminé. C'est pourquoi tu vois Processing ZZZ\n OK Immédiatement, car il se produit une fois l'appel à Retrbinary terminé.

Si vous souhaitez imprimer . Pour chaque appel, vous devez ensuite fournir une fonction de rappel pour ce faire. Voici le docstring pour Retrbinary:

    """Retrieve data in binary mode.  A new port is created for you.

    Args:
      cmd: A RETR command.
      callback: A single parameter callable to be called on each
                block of data read.
      blocksize: The maximum number of bytes to read from the
                 socket at one time.  [default: 8192]
      rest: Passed to transfercmd().  [default: None]

    Returns:
      The response code.
    """

Ainsi, vous devez fournir un rappel différent qui écrit à la fois le fichier et imprime '. "

import sys # At the top of your module.

# Modify your retrbinary    
ftp.retrbinary('RETR ' + h, lambda s: ftpfile.write(s) and sys.stdout.write('.'))

Vous devrez peut-être modifier cet extrait de code, mais cela devrait vous donner une idée de ce qu'il faut faire.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top