繁体   English   中英

python记录__name__和打包

[英]python logging __name__ and packaging

官方的python日志记录文档说:

该名称可能是用句点分隔的分层值,例如foo.bar.baz(例如,也可以是纯foo)。 层次结构列表中位于最下方的记录器是列表中较高处的记录器的子级。 例如,给定名称为foo的记录器,名称为foo.bar,foo.bar.baz和foo.bam的记录器都是foo的后代。 记录程序名称层次结构类似于Python包层次结构,如果您使用建议的构造logging.getLogger(__ name__)在每个模块的基础上组织记录程序,则记录程序名称层次结构与Python包层次结构相同。 这是因为在模块中,__name__是Python包命名空间中模块的名称。

但是我发现最后一句话并非严格正确。 __name__的值似乎取决于如何导入模块。 以下内容说明了这一点:

给定两个模块,foo和bar都在软件包pkg中:

这是foo

def showFoosName():
    print __name__

这是

from pkg import foo
if __name__ == '__main__':
    foo.showFoosName()

跑吧生产

pkg.foo

但是,如果我们将baz引入软件包pkg中,则该软件包将foo简单地导入为foo,这是合法的,因为两者都在同一个软件包中:

import foo
if __name__ == '__main__':
    foo.showFoosName() 

运行baz生产

foo

现在将讨论重新回到日志记录和日志记录配置中,似乎只有使用from pkg import bar语法对软件包中的from pkg import bar进行编码时,使用__name__命名记录器的python日志记录建议才有效。 这不是我所期望的。 我会认为__name__的值将独立于其导入方式。

这是导入路径被破坏的症状。 路径上同时具有pkg及其包含目录,这导致foo.py对应于两个单独的模块 foopkg.foo

可能是,包含pkg的目录位于您的导入路径上,但是您直接通过文件名运行bar.pybaz.py ,导致pkg本身也位于该路径上。 运行

python -m pkg.bar

要么

python -m pkg.baz

应该防止将pkg添加到路径中。

那只是弄乱导入路径的一种可能方法。 我们真的不能说。 阅读Python导入系统应该会有所帮助; 这是一种很好的资源

关于Python包和模块的问题是,就像Python中的其他所有内容一样,它们是动态的。 每个模块的__name__取决于它相对于Python根路径(在sys.path )的相对位置。 因此,如果您有一个名为pkg的文件夹,即使它包含__init__.py ,即使它直接位于sys.path上,它实际上也不是“包”。 如果pkg文件夹直接位于sys.path (例如,因为您在此处启动了Python解释器),则它不是一个包,并且其中的任何.py文件都是顶级模块,而不是任何包中的模块。 因此,如果你有foo.py里面pkg文件夹,当你从内启动Python解释pkgfoo.py “是真实的,正式名称 foo ,不是pkg.foo

除非包含的文件夹pkgsys.path没有pkg - from pkg import foo会失败,并ImportError 而且,如果pkg和包含pkg的文件夹都位于sys.path ,则您的Python路径格式错误,并且您有两个单独的可导入模块pkg.foofoo (具有所有全局变量的独立副本!)。

为了解决这种问题,最佳实践是将可执行脚本与可导入模块和包彼此分开。 这样一来,您就可以将所有可导入的模块和程序包放在一个公共位置(通常,在Python安装的site-packages下),并且无论脚本位于何处,可执行脚本都可以使用全名导入它们(通常,诸如/usr/bin/usr/local/bin

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM