可以使用 psycopg2 进行异步 i/o(可以在此处阅读)但是我不确定如何进行异步事务。考虑这一系列的事情:
- 绿色线程 1 启动事务 T
- GT1问题更新
- GT2 发布一个事务性更新
- GT1问题更新
- GT1 提交事务 T
我假设 GT1 更新与 GT2 更新冲突。
现在根据文档:
从同一连接创建的游标不是孤立的,即游标对数据库所做的任何更改都可以立即被其他游标看到。
所以我们不能在游标上实现上面的流程。我们可以在不同的连接上实现它,但是由于我们正在执行异步操作,因此产生(可能)数千个数据库连接可能会很糟糕(更不用说 Postgres 无法处理这么多的开箱即用)。
另一种选择是拥有一个连接池并重用它们。但是,如果我们发出 X 个并行事务,则所有其他绿色线程都会被阻塞,直到某个连接可用。因此,有用的绿色线程的实际数量是 ~X(假设应用程序受数据库严重限制),这引发了一个问题:我们为什么要使用 async 开始?
现在这个问题实际上可以推广到 DB API 2.0。也许真正的答案是 DB API 2.0 不适合异步编程?那么我们将如何在 Postgresql 上执行异步 io 呢?也许其他一些图书馆?
或者可能是因为 postgresql 协议实际上是同步的?能够在任何时间(每个连接)“写入”任何事务将是完美的。Postgresql 必须为此公开事务的 id。可行吗?也许两阶段提交是答案?
或者我在这里错过了什么?
编辑:这似乎是 SQL 的一个普遍问题,因为BEGIN; COMMIT;
语义不能有效地异步使用。