Golang - PGBouncer和交易用法
-
21-12-2019 - |
题
技术细节
- go版本1.2
- Postrgres Go BMizerany / PQ
这个问题让我发疯了,我希望有人能够提供帮助。
我已经开发在golang应用程序读取从Postgres数据库和每个记录数据使一个HTTP请求,然后更新该数据库。
这一切都足够简单。但是,我们有PGBouncer到位。我们为PGBouncer的配置是这样它不支持准备的陈述。围棋默默包裹在一份声明中的所有查询。围绕PGBouncer的方式是设置交易。这一切都很好,对插入/更新/删除等事情有益。
在SELECT语句中,我在事务中包装它:
func TransactionQuery(db *sql.DB, baseQuery string) (rows *sql.Rows, code int, err error) {
tx, txErr := db.Begin()
if txErr != nil {
return nil, -1, txErr
}
selectStmt, prepErr := tx.Prepare(baseQuery)
if prepErr != nil {
return nil, -1, fmt.Errorf("Failed to prepare statment: %s Error: %v", baseQuery, prepErr)
}
defer func() {
if stmtErr := selectStmt.Close(); stmtErr != nil {
rows = nil
code = -2
err = fmt.Errorf("Failed to close statement: %v.", stmtErr)
}
}()
rows, err = selectStmt.Query()
if err != nil {
fmt.Errorf("Failed to retrieve data: %v", err)
return nil, -1, err
}
return rows, 0, nil
}
.
(HHMM,似乎有抛缩进取下一小) ass你可以看到我开始bnut未关闭交易。这会导致在事物的PG侧,每一个选择是在事务”状态的“怠速留下了问题。
我已经尝试了tx.commit()和tx.rollback()和在两种情况下我得到错误:
"unknown response for simple query '3'"
.
或
"unknown response for simple query 'D'"
.
何我成功地关闭围棋交易?我希望能够让我们的pgbouncer.ini更新,允许我为驱动程序库切换到lib / pq,但我不确定这是否会直接帮助这个问题。
所以,如何正确关闭TX对象,或者有没有办法强制转到不使用引擎盖下的准备语句?
谢谢 内森
我试图改变一下:
func TransactionQuery(db *sql.DB, baseQuery string) (rows *sql.Rows, code int, err error) {
tx, txErr := db.Begin()
if txErr != nil {
return nil, -1, txErr
}
/*selectStmt, prepErr := tx.Prepare(baseQuery)
if prepErr != nil {
return nil, -1, fmt.Errorf("Failed to prepare statment: %s Error: %v", baseQuery, prepErr)
}
*/
rows, err = tx.Query(baseQuery)
if err != nil {
fmt.Errorf("Failed to retrieve data: %v", err)
return nil, -1, err
}
/* if stmtErr := selectStmt.Close(); stmtErr != nil {
rows = nil
code = -2
err = fmt.Errorf("Failed to close statement: %v.", stmtErr)
}*/
if txCloseErr := tx.Commit(); txErr != nil {
rows = rows
code = -3
err = txCloseErr
}
return rows, 0, nil
}
.
我在带有此代码的日志中看到的内容:
pq: unexpected describe rows response: '3'
.
但是,我应该指出,这是在第二次尝试SELECT语句的时候。此应用程序选择批处理,处理它,然后选择后续批处理。第二个选择时会发生此错误。第一个选择没有问题。 解决方案
对于其他人击中这个,我已经解决了这一点。
我已经将行对象返回到上面的呼叫代码(未示出)。在读取行之前结束交易似乎是问题的原因。我完全明白为什么如此,请澄清你是否这样做。
现在我返回行和事务对象。然后,当我读取所有行时,我回滚事务。这让一切都能工作。
谢谢 内森
其他提示
tx.query返回sql.rows的实例,它是一个光标到结果集。在迭代此光标时,数据并不一定检索。在迭代光标时,事务必须保持打开。
这就是为什么在交易关闭后,您无法再迭代光标。
不隶属于 StackOverflow