🚀

conreq - curlライクに使える同時リクエスト確認ツールを作った

に公開

はじめに

APIの動作確認で「同じエンドポイントに同時にリクエストを送ったらどうなるか」を確認したいことがあります。例えば、冪等性の確認、レート制限の検証、同時実行時の挙動テストなどです。

そんな時に使えるツール「conreq」を作りました。名前は concurrent + request を組み合わせた造語で、「コンリク」または「コンレック」と読みます。

開発の背景

同時リクエストを送るツールを探すと、いくつかの選択肢があります。

既存ツールの課題

GNU parallel

# 複雑になりがち...
seq 3 | parallel -j 3 "curl -H 'X-Request-ID: {}' https://api.example.com"

xargs

# さらに複雑に...
printf '%s\n' 1 2 3 | xargs -P 3 -I {} curl -H "X-Request-ID: {}" https://api.example.com

Apache BenchやHey

# 負荷テストツールなので目的が違う
ab -n 3 -c 3 https://api.example.com/
hey -n 3 -c 3 https://api.example.com/

これらのツールは素晴らしいものですが、同時リクエストのレスポンス内容を確認したい場合には向いていません。特に:

  • GNU parallelやxargsはコマンドが複雑になりがち
  • Apache BenchやHeyは性能測定がメインで、個々のレスポンス内容の確認には不向き
  • Request IDの管理や同時実行数の制御が面倒

conreqの特徴

そこで、curlのように使えて、同時リクエストに特化したツールを作りました。

# curlライクなシンプルさ
conreq https://httpbin.org/get

# 3つの同時リクエスト
conreq https://httpbin.org/get -c 3

# POSTリクエストも簡単(2つの同時リクエスト)
conreq https://httpbin.org/post -c 2 -X POST -d '{"key": "value"}' -H "Content-Type: application/json"

主な機能

  • シンプルなインターフェース: curlライクな使い心地
  • 同時リクエスト管理: 最大5つまでの並行実行(負荷テストではないため)
  • Request IDの自動生成: UUID v4で自動生成、カスタム値も設定可能
  • 見やすい出力: 同時実行結果を整理して表示
  • JSON出力対応: jqなどでの後処理も可能
  • リアルタイム表示: --streamオプションで進行状況を確認

インストール

macOSならHomebrewで簡単にインストールできます:

brew install shiroemons/tap/conreq

使い方

基本的な使い方

同時実行数を変えてテスト

# 5つの同時リクエスト
conreq https://httpbin.org/delay/1 -c 5

# リアルタイムで進行状況を見る
conreq https://httpbin.org/delay/1 -c 5 --stream

冪等性の確認

# 同じRequest IDで3つのリクエストを送信
conreq https://httpbin.org/anything -c 3 --same-request-id

# カスタムRequest IDを指定
conreq https://httpbin.org/anything -c 3 --request-id "test-request-123"

レート制限の検証

# 100ms間隔で5つのリクエスト
conreq https://httpbin.org/anything -c 5 --delay 100ms

出力例

通常の出力では、各リクエストの結果が見やすく整理されます:

=== Request Summary ===
URL: https://httpbin.org/get
Method: GET
Concurrent: 3
Total Requests: 3

=== Results ===
[1] 2025-07-29 15:30:45.123456 | Status: 200 | Time: 145ms | X-Request-ID: 550e8400-e29b-41d4-a716-446655440001
{
  "args": {},
  "headers": {
    "X-Request-Id": "550e8400-e29b-41d4-a716-446655440001"
  },
  ...
}

[2] 2025-07-29 15:30:45.234567 | Status: 200 | Time: 132ms | X-Request-ID: 550e8400-e29b-41d4-a716-446655440002
...

=== Summary ===
Success: 3/3 (100.0%)

=== Status Code Breakdown ===
2xx (Success): 3
Average Response Time: 414ms

各行の出力フォーマットの意味:

[1] 2025-07-29 15:30:45.123456 | Status: 200 | Time: 145ms | X-Request-ID: 550e8400-e29b-41d4-a716-446655440001
 ↑           ↑                      ↑           ↑              ↑
 |           |                      |           |              |
 |           |                      |           |              └─ リクエストごとのユニークID
 |           |                      |           └─ レスポンスタイム(リクエスト開始から完了まで)
 |           |                      └─ HTTPステータスコード
 |           └─ リクエストを開始した時刻(マイクロ秒単位)
 └─ リクエスト番号(実行順)

{                              ← この行以降がレスポンスボディ
  ...                            実際のAPIレスポンスの内容が
}                                整形されて表示される

この形式により、どのリクエストがいつ開始し、どれくらい時間がかかったか、そして実際のレスポンス内容が一目で分かります。同時実行時の動作確認において重要な情報が整理されて表示されるのが特徴です。

なお、通常の出力はすべてのレスポンスが返ってからまとめて表示されます。リアルタイムで進行状況を確認したい場合は、--streamオプションを使用します:

# リアルタイムで進行状況を表示
conreq https://httpbin.org/delay/2 -c 2 --stream

--streamオプションを使うと、各リクエストの状態変化(待機中→実行中→完了)がリアルタイムで表示され、どのリクエストがいつ開始・完了したかを動的に確認できます。

JSON出力にすればjqで加工も簡単:

# ステータスコードの分布を確認
conreq https://httpbin.org/status/200,400,500 -c 5 --json | \
  jq '.summary.status_codes'

実際の活用シーン

1. API の冪等性確認

同じRequest IDで複数回実行して、結果が同じか確認:

conreq https://api.example.com/orders -X POST \
  -d '{"item": "coffee", "quantity": 1}' \
  -H "Content-Type: application/json" \
  -c 3 --same-request-id

2. 排他制御の動作確認

在庫管理APIなど、同時実行時の排他制御を確認:

conreq https://api.example.com/inventory/decrement \
  -X POST -d '{"product_id": "123", "quantity": 1}' \
  -H "Content-Type: application/json" \
  -c 5

3. エラーハンドリングの検証

特定のステータスコードでの挙動を確認:

# ランダムに200, 400, 500を返すエンドポイントでテスト
conreq "https://httpbin.org/status/200,400,500" -c 5 --json | \
  jq '.summary'

開発について

このツールはClaude Code(claude.ai/code)を使って開発しました。Go言語で実装し、以下のようなシンプルな構成になっています:

  • Cobraフレームワーク: CLIの基盤
  • 標準ライブラリ中心: 外部依存を最小限に
  • 並行処理: sync.WaitGroupでシンプルに実装

ソースコードはGitHubで公開しています:
https://github.com/shiroemons/conreq

まとめ

conreqは「同時リクエストの動作確認」という特定の用途に特化したツールです。curlのような使い心地で、複雑なシェルスクリプトを書かずに同時リクエストのテストができます。

APIの開発やテストで「同時に複数のリクエストが来たらどうなるか」を確認したい時に、ぜひ使ってみてください!

Discussion