Deep-dive on the Next Gen Platform. Join the Webinar!

Skip Navigation
Show nav
Dev Center
  • Get Started
  • ドキュメント
  • Changelog
  • Search
  • Get Started
    • Node.js
    • Ruby on Rails
    • Ruby
    • Python
    • Java
    • PHP
    • Go
    • Scala
    • Clojure
    • .NET
  • ドキュメント
  • Changelog
  • More
    Additional Resources
    • Home
    • Elements
    • Products
    • Pricing
    • Careers
    • Help
    • Status
    • Events
    • Podcasts
    • Compliance Center
    Heroku Blog

    Heroku Blog

    Find out what's new with Heroku on our blog.

    Visit Blog
  • Log inorSign up
Hide categories

Categories

  • Heroku のアーキテクチャ
    • Dyno (アプリコンテナ)
      • Dyno Management
      • Dyno Concepts
      • Dyno Behavior
      • Dyno Reference
      • Dyno Troubleshooting
    • スタック (オペレーティングシステムイメージ)
    • ネットワーキングと DNS
    • プラットフォームポリシー
    • プラットフォームの原則
  • Developer Tools
    • コマンドライン
    • Heroku VS Code Extension
  • デプロイ
    • Git を使用したデプロイ
    • Docker によるデプロイ
    • デプロイ統合
  • 継続的デリバリーとインテグレーション
    • 継続的統合
  • 言語サポート
    • Node.js
      • Working with Node.js
      • Troubleshooting Node.js Apps
      • Node.js Behavior in Heroku
    • Ruby
      • Rails のサポート
      • Bundler の使用
      • Working with Ruby
      • Ruby Behavior in Heroku
      • Troubleshooting Ruby Apps
    • Python
      • Working with Python
      • Python でのバックグランドジョブ
      • Python Behavior in Heroku
      • Django の使用
    • Java
      • Java Behavior in Heroku
      • Working with Java
      • Maven の使用
      • Spring Boot の使用
      • Troubleshooting Java Apps
    • PHP
      • PHP Behavior in Heroku
      • Working with PHP
    • Go
      • Go の依存関係管理
    • Scala
    • Clojure
    • .NET
      • Working with .NET
  • データベースとデータ管理
    • Heroku Postgres
      • Postgres の基礎
      • Postgres スターターガイド
      • Postgres のパフォーマンス
      • Postgres のデータ転送と保持
      • Postgres の可用性
      • Postgres の特別なトピック
      • Migrating to Heroku Postgres
    • Heroku Data For Redis
    • Apache Kafka on Heroku
    • その他のデータストア
  • AI
    • Working with AI
  • モニタリングとメトリクス
    • ログ記録
  • アプリのパフォーマンス
  • アドオン
    • すべてのアドオン
  • 共同作業
  • セキュリティ
    • アプリのセキュリティ
    • ID と認証
      • シングルサインオン (SSO)
    • Private Space
      • インフラストラクチャネットワーキング
    • コンプライアンス
  • Heroku Enterprise
    • Enterprise Accounts
    • Enterprise Team
    • Heroku Connect (Salesforce 同期)
      • Heroku Connect の管理
      • Heroku Connect のリファレンス
      • Heroku Connect のトラブルシューティング
  • パターンとベストプラクティス
  • Heroku の拡張
    • Platform API
    • アプリの Webhook
    • Heroku Labs
    • アドオンのビルド
      • アドオン開発のタスク
      • アドオン API
      • アドオンのガイドラインと要件
    • CLI プラグインのビルド
    • 開発ビルドパック
    • Dev Center
  • アカウントと請求
  • トラブルシューティングとサポート
  • Salesforce とのインテグレーション
  • パターンとベストプラクティス
  • PgBouncer の設定

PgBouncer の設定

日本語 — Switch to English

この記事の英語版に更新があります。ご覧の翻訳には含まれていない変更点があるかもしれません。

最終更新日 2023年05月16日(火)

Table of Contents

  • データベース接続、セッション、接続プール
  • PgBouncer の接続プールのモード
  • Heroku での PgBouncer: サーバー側とクライアント側の比較
  • クライアント側の buildpack の設定

Heroku Postgres ユーザーで、選択されているデータベースプラン​の接続制限が発生する場合があります。その結果、接続リクエストがキューに入れられるため、パフォーマンスや信頼性が低下する可能性があります。PgBouncer で接続プールを使用すると、クライアント間でデータベースサーバー接続を共有することによってこの問題を解決できます。

この記事の内容は次のとおりです。

  • データベース接続とセッションの動作の概要について説明します。
  • PgBouncer で使用可能な接続プールのさまざまなタイプについて詳細に説明します。
  • Heroku で PgBouncer を使用した接続プールを実装する方法について説明します。

Premier または Signature Success Plan の Heroku Enterprise​ の顧客は、Customer Solutions Architecture (CSA) チームに、このトピックに関する詳細なガイダンスを要求​できます。ここでエキスパートコーチングセッション​について学習するか、または Salesforce の担当者にお問い合わせください。

データベース接続、セッション、接続プール

接続プールを使用すると、データベース接続とセッションの動作に関する重要な変更が導入されます。これらの変更を理解するには、まず、それらの通常の動作を理解することが重要です。プールされていない接続は、次の標準のクライアントサーバー接続アーキテクチャに従います。

Client-Server Connection Model

接続プールを使用しない PostgreSQL 接続のライフサイクル​の高レベルのビューを次に示します。

  1. クライアントが、サーバーへの接続を依頼し、それを認証することによって新しいセッションを開始します。
  2. サーバーは、接続と作業セッションを処理するための新しいシステムプロセスをフォークします。このセッションの状態は、サーバーレベル、データベースレベル、およびユーザーレベルの設定パラメータの組み合わせごとに初期化されます。
  3. クライアントは 1 つ以上のトランザクションを実行することによって、必要な量の作業を行います。例として、次のものがあります。
    • 関連 (テーブルやビューなど) に対する読み取りや書き込みを実行する
    • SET コマンドを使用して、セッションまたはトランザクションの状態を変更する
    • プリペアドステートメントを準備して実行する
  4. クライアントが接続を切断すると、セッションは終了します。
  5. サーバーは、セッションを処理したプロセスを破棄します。

データベースセッション​は、1 つの接続の有効期間にわたって実行されたすべての作業で構成されます。データベースセッションは時間の長さが可変であり、クライアントとサーバーの両方で可変量のリソースを消費します。

これの重要な点は次のとおりです。

  • 接続プロセスの作成、管理、および破棄は時間がかかり、リソースを消費します。
  • サーバーの接続数が増えると、それらの接続を管理するために必要なリソースも増加します。さらに、クライアントがそれらの接続で作業を行うと、サーバーのプロセスごとのメモリ使用量は増加し続けます。
  • 1 つのセッションは 1 つのクライアントしか処理しないため、クライアントはデータベースセッションの状態を変更し、これらの変更が連続したトランザクションにまたがって保持されることを期待できます。

接続プーラー​は、クライアントとサーバーの間に配置されます。クライアントはプーラーに接続し、プーラーがサーバーに接続します。接続プーラーの導入によって、接続モデルがクライアントプロキシサーバーアーキテクチャに変更されます。

Client-Pooler-Server Connection Model

これにより、クライアント接続の有効期間がサーバー接続とプロセスの有効期間から切り離されます。接続プーラーは、次の役割を担うようになります。

  • クライアントからの接続の受け付けと管理
  • サーバーへの接続の確立と保持
  • クライアント接続へのサーバー接続の割り当て

これにより、次のことが可能になります。

  • 1 つのサーバー接続で、異なるクライアントのセッション、トランザクション、ステートメントを処理できます。
  • 1 つのクライアントセッションのトランザクションかステートメント、またはその両方を異なるサーバー接続で実行できます。

この記事の残りの部分は次のとおりです。

  • “クライアント接続” は、クライアントと接続プーラーの間の接続を指します。
  • “サーバー接続” は、接続プーラーとサーバーの間の接続を指します。

PgBouncer の接続プールのモード

PgBouncer には、使用可能なプーリングモードとしてトランザクションプーリング、セッションプーリング、ステートメントプーリングの 3 つがあります。それぞれの動作を理解することが重要です。使用されるプーリングモードは、次のように機能します。

  • サーバー接続がクライアント接続にどれだけ長く割り当てられたままになるかを決定します。
  • クライアントは何ができ、何ができないかに関する制限を課します。これは、次のセクションで説明されます。

トランザクションプーリングモード (推奨)

データベースクライアントが、連続したトランザクションを間で一時停止せずに実行することはめったにありません。代わりに、データベース以外の作業はトランザクション間で実行されます。つまり、サーバー接続は新しい作業の到着を待機している間、アイドル状態で長い時間を費やします。

トランザクションプーリングモードは、次のように、サーバー接続のアイドル時間を短縮しようとします。

  • クライアントがトランザクションを開始すると、プーラーはそのクライアントにサーバー接続を割り当てます。
  • クライアントのトランザクションが完了するとすぐに、プーラーは接続の割り当てを解放します。

これは次のことを示します。

  • クライアントが複数のトランザクションを実行する場合は、各トランザクションが異なるサーバー接続で実行される可能性があります。
  • 1 つのサーバー接続が、その有効期間中、異なるクライアントによって発行されたトランザクションを実行できます。

Transaction Pooling Mode Example

これにより、アクティブなクライアントの数は、サーバーによって許可される接続よりはるかに多くなります。特定のワークロードに左右されるものの、アクティブなクライアント接続のサーバー接続に対する比率が 10 倍以上になることも珍しくありません。

これには、次の重要な注意事項が伴います。同じクライアントによって作成された連続したトランザクションが異なるサーバー接続で実行される可能性があるため、クライアントは、データベースセッション状態への変更がそれらのトランザクションにまたがって保持されることを期待できなくなります。さらに、クライアントがセッション状態を変更すると、それが他のクライアントに影響を与える可能性があります。

トランザクションプーリングを示す上の図の例を使用したいくつかの例を次に示します。

  • クライアント 1 が T1 で最初のサーバー接続でセッションを読み取り専用に設定し、クライアント 2 の T3 が書き込みトランザクションである場合、読み取り専用になっているサーバー接続で実行されるため T3 は失敗します。
  • クライアント 1 が T1 で PREPARE a1 AS ...​ を実行した後、T2 で EXECUTE a1 ...​ を実行した場合、そのプリペアドステートメントは T1 が実行されたサーバー接続に対してローカルであるため T2 は失敗します。
  • クライアント 2 が T3 で一時テーブルを作成し、T4 でそれを使用しようとする場合、その一時テーブルは T3 が実行されたサーバー接続に対してローカルであるため T4 は失敗します。

トランザクションプーリングモードの利点:

  • アクティブなクライアントの数が、サーバーによって許可される接続より多くなります。
  • 特定の数のクライアントに必要なサーバーリソースが削減されます。

 

トランザクションプーリングモードの注意事項:

  • SET​ を使用したセッション状態に対するすべての変更は、その変更が現在実行されているトランザクションにのみスコープ指定されるように、SET LOCAL​ を使用してのみ行う必要があります。SET SESSION​、またはトランザクションプーリングではデフォルトで SET SESSION​ になる単独の SET​ を決して使用しないでください。
  • プリペアドステートメントは使用できません。
  • 一時テーブルを使用している場合、それらのテーブルは同じトランザクションで作成、使用、および削除する必要があります。ヒント: ​一時テーブルを作成する​ときに ON COMMIT DROP​ を使用すると、作成したトランザクションが完了したとき、それらのテーブルは自動的に削除されます。
  • options​ などの特定の接続パラメータを PgBouncer に渡すことはできません。

トランザクションプーリングを使用するときにサポートされないセッション状態の機能と操作の完全な一覧については、PgBouncer の一覧​を参照してください。

セッションプーリングモード

ここでは、クライアントへのサーバー接続の割り当てがクライアント接続の有効期間中は継続されます。これは、接続プーラーをまったく使用しない場合と同じに見えるかもしれませんが、重要な違いがあります。割り当てられているクライアントが接続を切断しても、サーバー接続は破棄されません。クライアントが接続を切断すると、プーラーは次の処理を行います。

  • そのクライアントによって行われたセッション状態の変更をすべて消去します。
  • サーバー接続を別のクライアントで使用できるようにプールに戻します。

Session Pooling Mode Example

セッションプーリングモードの利点:

  • セッションプーリングは、クライアントが接続したとき、サーバーが新しい接続プロセスを作成するまで待機するために費やされる時間を短縮します。
  • 多くの ORM やアプリケーションフレームワークが、その組み込みの接続プールによるセッションプーリングを提供しています (Ruby on Rails など)。

 

セッションプーリングモードの注意事項:

  • サーバー接続の割り当てが、割り当てられているクライアント接続の有効期間中は継続されるため、アクティブなクライアント接続の数が依然としてサーバーの接続制限によって制限されます。
  • セッションプーリングで PgBouncer を使用する前に、選択したアプリケーションフレームワークか ORM、またはその両方にセッションプールが用意されているかどうかを必ず確認してください。
  • options​ などの特定の接続パラメータを PgBouncer に渡すことはできません。

ステートメントプーリングモード

ここでは、サーバー接続の割り当てが 1 つのステートメントの期間中しか継続されません。これには、トランザクションプーリングモードと同じセッション状態の制限がありますが、さらにトランザクションのセマンティックスも中断されます。

Statement Pooling Mode Example

これにより、すべてのクライアント接続が “自動コミット” モードであるかのように動作します。クライアントがマルチステートメントトランザクションを開始しようとすると、プーラーはエラーを返します。それは制限になりますが、アクティブなクライアント接続の数はトランザクションプーリングの場合より多くなります。適切なユースケースとしては、大量の単純なキールックアップの処理や、単一ステートメントの書き込みの発行などがあります。

ステートメントプーリングモードの利点:

アクティブなクライアント接続の数が、トランザクションプーリングモードよりはるかに多くなります。

 

ステートメントプーリングモードの注意事項:

  • トランザクションプーリングモードと同じセッション状態の制限があります。
  • マルチステートメントトランザクションは許可されません。
  • options​ などの特定の接続パラメータを PgBouncer に渡すことはできません。

Heroku での PgBouncer: サーバー側とクライアント側の比較

Heroku プラットフォームで PgBouncer を使用するためのオプションには、サーバー側​とクライアント側​の 2 つがあります。各オプションの主な機能を次に示します。

サーバー側

  • Heroku Postgres サーバー上でローカルに動作する
  • トランザクションプーリングモードのみ
  • 最大 10,000 のクライアント接続をサポート
  • ユーザーの設定変更はサポートされない
  • デフォルトの Postgres 資格情報​での使用のみをサポート
  • このオプションを設定して使用する方法については、ここ​のドキュメントを参照してください。

クライアント側の buildpack

  • 使用が (アプリケーションの Procfile で) 設定されている各 dyno タイプでローカルに動作する
  • アプリケーションの環境設定を使用した PgBouncer の最も一般的な設定オプションの設定が可能
  • 任意の数の Heroku Postgres 資格情報で動作する
  • buildpack​ をインストールして使用する方法については、ここ​のドキュメントを参照してください。

サーバー側またはクライアント側のどちらかの PgBouncer の選択

サーバー側のオプションは、設定項目の少なさが制限になるように見えるかもしれませんが、使いやすいトランザクションプーラーを必要とする最も一般的なユースケースに対応しています。ある時点でその制限が厳しくなりすぎた場合は、代わりにクライアント側の buildpack を使用できます。

次の場合は、まずサーバー側のオプションを検討してください。

  • トランザクションプーリングモードをまさに必要としている。
  • デフォルトの Heroku Postgres 資格情報のみを使用している。

次の場合は、クライアント側のオプションを使用してください。

  • 接続プールの制御と設定可能性を完全なものにしたい。
  • デフォルトの資格情報だけでなく、それ以上の資格情報を使用する。
  • セッションプーリングモードまたはステートメントプーリングモードのどちらかが必要である。

クライアント側の buildpack の設定

デフォルト値から変更することを考慮する必要がある主な設定オプションの簡単な概要を次に示します。

PgBouncer の接続プールは、1 人のデータベースユーザーによって 1 つのホスト上の 1 つのデータベースに対して作成されたすべての接続で構成されています。たとえば、'user1’ によって ‘host1’ 上の ‘database1’ に対して作成されたすべての接続が、特定の PgBouncer インスタンス上の同じプールを使用します。

PGBOUNCER_POOL_MODE (Default: transaction)

これは、セッションプーリングモードまたはステートメントプーリングを使用する場合に変更します。

PGBOUNCER_URLS (Default: DATABASE_URL)

各 dyno 上のローカルの PgBouncer インスタンスを指すように書き換えるための、アプリケーション設定 URL の (スペースで区切られた) 一覧。この URL の書き換えは、アプリケーションの環境設定ではなく、実行中の dyno 上の環境変数値にのみ影響を与えます。

PGBOUNCER_MAX_CLIENT_CONN (Default: 100)

プーラーが完全に拒否するようになる前に、管理されているすべてのプールにまたがって受け入れるクライアントの数。トランザクションまたはステートメントプーリングを使用しているときは、サーバー接続の制限よりはるかに多くなる場合があるため、デフォルト値が大きくなっています。

PGBOUNCER_DEFAULT_POOL_SIZE (Default: 1)

予約接続 (以下を参照) を使用する前にプールに割り当てることができるサーバー接続の最大数。dyno ごとに並列リクエストを処理する大きな、トラフィック量の多いアプリケーションでは、この値を増やします。

この値を設定する場合は、すべての dyno 上のすべてのプールにわたって許可されるサーバー接続の合計数がサーバーの接続制限を超えることがないように注意してください。

たとえば、それぞれに 1 つのプールを持つ 20 の dyno を実行することを計画している場合、20 のすべての dyno にまたがって作成できるサーバー接続の最大数を決定するには、この値に 20 を掛ける必要があります。その計画で 500 の接続を許可する場合は、この値を 25 以下に維持する必要があります (20 * 25 -> 500)。

PgBouncer での Preboot 機能​の使用に関する注意事項

Preboot は、dyno の置き換えを起動してから、置き換えられる dyno を停止する (dyno の再起動は dyno の置き換え) ことによって、dyno の再起動のトラフィックの中断への影響を最小限に抑えるように動作します。 すべてのプールの dyno にまたがって許可されるサーバー接続の合計数が Heroku Postgres プランの接続制限の半分を超えており、かつ新しい dyno が急速に増大した場合は、アプリケーションのリクエストがデータベース接続を待機している間に停止し、これに対処するためにプールサイズの削減が必要になるという問題が発生する可能性があります。

PGBOUNCER_RESERVE_POOL_SIZE (Default: 1)​ および PGBOUNCER_RESERVE_POOL_TIMEOUT (Default: 5 seconds)

特定のプールのアクティブなサーバー接続が現在最大値に達している (PGBOUNCER_DEFAULT_POOL_SIZE​ を参照) ために、クライアントがサーバー接続の割り当てを待機している場合は、PGBOUNCER_RESERVE_POOL_TIMEOUT​ の待機時間が経過した後に最大 PGBOUNCER_RESERVE_POOL_SIZE​ 個の追加の接続を許可します。予約プールは、すべての接続プールで共有されます。

PGBOUNCER_SERVER_IDLE_TIMEOUT (Default: 10 seconds)

これより長い時間にわたって未使用のままになっているサーバー接続はすべて閉じられます。これを 0 に設定すると、アイドルタイムアウトが無効になります。

PGBOUNCER_SERVER_LIFETIME (Default: 3600 seconds)

この設定より長い時間にわたって有効になっている未使用のサーバー接続はすべて閉じられます。これを 0 に設定しても、この設定は無効にならず、代わりに各サーバー接続が 1 回使用の接続になります。

PGBOUNCER_SERVER_RESET_QUERY (Default: "DISCARD ALL;" in session pooling mode, empty otherwise)

これは、クライアントがセッションプーリングモードで接続を切断した後、プーラーがセッションをリセットするために使用します。この記事の前の部分で詳細に説明されているように、トランザクションおよびステートメントプーリングモードを使用しているときは、これを使用してサポートされないセッション状態の機能を回避するための効果的な方法はありません。

PGBOUNCER_QUERY_WAIT_TIMEOUT (Default: 120 seconds)

これにより、プーラーがエラーを返す前に、クライアントがサーバー接続の割り当てを待機するために許可される時間が決定されます。クライアントが定期的にサーバー接続を待機していることが疑われる場合は、これを小さい値にすると、最終的に続行したクライアントではなく、失敗したクライアントが原因であることを示すのに役立ちます。

関連カテゴリー

  • パターンとベストプラクティス
アプリケーションの負荷テスト リソースコストの最適化

Information & Support

  • Getting Started
  • Documentation
  • Changelog
  • Compliance Center
  • Training & Education
  • Blog
  • Support Channels
  • Status

Language Reference

  • Node.js
  • Ruby
  • Java
  • PHP
  • Python
  • Go
  • Scala
  • Clojure
  • .NET

Other Resources

  • Careers
  • Elements
  • Products
  • Pricing
  • RSS
    • Dev Center Articles
    • Dev Center Changelog
    • Heroku Blog
    • Heroku News Blog
    • Heroku Engineering Blog
  • Twitter
    • Dev Center Articles
    • Dev Center Changelog
    • Heroku
    • Heroku Status
  • Github
  • LinkedIn
  • © 2025 Salesforce, Inc. All rights reserved. Various trademarks held by their respective owners. Salesforce Tower, 415 Mission Street, 3rd Floor, San Francisco, CA 94105, United States
  • heroku.com
  • Legal
  • Terms of Service
  • Privacy Information
  • Responsible Disclosure
  • Trust
  • Contact
  • Cookie Preferences
  • Your Privacy Choices