我想用我自己的模块版本更新python包中的一个模块,具有以下条件:
- 我希望我更新的模块存在于原始包之外(因为我无法访问包源,或者因为我想将我的本地修改保存在单独的repo中等)。
- 我想要
import
引用原始包/模块以解析到我的本地模块的语句
这是我想用django的细节做的一个例子,因为这就是我出现这个问题的地方:
说这是我的项目结构
django/
... the original, unadulterated django package ...
local_django/
conf/
settings.py
myproject/
__init__.py
myapp/
myfile.py
然后在myfile.py中
# These imports should fetch modules from the original django package
from django import models
from django.core.urlresolvers import reverse
# I would like this following import statement to grab a custom version of settings
# that I define in local_django/conf/settings.py
from django.conf import settings
def foo():
return settings.some_setting
我能用魔法做些什么吗? __import__
声明 myproject/__init__.py
完成这个?是否有更“pythonic”的方法来实现这一目标?
更新 - 我为什么要这样做
这是我认为这有意义的场景。
- 我正在全球预装django的服务器上启动一个django支持的网站。在这种情况下,我无法修改实际的django源。
- 我的django项目使用第三方可重用的应用程序,我不想改变
imports
例如,在所有要导入的应用程序中 mycustomsettings
。我想让可重用的应用程序幸福地无知我已经改变了django.conf.settings的实现。
只需在sys.modules中设置条目,然后再导入它:
import sys
import myreplacement
sys.modules["original"] = myreplacement
然后,当某人“导入原始”时,他们将获得您的版本。
如果要替换子模块,可以这样做:
import sys
import thepackage
sys.modules["thepackage"].submodule = myreplacement
sys.modules["thepackage.submodule"] = myreplacement
然后“from thepackage import submodule”或“import thepackage.submodule”将给出“myreplacement”。
只需在sys.modules中设置条目,然后再导入它:
import sys
import myreplacement
sys.modules["original"] = myreplacement
然后,当某人“导入原始”时,他们将获得您的版本。
如果要替换子模块,可以这样做:
import sys
import thepackage
sys.modules["thepackage"].submodule = myreplacement
sys.modules["thepackage.submodule"] = myreplacement
然后“from thepackage import submodule”或“import thepackage.submodule”将给出“myreplacement”。
也许你可以利用 Django的值 项目,提供了一个 dbsettings
应用程序,...
...允许占位符进行设置
在Python中定义,而他们的值
由工作人员使用编辑设置
服务器已启动并正在运行。许多
值类型可用,它们
每个映射到本机Python类型,所以
模型方法和其他Python代码
可以作为标准类访问它们
属性。
还做了很多努力
减少此功能的开销,
这样只查询数据库
每次服务器重启期间一次,和
仅在值时更新
他们自己更新。
注意:这不是作为一个
替换settings.py。这是
专为预期的价值而设计
根据需要改变
网站或其用户,这样的
变化不需要那么多
重新开始。 settings.py仍然是
放置设置的地方
仅因项目而异。
看待它的一种方法是
settings.py适合那些东西
是技术要求
透视(数据库连接,
已安装的应用程序,avaialble
中间件等),而dbsettings是
最适合那些事情
由于组织政策的要求
(配额,最低要求等)。
这样,程序员就维持着
技术要求,而
管理员维护组织
政策。
该项目由Marty Alchin(编写Pro Django书籍)并且不需要对Django代码进行任何更改 - 它是标准的Django应用程序。
import local_django.conf
import django.conf
django.conf.settings = local_django.conf.settings
模块是单身人士。模块仅初始化/加载一次。在导入使用django.conf.settings的模块之前,您需要执行此操作以获取更改。
阅读此链接以获取更多信息,以了解是否有更标准的方法使用django,因为文档特别建议不要像我在上面显示的设置对象一样。
http://docs.djangoproject.com/en/dev/topics/settings/
它应该适用于其他对象和模块。
在这种特殊情况下,“最好遵循规定 用于创建自己的设置的机制。
在一般情况下,使用进口产品可能会让您的读者感到困惑(可能是您)。改变类行为的pythonic方法是sub-class和override。
大约两三天前,我被介绍过这个,但是这样做的一种方法是使用Python虚拟环境。这允许您指定您正在使用的Python版本,以及您要安装的模块的版本,并且能够相对容易地在不同版本和项目之间进行交换;它还允许您安装Python系统,否则您可能无法获得安装所需的权限。
您可以从中了解更多关于virtualenv的信息 virtualenv信息。
还有一个“virtualenvwrapper”软件包,它提供了更容易在环境之间交换的工具。
不可否认,我对此没有多少经验,我发现这个问题是为了了解如何使用自定义版本覆盖Python标准库 - 所以它并不完美。但是,我对其指定安装内容的能力印象深刻,直到单个模块的版本!