我正在为我的 Django 项目编写小型应用程序。这个想法是创建某种小部件——可以通过包含标签添加到模板中的小视图功能,以显示一些辅助信息(例如博客记录、快速链接列表、菜单等)。为此,我想创建类似于默认templatetag
注册机制的东西。通常我需要以下组件:
- 自定义装饰器来注册这些视图函数
- 某些功能将在启动时搜索所有已安装应用程序中的特定模块(现在是“widgets.py”)(可能从 settings.py 调用)
我现在写的看起来像这样:
# -*- coding: utf-8 -*-
REGISTERED_WIDGETS = []
class Library(object):
"""
Utility class for registering defined widgets
"""
def widget(self, view=None, name=None, form_class=None):
if name is None:
name = view.__name__
def decorator(view):
print 'registering', view
REGISTERED_WIDGETS.append((view, name, form_class))
def wrapper(request, *args, **kwargs):
return view(request, *args, **kwargs)
return wrapper
if view is not None:
return decorator(view)
else:
return decorator
def search_widgets():
"""
Search for 'widgets.py' modules inside installed applications and import them,
hence initializing its registration
"""
from django.conf import settings
for app in settings.INSTALLED_APPS:
try:
module = __import__(app + '.widgets')
print module
except ImportError:
pass
else:
print 'Imported widgets from ', app
if __name__ == '__main__':
search_widgets()
print REGISTERED_WIDGETS
为了测试它,我在我的一个应用程序中的 widgets.py 中添加了这个存根小部件:
# -*- coding: utf-8 -*-
from experiments.widgets.base import Library
register = Library()
@register.widget(name='dummy')
def dummy_widget(request):
pass
我现在遇到了一个愚蠢的问题——当运行这个模块时,我想看到 REGISTERED_WIDGETS 变量充满了找到的小部件,但它是空的。实际上我看到了这个输出:
>>> %run widgets/base.py
<module 'django' from '/usr/lib/python2.7/dist-packages/django/__init__.pyc'>
Imported widgets from django.contrib.admin
registering <function dummy_widget at 0x364f320>
<module 'experiments' from '/home/east825/Development/pycharm-experiments/experiments/../experiments/__init__.pyc'>
Imported widgets from experiments.layout
[]
似乎我忘记了关于 python 共享全局变量行为的一些非常重要的事情。有什么建议吗?