2016-06-07 2 views
3

J'ai un script python qui me fait mal sur Ubuntu 12.02 avec Python 2.7.3. PS: il fonctionne sans problème sous Windows.erreur shutil samefile sous Linux

>>> import os 
>>> import shutil 

>>> shutil.copy("/mnt/my_network_dive/somewhere/sample.xml", "/mnt/my_network_drive/COMPLETED/") 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
    File "/usr/lib/python2.7/shutil.py", line 117, in copy 
     copyfile(src, dst) 
    File "/usr/lib/python2.7/shutil.py", line 69, in copyfile 
     raise Error("`%s` and `%s` are the same file" % (src, dst)) 
shutil.Error: `/mnt/my_network_dive/somewhere/sample.xml` and `/mnt/my_network_drive/COMPLETED/sample.xml` are the same file 

Vérification des propriétés des fichiers:

>>> os.path.exists("/mnt/my_network_drive/somewhere/sample.xml") 
True 
>>> os.path.exists("/mnt/my_network_drive/COMPLETED/sample.xml") 
True 
>>> os.stat("/mnt/my_network_drive/somewhere/sample.xml") 
posix.stat_result(st_mode=33272, st_ino=4913809333, st_dev=25L, st_nlink=1, st_uid=1000, st_gid=0, st_size=5447, st_atime=1465311674, st_mtime=1465311674, st_ctime=1465311685) 
>>> os.stat("/mnt/my_network_drive/COMPLETED/sample.xml") 
posix.stat_result(st_mode=33272, st_ino=4913809333, st_dev=25L, st_nlink=1, st_uid=1000, st_gid=0, st_size=10, st_atime=1465317482, st_mtime=1465317482, st_ctime=1465317483) 
>>> os.path.islink("/mnt/my_network_drive/somewhere/sample.xml") 
False 
>>> os.path.islink("/mnt/my_network_drive/COMPLETED/sample.xml") 
False 

>>> shutil._samefile("/mnt/my_network_dive/somewhere/sample.xml", "/mnt/my_network_drive/COMPLETED/sample.xml") 
False 

Comme vous le voyez, je reçois l'appel shutil._samefileFalse mais shutil.copy heurteront à la même samefile error.

Est-ce que j'oublie quelque chose? Un autre moyen de déplacer ou de copier des fichiers avec Python?

+0

Vous n'avez pas besoin de les copier. Ce sont deux entrées de répertoire différentes pointant sur le même fichier. Étant le même fichier, il n'y a aucune possibilité que leur contenu peut différer. –

+0

(Pourquoi 'shutil._samefile' renvoie False est une question différente, et peut-être quelque chose pour déposer un bogue, mais puisque st_dev' et' st_ino' sont identiques, il ne fait aucun doute qu'il s'agit du même contenu pointé par les deux entrées du répertoire). –

+1

@vmenezes Le premier argument de la copie dans la première case contient des instructions de plongée, est-ce seulement typo? –

Répondre

2

Il semble que les deux fichiers sont à la fois des liens durs et le même fichier. Vous pouvez dire parce qu'ils partagent le même numéro d'inode

st_ino=4913809333 

Les utilisateurs de Windows ne créent généralement pas de liens physiques. Ils sont plus courants dans les environnements Linux, ce qui explique pourquoi vous n'avez peut-être pas rencontré le problème jusqu'à présent.

Il est étrange que samefile renvoie False. Quel système d'exploitation utilisez-vous? shutil._samefile est juste une enveloppe autour de os.path.samefile (sur les systèmes où cette fonction existe). Quels sont les résultats de os.path.samefile? Sur les systèmes POSIX, il vérifie que tout le dispositif et correspondance inode (ce qu'ils font dans votre cas) et il devrait retourner True

posixpath.py

def samefile(f1, f2): 
    s1 = os.stat(f1) 
    s2 = os.stat(f2) 
    return samestat(s1, s2) 

def samestat(s1, s2): 
    return s1.st_ino == s2.st_ino and s1.st_dev == s2.st_dev 
+0

Il est probable que l'un des répertoires parents ou les deux soient des liens symboliques vers le même répertoire. – tdelaney

+0

@tdelaney Mais 'samefile' devrait toujours retourner' True' dans ce cas, non? –

+0

Oui, je suis aussi perplexe que toi. Comme avec un lien dur, le dev et l'inode devraient être les mêmes. – tdelaney

0

En python 3 dans shutil. copie il y a follow_symlinks argument supplémentaire = True Regardez ce https://docs.python.org/3/library/shutil.html

Si follow_symlinks est faux, et src est un lien symbolique, dst sera cr assis comme un lien symbolique. Si follow_symlinks est vrai et src est un lien symbolique, dst sera une copie du fichier auquel src fait référence.

+0

Ne répond pas à la question d'OP à propos de Python 2.7.3. – martineau

+0

@martineau Mais peut-être que vérifier comment cela fonctionne dans Python 3 pourrait aider à déterminer si c'est le problème. Si oui, peut-être pourrait-il regarder la source de la nouvelle version et copier ce code. –

+0

Comment savez-vous que l'utilisation de Python 3 ne pose pas de problème non plus? – martineau