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

使用Selenium测试Django Channels 2失败:无法Pickle本地对象报错

解决Django Channels测试中的AttributeError: Can't pickle local object 'DaphneProcess.__init__.<locals>.<lambda>'

这个问题我之前在跟进Django Channels聊天功能测试时也踩过坑,核心原因是Daphne启动进程时用了局部定义的lambda函数——而Django测试的多进程环境需要序列化进程相关对象,但lambda根本没法被pickle序列化,所以才触发了这个报错。下面给你几个可行的解决办法:

方案1:升级Daphne到最新版本

最省心的就是直接升级Daphne,这个pickle问题是旧版本的已知bug,官方在后续版本里已经替换了lambda的使用逻辑。执行下面的命令升级即可:

pip install --upgrade daphne

升级后重新运行测试,大概率能直接解决问题。

方案2:重写测试类的进程启动方法

如果升级后还是有问题,你可以在测试类里重写get_worker_process方法,手动创建Daphne进程,避开原逻辑里的lambda:

from django.test import ChannelsLiveServerTestCase
from daphne.server import Server
from django.conf import settings
from django.utils.module_loading import import_string
from multiprocessing import Process

class ChatTestCase(ChannelsLiveServerTestCase):
    def get_worker_process(self, port):
        # 手动初始化ASGI应用与Daphne服务器
        application = import_string(settings.ASGI_APPLICATION)
        server = Server(application)
        # 直接传递server.run方法作为进程目标,替代原逻辑中的lambda
        return Process(
            target=server.run,
            args=(port,),
        )

方案3:调整多进程启动方式

在测试文件的最顶部添加以下代码,强制使用spawn启动方式(Windows默认是spawn,Linux/macOS可能需要显式设置),确保子进程能正确序列化所需对象:

import multiprocessing

# 仅在主进程执行时设置启动方式
if __name__ == '__main__':
    multiprocessing.set_start_method('spawn')

额外排查点

  • 确认你的测试类继承的是ChannelsLiveServerTestCase,而非普通的TestCase——只有前者会自动启动ASGI服务器进程。
  • 检查settings.ASGI_APPLICATION配置是否正确,确保指向你的项目ASGI应用模块。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.26 08:12:29