微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

Python-从导入的模块注册函数

如何解决Python-从导入的模块注册函数

我正在尝试确定实现我的应用程序的最佳方法,其中将有一个主程序(main.py)和一个单独的规则模块(rules.py),在其中可以编写任意数量的规则,它们将所有这些都可以在main.py中应用以处理一些数据(字典)。应用程序的用户可以将自己的自定义规则添加到rules.py中,而不会影响main.py中的逻辑。

我当时认为装饰器在这里可能有用,以便将main.py遍历它们的方式注册到rules.py中,但是我不确定确切的实现。这是我的基本代码

main.py

import rules

modifiers = [] # List of fuctions to modify data

def add_modifier(f):
  modifiers.append(f)
  return f

def invoke_modifiers(data):
  for modifier in modifiers:
    data = modifier(data)
  return data

if __name__ == "__main__":
  data = {'foo': 'bar'}
  print(f"Invoking modifiers on data: {data}")
  data = invoke_modifiers(data)
  print(f"Done invoking modifiers: {data}")

rules.py

from main import add_modifier

@add_modifier
def mod1(data):
  data['foo'] = 'baz'
  return data

@add_modifier
def mod2(data):
  data['quz'] = 'qux'
  return data

但是当我执行代码时,它不会修改我的数据。

$ python main.py
Invoking modifiers on data: {'foo': 'bar'}
Done invoking modifiers: {'foo': 'bar'}

所以我的问题有两个:

  1. 这是在主应用程序之外具有用户定义功能的好方法吗?
  2. 需要进行哪些更改才能使rules.py模块中的mod1和mod2修改数据?

编辑

如果我在rules.py中省略了from main import add_modifier,则在执行过程中会得到以下信息:

Traceback (most recent call last):
  File "main.py",line 3,in <module>
    import rules
  File "/home/telorb/Python/registerTest/rules.py",in <module>
    @add_modifier
NameError: name 'add_modifier' is not defined

解决方法

我对装饰工不是很熟悉,所以也许其他人可能对此有所建议。

但是考虑到您在做什么,我认为创建一个供用户添加功能的类将具有您想要的功能。

该线程:Is there a way to loop through and execute all of the functions in a Python class?

一个建议的解决方案确实使用了装饰器,因此可以阐明如何更好地构建您的结构。

,

目前,我要使用一种在这里找到的解决方案:How can I decorate all functions imported from a file?

main.py

import types
import functools

modifiers = [] # List of fuctions to modify data

def decorate_all_in_module(module,decorator):
    for name in dir(module):
        obj = getattr(module,name)
        if isinstance(obj,types.FunctionType):
            setattr(module,name,decorator(obj))

def add_modifier(f):
  print(f"Adding modifier: {f}")
  modifiers.append(f)
  return f

def invoke_modifiers(data):
  print(f'Invoking {len(modifiers)} modifiers')
  for modifier in modifiers:
    print(f'Invoking {modifier}')
    data = modifier(data)
  return data

@add_modifier
def mod_main(data):
  data['xray'] = 'zulu'
  return data

import rules

if __name__ == "__main__":
  decorate_all_in_module(rules,add_modifier)
  data = {'foo': 'bar'}
  print(f"Invoking modifiers on data: {data}")
  data = invoke_modifiers(data)
  print(f"Done invoking modifiers: {data}")

rules.py

def mod1(data):
  data['foo'] = 'baz'
  return data

def mod2(data):
  data['quz'] = 'qux'
  return data

$ python main.py

Adding modifier: <function mod_main at 0x7fe69ce75160>
Adding modifier: <function mod1 at 0x7fe69ce75040>
Adding modifier: <function mod2 at 0x7fe69ce75700>
Invoking modifiers on data: {'foo': 'bar'}
Invoking 3 modifiers
Invoking <function mod_main at 0x7fe69ce75160>
Invoking <function mod1 at 0x7fe69ce75040>
Invoking <function mod2 at 0x7fe69ce75700>
Done invoking modifiers: {'foo': 'baz','xray': 'zulu','quz': 'qux'}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。