Os namespaces são uma ótima ideia – vamos fazer mais disso!
– Tim Peters, PEP20
Todos nós sabemos (ou deveríamos saber) como os namespaces funcionam no Python. Você coloca um módulo em um caminho específico e pode acessá-lo como path.to.my.module
(desde que path
esteja visível para Python usando vários métodos). Não é a isso que “namespace” nesta postagem se refere.
Aqui, estou me referindo à separação de vários submódulos em um namespace raiz comum. Isso pode ser incrivelmente útil para módulos díspares, mas de alguma forma relacionados. Digamos que eu tenha a seguinte configuração de diretório em um projeto em que estou trabalhando:
foo/
__init__.py
bar/
__init__.py
baz/
__init__.py
Depois de um monte de trabalho, descobri que eu gostaria de provocação bar
e baz
para fora em seus próprios módulos de base, dando aos usuários a capacidade de depender apenas os módulos que eles se preocupam em vez de ter que navegar toda a pia da cozinha.
Agora, tudo isso pode ser feito facilmente seguindo convenções horríveis, como usar os nomes foo_bar
, foo_baz
ou outro nome mutilado, mas não é o efeito que desejo. Além de ser feio, isso forçaria todos os dependentes da atualização do pacote para o novo estilo a mudar suas importações. Como tal, não é uma opção viável.
Obviamente, não podemos simplesmente nomear um pacote com a estrutura de diretório interno e ter outro pacote com a estrutura de diretório interno . Certamente, isso introduzirá uma colisão de importação.foo.bar
foo/bar/
foo.baz
foo/baz
Ou vai?
É aí que namespace_packages
(das ferramentas de configuração) entra em jogo. Usando este recurso, você pode definir um namespace raiz para cada pacote a ser usado. Com o exemplo acima, se eu simplesmente definir o namespace_package
como "foo"
, cada pacote com a raiz foo
não colidirá um com o outro.
Há duas coisas importantes a lembrar ao usar isso:
- Nada além de init .py e outros diretórios de submódulo podem existir no diretório do namespace
- O init .py deve conter ( exigido a partir de 0.7). Não deve conter mais nada.
__import__('pkg_resources').declare_namespace(__name__)
http://www.python.org/dev/peps/pep-0382/
http://pythonhosted.org/distribute/setuptools.html#namespace-packages