ShellスクリプトによるREST APIレスポンス検証の堅牢化と自動化

Tech

  • 語り口: プロフェッショナルかつ簡潔なエンジニア向け技術ドキュメント

  • 表記: 専門用語は正確に、説明は最小限で意図を伝える

  • 構成: 指示されたセクション順守、論理的フローの重視

  • 視覚的工夫: コードブロック、Mermaid、箇条書きの活用

  • 価値提供: 現場で即利用可能な「ベストプラクティス」を提示

本記事はGeminiの出力をプロンプト工学で整理した業務ドラフト(未検証)です。

ShellスクリプトによるREST APIレスポンス検証の堅牢化と自動化

【導入と前提】

APIヘルスチェックやデータ抽出を自動化し、異常検知時に確実な終了ステータスを返す堅牢な運用フローを構築します。

  • 実行環境: GNU/Linux (bash 4.0+), curl, jq 1.6+

  • 前提条件: APIエンドポイントへの疎通権限、およびjqのインストール

【処理フローと設計】

graph TD
A[Start] --> B["curl: API Request"]
B --> C{"HTTP Status 200?"}
C -- No --> D["Error Exit / Retry"]
C -- Yes --> E["jq: Parse & Validate JSON"]
E --> F{"Target Value Exists?"}
F -- No --> G["Validation Error"]
F -- Yes --> H["Process Success / Output"]
H --> I[End]

APIリクエスト、HTTPステータス確認、JSON構造バリデーションの3段階でフィルタリングを行い、後続処理に不正なデータを渡さない「Fail-fast」設計を採用します。

【実装:堅牢な自動化スクリプト】

1. 堅牢なバリデーションスクリプト (api_check.sh)

#!/usr/bin/env bash

# --- 安全設定 ---

set -euo pipefail # エラーで停止、未定義変数禁止、パイプ内のエラー捕捉
IFS=$'\n\t'       # スペースを含むファイル名の誤動作防止

# --- 定数 ---

readonly API_URL="https://api.example.com/v1/health"
readonly TEMP_FILE=$(mktemp /tmp/api_res.XXXXXX)

# --- クリーンアップ ---

trap 'rm -f "$TEMP_FILE"' EXIT # 終了時に必ず一時ファイルを削除

echo "Fetching API status..."

# --- 実行 ---


# -s: 進捗非表示, -S: エラー表示, -L: リダイレクト追従


# --retry: 通信失敗時の再試行, --fail: 4xx/5xxで終了コードを返す

if ! curl -sSL --retry 3 --retry-delay 2 --max-time 10 \
     -o "$TEMP_FILE" -w "%{http_code}" "$API_URL" | grep -q "200"; then
    echo "Error: API request failed or returned non-200 status." >&2
    exit 1
fi

# --- jqによる検証 ---


# -e: 結果がnullまたはfalseの場合に終了ステータス1を返す

if ! jq -e '.status == "UP" and .components.db.status == "OK"' "$TEMP_FILE" > /dev/null; then
    echo "Error: JSON validation failed. Unexpected API response structure." >&2
    cat "$TEMP_FILE" >&2
    exit 1
fi

echo "API Health Check Passed."

2. 定期実行設定 (systemd)

/etc/systemd/system/api-healthcheck.service

[Unit]
Description=API Health Check Automation

[Service]
Type=oneshot
ExecStart=/usr/local/bin/api_check.sh
User=nobody
Group=nogroup

[Install]
WantedBy=multi-user.target

/etc/systemd/system/api-healthcheck.timer

[Unit]
Description=Run API Health Check every 5 minutes

[Timer]
OnCalendar=*:0/5
Persistent=true

[Install]
WantedBy=timers.target

【検証と運用】

正常系の確認

スクリプトを直接実行し、終了コードを確認します。

./api_check.sh
echo $? # 0 であれば正常

異常系のログ確認

systemd経由で実行している場合、journalctl で詳細を確認可能です。

journalctl -u api-healthcheck.service -f

【トラブルシューティングと落とし穴】

  • 権限問題: mktemp を使用する際、実行ユーザーに /tmp への書込権限があるか確認してください。systemdで User=nobody を指定する場合、プライベートな一時ディレクトリ設定 (PrivateTmp=true) の活用を検討してください。

  • 環境変数の漏洩: APIトークン等の機密情報はスクリプト内にハードコードせず、systemdEnvironmentFile または環境変数から読み込むように設計してください。

  • jqのパースエラー: 不完全なJSON(ネットワーク断による途切れ等)を jq に渡すとエラーを吐いて停止します。set -e により即座にスクリプトが止まるため、ログに原因を残す工夫が必要です。

【まとめ】

運用の冪等性を維持するための3つのポイント:

  1. Fail-fastの実装: set -euo pipefailcurl --fail を組み合わせ、異常発生時に即座に停止させる。

  2. 一時リソースの自動破棄: trap コマンドで作業用ファイルを確実にクリーンアップし、ディスク圧迫を防ぐ。

  3. スキーマ検証の厳格化: jq -e を活用し、単なる通信成功だけでなくデータ構造が期待通りであることを保証する。

ライセンス:本記事のテキスト/コードは特記なき限り CC BY 4.0 です。引用の際は出典URL(本ページ)を明記してください。
利用ポリシー もご参照ください。

コメント

タイトルとURLをコピーしました