在Go中为SQL连接设置TCP超时

Pet*_*jci 7 database connection tcp go

当我使用VPN连接到数据库(使用标准的go sql库)并且VPN接口出现故障时,无论接口是否同时启动,尝试进行SQL查询都会有75秒钟的超时。我想将此超时减少到某个合理的时间,因此在这种情况下,我的应用程序不会冻结75秒。

db, err := sql.Open(driverName, dataSourceName)
Run Code Online (Sandbox Code Playgroud)

是否可以通过db变量以某种方式设置它?

ter*_*kes 7

从 Go 1.8 开始,sql.DB抽象现在接受context.Context,它可用于更快地超时连接。

func (c *Client) DoLookup(ctx context.Context, id int) (string, error) {
  var name string
  // create a child context with a timeout
  newCtx, cancel := context.WithTimeout(ctx, time.Second)
  // release resources used in `newCtx` if
  // the DB operation finishes faster than the timeout
  defer cancel()

  row := c.db.QueryRowContext(newCtx, "SELECT name FROM items WHERE id = ?", id)

  err := row.Scan(&name)
  if err != nil {
    return "", err
  }

  return name, nil
}
Run Code Online (Sandbox Code Playgroud)

如果您的DoLookup函数尚未采用 a context.Context(它确实应该!),您可以通过调用 来创建一个父函数context.TODO()


Ili*_*oly 6

database/sql包不超时将呼叫提供的一般方法database/sql.Open。但是,各个驱动程序通过DSN(dataSourceName)连接字符串提供此功能。

https://github.com/lib/pq

sql.Open("postgres", "user=user dbname=dbname connect_timeout=5")
Run Code Online (Sandbox Code Playgroud)

https://github.com/go-sql-driver/mysql

sql.Open("mysql", "user:password@/dbname?timeout=5s")
Run Code Online (Sandbox Code Playgroud)

https://github.com/denisenkom/go-mssqldb

sql.Open("sqlserver", "sqlserver://username:password@host/instance?dial+timeout=5")
Run Code Online (Sandbox Code Playgroud)

等...