本ドキュメントでは、公式の node-postgres (brianc/node-postgres) ライブラリのテスト手法と、node_pg Gleam ラッパーの実装を比較・分析します。
- Vitest (~3.0.9): 主要なテストフレームワークとして採用。
- Make: テストのオーケストレーションに使用(
make test-allを介して実行)。 - Cloudflare Workers Pool: プラットフォーム固有のテスト用 (@cloudflare/vitest-pool-workers)。
- gleeunit: Gleam のユニットテスト用(同期実行のみ)。
- Bun test: JavaScript 統合テスト用(非同期サポートのため)。
- Node-postgres は単一のテストランナー (Vitest) を設定変更のみでユニット/統合テストの両方に使用しています。
- Node_pg は Gleam の同期制限により、2つのフレームワークに分かれています。
- Node-postgres は Make ターゲットを使用し、きめ細かなテスト制御を実現しています。
ディレクトリ構造:
packages/pg/test/
├── unit/
│ └── client/ (16個のテストファイル)
│ ├── configuration-tests.js
│ ├── simple-query-tests.js
│ ├── prepared-statement-tests.js
│ ├── error-handling-tests.js
│ ├── 認証テスト (md5, sasl-scram, cleartext)
│ └── test-helper.js
├── integration/
│ ├── client/ (40個のテストファイル)
│ │ ├── simple-query-tests.js
│ │ ├── prepared-statement-tests.js
│ │ ├── connection-tests.js
│ │ ├── transaction-tests.js
│ │ ├── 型パーステスト (array, json, numeric)
│ │ ├── error-handling-tests.js
│ │ └── test-helper.js
│ ├── connection-pool/
│ └── gh-issues/ (GitHub の問題再現テスト)
├── native/
├── tls/
├── cloudflare/
└── test-helper.js (ルートのテストユーティリティ)
テストの哲学:
- ユニットテスト: PostgreSQL サーバの起動を必要としません。Client 階層下の Connection レイヤーをスタブ化します。
- 統合テスト: 実際の PostgreSQL への接続を必要とします。
- テストファイルには慣習的に
-tests.jsという接尾辞を付けます。 - GitHub の Issue ごとに回帰テスト用のディレクトリを分けています。
test/
├── client_test.gleam (ユニット: Config 生成のみ)
├── simple-integration.test.mjs (2つの基本的な接続テスト)
└── integration.test.mjs (複数の describe ブロック: 27テスト)
主な違い:
- 規模: Node-postgres は 56以上のファイルがあるのに対し、node_pg は 3ファイルのみです。
- 粒度: Node-postgres は関心事(プリペアドステートメント、トランザクション等)ごとにファイルを分割しています。
- 回帰テスト: Node-postgres にはバグ修正用の専用ディレクトリ
gh-issues/があります。 - ユニットテストの網羅性: Node-postgres は DB なしでクライアント内部を広範囲にテストしていますが、node_pg は Config 生成のみです。
イベント駆動型テスト:
// イベント発行のカスタムアサーション
assert.emits(query, 'end', function() {
// イベント発生後のアサーション
});
// クリーンアップ用の drain パターン
client.on('drain', client.end.bind(client));Promise ベース (モダン):
// 統合テストより
const result = await client.query('SELECT 1');
assert.equal(result.rows[0], 1);カスタムタイムアウト・ラッパー:
// test-helper.js より
function expect(callback, timeout) {
timeout = timeout || parseInt(process.env.TEST_TIMEOUT || 5000);
// コールバックをタイムアウト保護でラップ
}// Bun test での async/await
test('should execute SELECT query', async () => {
const client = new PgClient(validConfig);
await client.connect();
const result = await client.query('SELECT 1 AS number');
expect(result.rows[0].number).toBe(1);
await client.end();
});主な違い:
- Node-postgres はイベント駆動と Promise ベースの両方をサポートしています。
- Node-postgres は環境変数
TEST_TIMEOUTで設定可能なカスタムタイムアウト処理を備えています。 - Node_pg はモダンな async/await のみを使用しており、クリーンですが柔軟性は低めです。
DB スキーマのセットアップ:
- スクリプト:
script/create-test-tables.js - 実行: 統合テストの前に
make test-connectionを実行。 - 内容: 26個のシードレコード(名前 Aaron から Zanzabar、年齢 10-260)を含む
personテーブルを作成。
テストごとのクリーンアップ:
// Wiki で推奨されているパターン
tearDown: function() {
pg.connect(connectionString, function(err, client) {
client.end()
});
}テストヘルパー・ユーティリティ:
test-helper.js の機能:
assert.emits: イベント発行の検証。assert.equalBuffers: バッファ比較。setTimezoneOffset: タイムゾーンのテスト用。rejection(promise): 拒否された Promise からエラーを取得。
自動化されたセットアップなし:
- 手動での DB 準備が必要(localhost:5432、'app' データベース)。
- シードデータなし、バージョンチェックなし。
一時テーブル (TEMP TABLE) の活用:
// テストデータをインラインで作成
await client.query('CREATE TEMP TABLE test_table (id INT, name TEXT)');
// セッション終了時に自動で削除される主な違い:
- Node-postgres は専用のセットアップスクリプトがありますが、node_pg は手動設定に依存しています。
- Node-postgres には豊富なヘルパーがありますが、node_pg は標準の Bun アサーションのみです。
- Node_pg が一時テーブル (TEMP TABLE) を使用している点は、node-postgres でも見られる良いプラクティスです。
- 複数 DB サポート: CLI や環境変数 (
PGUSER,PGHOST等) でパラメータを変更可能。 - CI/CD 統合: GitHub Actions で PostgreSQL サービスを起動し、ヘルスチェック (
pg_isready) を実施。 - 認証テスト: 標準パスワード、SCRAM-SHA-256、SSL/TLS 接続など、多様な認証方法をテスト。
- 単一 DB:
localhost:5432/appにハードコードされています。 - CI/CD なし: 現時点では自動化されたプロビジョニングはありません。
- マトリックス・テスト: Node.js の 6つのバージョン (16〜25) で並列テスト。
- 順次実行: DB 競合を避けるため、パッケージごとに順次テストを実行。
- 品質ゲート: テスト実行前に Lint とビルド(TypeScript コンパイル)を必須化。
| 項目 | Node-Postgres | Node_pg Gleam ラッパー | ギャップ |
|---|---|---|---|
| フレームワーク | Vitest | gleeunit + Bun test | レイヤーごとにツールが分離 |
| テストファイル数 | 56+ | 3 | 網羅率に大きな差 |
| ユニットテスト | 内部、認証、パース等広範囲 | Config 生成のみ | 最小限のテスト |
| 組織化 | 機能ごとにファイル分割 | 巨大な 1ファイル | メンテナンス性に課題 |
| セットアップ | スクリプトによる自動化 | 手動 | 自動化が必要 |
| CI/CD | 完備 (6つの Node バージョン) | なし | 自動化なし |
GitHub Actions (.github/workflows/test.yml) を作成し、PostgreSQL サービスを定義して、プッシュごとに自動テストを実行します。
巨大な統合テストファイルを、connection.test.mjs, query.test.mjs, transactions.test.mjs のように機能別に分割します。
共通の接続設定や、クライアントの自動終了を保証する withClient などのラッパー関数を整備します。
make test-all など、1つのコマンドでユニットテストと統合テストの両方を実行できるようにします。
クエリのエスケープ処理や、Gleam と JavaScript 間の型変換ロジックのテストを追加します。
PostgreSQL のバージョンを検知し、古いバージョンでは実行できない機能を条件付きでスキップできるようにします。
- ✅ モダンな async/await を採用しており、コードが読みやすい。
- ✅ データの独立性のために TEMP TABLE を活用している。
- ❌ CI/CD 自動化の欠如(最も優先度が高い)。
- ❌ テストの組織化(巨大なファイルに集約されている)。
- ❌ 手動のデータベースセットアップへの依存。
- 第1週: GitHub Actions による CI/CD の導入。
- 第2週: テストヘルパーの作成と構造の再編。
- 第3週: ユニットテストの範囲拡大。
- 第4週: 回帰テスト用の仕組み作り。
ドキュメント バージョン: 1.0 日付: 2026-01-14