return tx.dc, nil
}
+// closemuRUnlockRelease is used as a func(error) method value in
+// ExecContext and QueryContext. Unlocking in the releaseConn keeps
+// the driver conn from being returned to the connection pool until
+// the Rows has been closed.
+func (tx *Tx) closemuRUnlockRelease(error) {
+ tx.closemu.RUnlock()
+}
+
// Closes all Stmts prepared for this transaction.
func (tx *Tx) closePrepared() {
tx.stmts.Lock()
// For example: an INSERT and UPDATE.
func (tx *Tx) ExecContext(ctx context.Context, query string, args ...interface{}) (Result, error) {
tx.closemu.RLock()
- defer tx.closemu.RUnlock()
dc, err := tx.grabConn(ctx)
if err != nil {
+ tx.closemu.RUnlock()
return nil, err
}
- return tx.db.execDC(ctx, dc, func(error) {}, query, args)
+ return tx.db.execDC(ctx, dc, tx.closemuRUnlockRelease, query, args)
}
// Exec executes a query that doesn't return rows.
// QueryContext executes a query that returns rows, typically a SELECT.
func (tx *Tx) QueryContext(ctx context.Context, query string, args ...interface{}) (*Rows, error) {
tx.closemu.RLock()
- defer tx.closemu.RUnlock()
dc, err := tx.grabConn(ctx)
if err != nil {
+ tx.closemu.RUnlock()
return nil, err
}
- releaseConn := func(error) {}
- return tx.db.queryDC(ctx, dc, releaseConn, query, args)
+
+ return tx.db.queryDC(ctx, dc, tx.closemuRUnlockRelease, query, args)
}
// Query executes a query that returns rows, typically a SELECT.