db-connection-pooling について
データベース接続プールの設定リスクを調べ、接続枯渇につながる問題を特定するスキルです。サーバーレス環境からのPostgres直結、トランザクションプーラーとの互換性、プールサイズを扱います。
主な機能
- 01サーバーレスからのPostgres直結を検出
- 02トランザクションプールとセッション機能の競合確認
- 03接続上限に対するプールサイズの評価
- 04Postgres検証クエリの提示
活用シーン
- 01サーバーレス環境のDB接続設定の確認
- 02トランザクションプールでのプリペアド文使用の調査
- 03プール数とインスタンス数の上限超過確認
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ hainrixz/ claude-db --skill db-connection-poolingインストール後、Claude Code で/db-connection-poolingを入力して読み込まれたか確認します。
詳細
db-connection-pooling (M15)
接続の枯渇は、本番環境での障害の主な原因であり、純粋にパフォーマンスとスケーラビリティ(軸
performance)に関する問題です。リレーショナルデータベースの Pooling w10、およびすべての NoSQL
プロファイルの Conexión カテゴリに影響します。現代で主流の障害パターンは、サーバーレス関数が直接接続をそれぞれ開き、バックエンドを飽和させることです。
チェック項目
- サーバーレス+Postgresへの直接接続 — 関数/エッジランタイム(Vercel/Lambda/Cloudflare/Netlify)が
プーラーを介さずに Postgres に直接接続している状態です。コールドスタートごとに接続が開かれ、同時実行数の
急増によって
max_connectionsを超過します。トランザクションモードのプーラー、またはサーバーレスドライバー (Neon/@neondatabase/serverless、Supabase pooler、PlanetScale HTTP)を推奨します。 - トランザクションモードのプーラーの誤用 — トランザクションプーリングエンドポイント(PgBouncer の
transactionモード、Supabase のポート 6543)を使いながら、そのモードで動作しなくなるセッション機能に依存している状態です。具体的には、サーバー側のプリペアドステートメント、SET/セッション GUC、LISTEN/NOTIFY、セッションアドバイザリーロックです。 - プールサイズ — アプリケーションプールの
max× インスタンス数がバックエンドのmax_connectionsを超えている、またはプールが小さすぎてリクエストを直列化している状態です。
サイズ設定の指針
- サーバー接続数の上限は、ピーク時の同時実行数ではなく、vCPU の小さな倍数程度です。
(cores*2) + effective_spindlesは、実用上負荷をかけられるバックエンド接続数のサーバー側の上限として 捉えてください。アプリケーションプールごとの目標値ではありません。 - クライアントプールのサイズは、ピーク時のリクエスト同時実行数ではなく、この上限に合わせてください。サーバーが実用上処理できる数を超えるバックエンド接続は、コンテキストスイッチやロック競合を増やすだけです。データベースではなく、プールでキューイングしてください。
max_connectionsより少ない余裕を確保してください。superuser_reserved_connectionsを空け、ほかのアプリケーションやレプリケーション用の枠も確保しておけば、プールが飽和したときでも管理者が接続できます。- PgBouncer のトランザクションモードでは、多数のクライアント接続を少数のバックエンド接続に多重化するため、クライアントプールをバックエンド接続数の上限より大幅に大きくできます。ただし、このモードではセッションレベルの機能(サーバー側のプリペアドステートメント、
SET/セッション GUC、LISTEN/NOTIFY、セッションスコープのアドバイザリーロック)が動作しなくなります。
スコア/軸
performance のみに影響します(リレーショナルデータベースの Pooling w10、NoSQL プロファイルの Conexión/Pooling)。
Tier-0(静的解析)
ランタイム(references/detection-signals.md に記載されているサーバーレスの指標)とクライアント/ドライバー
(pg、postgres、@neondatabase/serverless、@prisma/client、接続 URL のホスト/ポート)を検出します。サーバーレスからの直接接続、プリペアドステートメントの使用を伴うポート 6543/pgbouncer=true の URL、およびプール設定にフラグを付けます。バックエンドの max_connections と実際の接続数はランタイム情報のため、Tier-0 では needs_api です。
Tier-1(検証クエリ、Postgres)
SELECT current_setting('max_connections') AS max_conn,
count(*) AS open_conns,
count(*) FILTER (WHERE state = 'idle') AS idle
FROM pg_stat_activity;
メソッド connection_introspect。open_conns が max_conn に近づいている場合、接続枯渇の検出結果を
established として確認できます。サーバーレスからの直接接続とプーラーモードの検出結果は設定だけで確認できるため
(directional)、負荷時の影響については、Tier-2 がなければ needs_api です。
検出結果
schema/finding.schema.json に従って検出結果を出力します。例:
M15.app.serverless_direct_pg— プーラーを使わず、Postgres に直接接続するサーバーレス関数 (severity:4、warn、軸performance、confidencedirectional、fixable: proposed— プーラー/ サーバーレスドライバーに切り替えます)。M15.app.prepared_stmt_on_txn_pooler— トランザクションモードのプーラー経由でのサーバー側プリペアドステートメント (severity:3、warn、directional、fixable: proposed)。M15.app.pool_exceeds_max_connections— プール × インスタンス数がバックエンドの最大値を超過 (severity:3、warn、Tier-1 ではestablished/directional、fixable: proposed)。
各検出結果では、evidence.observed に接続設定/ドライバーのインポートを認証情報を伏せたうえでそのまま引用します。verification.reproduce には、$DATABASE_URL を参照する上記のカタログクエリを指定します。expected_impact は幅と信頼度を付けて示します(単独の % は不可)。
誠実さ
- 適切なプールを備えた長時間稼働サーバー(単一の Node/Rails プロセス)なら、直接接続でも問題ありません。サーバーレスでの直接接続に関する調査結果は、呼び出しごとにランタイムが起動する環境にのみ当てはまります。
- 観測できない接続数や障害発生確率を決して引用しないでください。影響度は段階でのみ示し、リソース枯渇に関する主張を
establishedとするには、Tier-1/2 が必要です。 - ここでの修正はいずれも設定/アーキテクチャに関するものであり、
proposed/advisoryとします。決してautoにはしません。