为什么 APScheduler 类没有序列化?

问题描述

我正在尝试使用共享内存创建一个单例,以确保所有进程之间的类对象都相同,但为此我需要对其进行序列化:

class Singleton(type):

    filename = path.basename(path.abspath(__file__)).split('.')[0]

    def __call__(cls,*args,**kwargs):
        instance = super(Singleton,cls).__call__(*args,**kwargs)
        pickled = pickle.dumps(instance)


class SingleScheduler(APScheduler,Metaclass=Singleton):

    def __init__(self,**kwargs):
        super().__init__(args,kwargs)
TypeError: Schedulers cannot be serialized. Ensure that you are not passing a scheduler instance as an argument to a job,or scheduling an instance method where the instance contains a scheduler as an attribute.

有什么方法可以序列化这个吗?

附言是的,我知道我可以只获取一个 redis 并将参数和状态传递给它,但我想尝试在没有任何依赖的情况下进行...

解决方法

调度程序被明确地设为不可序列化,因为它无论如何都不会序列化,因为它包含同步原语和对作业存储的引用。很多人因此遇到了酸洗错误,因此 3.7.0 版本添加了这条明确的错误消息。

只要付出足够的努力,所有这些都可以解决,内存作业存储除外。如果您的目的是创建共享单个外部存储的调度程序的多个副本,这将不适用于 APScheduler 3.x,因为它不是为分布式使用而设计的。 4.0 版本将纠正这一点,这是那里最突出的功能。另一方面,如果您使用内存支持的作业存储,序列化只会创建作业的多个副本,此时您最好为每个进程创建一个新的调度程序。

如果你想在多个进程之间共享一个调度器,在 APScheduler 3.x 上实现的方法是让调度器在一个专用进程中运行,然后通过 RPyC、一些 Web 服务器或类似的 IPC 与所述进程通信或网络机制。

FAQ entry on scheduler sharing

Example on how to use RPyC to provide a shared scheduler

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...