如何防止Python包导入后函数被修改?
防止Python包内函数被外部修改的几种方法
针对你遇到的问题,这里有几种实用的方案来阻止外部用户修改你的check函数:
1. 把check函数嵌套在foo内部
直接将check定义为foo的内部函数,这样外部代码根本无法访问到check,自然也就无法修改它:
# mypackage 模块代码 def foo(): def check(): if env_var == "value": return True return False if check(): raise PermissionError() else: return "foo"
2. 使用双下划线前缀将函数设为模块私有
给check函数加上双下划线前缀,Python会自动对这个函数名做名称混淆处理,外部代码无法直接通过mypackage.check访问或修改它:
# mypackage 模块代码 def __check(): if env_var == "value": return True return False def foo(): if __check(): raise PermissionError() else: return "foo"
注意:这种方法是“防君子不防小人”,如果用户知道混淆后的名称(比如_mypackage__check),还是能修改,但对于普通用户来说已经足够。
3. 用类封装并将check设为私有静态方法
把相关逻辑封装到类中,将check设为私有静态方法,外部无法直接访问和修改:
# mypackage 模块代码 class MyPackage: @staticmethod def __check(): if env_var == "value": return True return False @staticmethod def foo(): if MyPackage.__check(): raise PermissionError() else: return "foo"
用户使用时只需调用mypackage.MyPackage.foo()即可。
4. 限制模块导出的成员(辅助方案)
在模块顶部定义__all__列表,只列出允许外部访问的函数(比如只包含foo),这样当用户使用from mypackage import *时不会导入check,但用户仍能通过mypackage.check访问,所以这只是辅助手段:
# mypackage 模块顶部 __all__ = ["foo"] def check(): if env_var == "value": return True return False def foo(): if check(): raise PermissionError() else: return "foo"
5. 锁定模块属性(硬核方案)
在模块加载完成后,通过修改模块的属性设置逻辑,禁止修改check函数:
# mypackage 模块代码 def check(): if env_var == "value": return True return False def foo(): if check(): raise PermissionError() else: return "foo" # 锁定check函数,禁止外部修改 import sys current_module = sys.modules[__name__] def __setattr__(name, value): if name == "check": raise AttributeError("Cannot modify 'check' function") super(current_module.__class__, current_module).__setattr__(name, value) current_module.__setattr__ = __setattr__
这种方法会完全阻止修改check,但要注意如果模块自身后续需要修改check也会报错,需谨慎使用。
内容的提问来源于stack exchange,提问作者elj96
相关产品推荐
相关产品推荐

