Fork me on GitHub

コネクションプール


database/sql パッケージには基本的なコネクションプールがあります。制御したり検査したりするための多くの機能はありませんが、知っておくと便利なことがあります。

  • コネクションプーリングとは、単一のデータベースに2つの連続するステートメントを実行するときに、2つのコネクションが開かれ、独立して実行される可能性があることになります。プログラマにとって、コードがうまく動かない原因に混乱することはよくあることです。例えば LOCK TABLES の後の INSERT はブロックされる可能性があります。INSERT はテーブルのロックを取得したコネクションとは別のコネクションにある可能性があるためです。

  • コネクションは必要なときに生成され、プール内には空いているコネクションはありません。

  • デフォルトではコネクションの数に制限はありません。一度に多くのことをしようとすると任意の数のコネクションを生成することができます。ただしデータベースは「接続が多すぎます」などのエラーを返すことがあります。

  • Go1.1以降では、db.SetMaxIdleConns(N) を使用して、プール内のアイドルコネクションの数を制限できます。ただし、これはプールサイズを制限しません。

  • Go1.2.1以降では、データベースへのOpenしている合計のコネクション数を制限するために db.SetMaxIdleConns(N) を使うことができます。残念なことに デッドロックのバグ ( 修正済 ) により db.SetMaxOpenConns(N) が1.2では安全に使用できなくなります。

  • コネクションは非常に早く再利用されるようになります。db.SetMaxIdleConns(N) でアイドルコネクション数を高い値にしておくことでこの再生成を減らすことができ、再利用のためのコネクションを維持できます。

  • コネクションを長時間アイドル状態にしておくと問題が発生する場合があります。(このような Microsoft AzureのMySQLに関するものです。アイドル時間が長すぎることによってコネクションのタイムアウトが発生する場合、db.SetMaxIdleConns(0) を試してみてください。

  • db.SetConnMaxLifetime(duration) を設定することにより、コネクションを再利用できる最大時間を指定できます。これは、長時間有効なコネクションを再利用するとネットワークの問題が発生する可能性があるためです。これにより、未使用のコネクションが遅延して閉じられます。つまり、有効期限が切れた接続を閉じることが延期される場合があります。