You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

循环导入及async/await场景下全局变量未定义报错问题咨询

问题排查与解决

1. NameError报错根因

这个错误和多进程、async/await均无关,是循环导入+全局变量初始化时机错误导致的:

  • 运行main模块时,首先会执行顶层的import api语句
  • api模块执行时又会导入main,此时main模块的main()函数还未运行,全局变量lock尚未定义
  • 后续调用main.log()时,函数内部引用未初始化的lock,直接触发NameError

另外可以明确:async/await是单线程协程模型,本身不会创建任何新进程,你观察到的非主进程PID,是后续multiprocessing相关逻辑触发的子进程导入导致的,和协程无关。

2. 修复方案

第一步:解除循环导入

不要让main和api互相依赖,将公共的日志函数、全局锁抽离到独立的公共模块,例如新建common.py:

import multiprocessing

# 直接在模块顶层初始化锁,导入时即可完成创建
lock = multiprocessing.Lock()

def log(msg):
    print(multiprocessing.current_process().pid)
    with lock:
        some_log_func(msg)

之后main和api都导入common.log使用即可,不需要互相导入。

第二步:子进程共享锁的处理

根据你使用的多进程启动模式,对应处理锁的继承:

  • fork模式(Linux/macOS默认):父进程初始化的锁会自动被子进程继承,只要锁是在创建子进程前初始化完成,即可直接在子进程中使用。
  • spawn模式(Windows默认):创建子进程时会重新导入所有模块,不会自动继承父进程的全局变量,需要通过进程池的初始化函数传递锁:
# main模块代码示例
import multiprocessing
from common import lock

def pool_init(shared_lock):
    # 给子进程的全局变量赋值
    import common
    common.lock = shared_lock

if __name__ == '__main__':
    pool = multiprocessing.Pool(
        processes=4,
        initializer=pool_init,
        initargs=(lock,)
    )
    # 后续使用进程池执行任务即可

内容的提问来源于stack exchange,提问作者awarrier99

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.07 04:18:03