2009-12-24 18 views
8

Fondamentalmente ho un pacchetto secondario con lo stesso nome di un pacchetto di libreria standard ("registrazione") e mi piacerebbe poter importare in modo assoluto lo standard uno no importa come lo eseguo, ma questo fallisce quando sono nel pacchetto genitore.Errore assoluto di importazione nel pacchetto parziale che ombreggia un nome di pacchetto stdlib

Sembra davvero un bug o un comportamento non documentato del nuovo supporto "absolute import" (nuovo come in Python 2.5). Ho provato con 2.5 e 2.6.

layout di pacchetto:

foo/ 
    __init__.py 
    logging/ 
     __init__.py 

In foo/__init__.py importiamo la nostra registrazione subpackage:

from __future__ import absolute_import 
from . import logging as rel_logging 
print 'top, relative:', rel_logging 

In foo/logging/__init__.py vogliamo importare il pacchetto stdlib logging:

from __future__ import absolute_import 
print 'sub, name:', __name__ 

import logging as abs_logging 
print 'sub, absolute:', abs_logging 

Nota : La cartella contenente foo si trova in sys.path.


Quando importate dall'esterno/sopra foo, l'uscita è come previsto:

c:\> python -c "import foo" 
sub, name: foo.logging 
sub, absolute: <module 'logging' from 'c:\python26\lib\logging\__init__.pyc'> 
top, relative: <module 'foo.logging' from 'foo\logging\__init__.pyc'> 

Così l'importazione assoluta nel subpackage trova il pacchetto stdlib, se lo desideri.

Ma quando siamo all'interno della cartella foo, si comporta in modo diverso:

c:\foo>\python25\python -c "import foo" 
sub, name: foo.logging 
sub, name: logging 
sub, absolute: <module 'logging' from 'logging\__init__.pyc'> 
sub, absolute: <module 'logging' from 'logging\__init__.pyc'> 
top, relative: <module 'foo.logging' from 'c:\foo\logging\__init__.pyc'> 

La doppia uscita per "sub, nome" mostra che il mio subpackage chiamato "registrazione" è l'importazione di per sé una seconda volta, e non trova il pacchetto "logging" stdlib anche se "absolute_import" è abilitato.

Il caso d'uso è che mi piacerebbe essere in grado di lavorare, testare, ecc., Questo pacchetto indipendentemente da quale sia la directory corrente. Cambiare il nome da "logging" a qualcos'altro sarebbe una soluzione, ma non desiderabile, e in ogni caso questo comportamento non sembra adattarsi alla descrizione di come dovrebbero funzionare le importazioni assolute.

Qualche idea su cosa sta succedendo, che si tratti di un bug (mio o di Python) o se questo comportamento sia di fatto implicito da qualche documentazione?

Modifica: la risposta di gahooa mostra chiaramente qual è il problema. Un grezzo work-around che dimostra che è tutto è mostrato qui:

c:\foo>python -c "import sys; del sys.path[0]; import foo" 
sub, name: foo.logging 
sub, absolute: <module 'logging' from 'c:\python26\lib\logging\__init__.pyc'> 
top, relative: <module 'foo.logging' from 'c:\foo\logging\__init__.pyc'> 

risposta

10

sys.path[0] è per default '', che significa "directory corrente". Quindi se sei seduto in una directory con logging al suo interno, verrà scelto per primo.

Mi sono imbattuto in questo recentemente, fino a quando mi sono reso conto che ero effettivamente seduto in quella directory e che sys.path stava raccogliendo la mia attuale directory PRIMA, prima di guardare nella libreria standard.

+0

Grazie. Mi ero appena reso conto di come pensavo più a pranzo.Immagino che sia inevitabile che ciò accada a meno che non si rimuova deliberatamente sys.path [0] o si spostino '' alla fine o qualcosa del genere. Lo noterò nella mia domanda. –

Problemi correlati