【问题标题】:platform dependent error with psycopg2: (only) Win10 says "can't pickle psycopg2.extensions.connection"psycopg2 的平台相关错误:(仅限)Win10 说“无法腌制 psycopg2.extensions.connection”
【发布时间】:2018-10-22 00:00:30
【问题描述】:

我有一些连接到 postgres 的多处理代码。核心逻辑不是很复杂:

manager = Manager()
managedwork = manager.list(thelist)
connections = {i: setconnection() for i in range(workercount)}
jobs = [Process(target=managedworker, args=(managedwork, connections[i])) for i in range(workercount)]

setconnection() 返回一个内部有 psycopg2 连接的对象。界面不是很有趣:c = setconnection() + c.dbconnection 会给你你认为你可能得到的东西。在我们定义了作业之后,以下会产生问题:

for j in jobs:
    j.start()
for j in jobs:
    j.join()

start() 在 Windows10 上使用 python37 引发异常:TypeError: can't pickle psycopg2.extensions.connection objects。被冒犯的一方是ForkingPickler

同样的代码在安装了python37 的 macOS、FreeBSD 和 Linux 上也能正常工作。 psycopg 2.7.5 也部署在所有四个平台上。我很想知道可能需要什么样的修复来解决这个问题。我根本不习惯 Windows,所以对于其他人来说可能很明显为什么会发生这种情况。

感谢您的关注和帮助。

【问题讨论】:

    标签: python-3.x multiprocessing cross-platform pickle psycopg2


    【解决方案1】:

    回答我自己的问题,因为它可能对其他人有所帮助...

    posix 系统 (os.name) 上,如果连接发送给每个工作人员,则会出现线程问题。在nt 系统上(又是os.name),连接无法被腌制,因此无法发送给工作人员。核心问题似乎是 nt 需要的 spawn 方法 - 与 posix 使用 fork 形成鲜明对比 - 用于 multiprocessing

    核心程序现在通过一个有点丑陋的解决方法工作。如果os.name = nt,则发送None 作为连接。然后通过测试在新生成的解释器副本中获取一个连接:if not connection: connection = setconnection()。令人讨厌,但也许是不可避免的,因为 multiprocessing 的实现在各个平台之间并不统一......

    【讨论】:

      猜你喜欢
      • 2020-07-25
      • 1970-01-01
      • 2019-03-03
      • 1970-01-01
      • 2018-09-23
      • 2017-12-03
      • 1970-01-01
      • 2012-04-21
      • 2012-12-23
      相关资源
      最近更新 更多