コンテンツにスキップ

cURL コマンドを JavaScript fetch・Python requests に変換する方法|DevTools 連携

カテゴリ:HTTP・API 開発

API デバッグでよくある作業が「Chrome DevTools で確認した cURL コマンドをそのままコードに落とす」というものです。本記事では cURL のオプション体系、DevTools の「Copy as cURL」機能の仕組み、主要言語 (JavaScript fetch / axios / Python requests / PHP cURL / Go net/http) への変換パターンを解説します。末尾で紹介する cURL 変換ツール を使えば、これらをコピペ一発で変換できます。

なぜ cURL を起点にするのか

API を実装・デバッグする際、まず「curl で叩いて動くか確認してからコードに起こす」というワークフローが一般的です。理由は以下の通り:

  • 言語非依存: curl はほぼあらゆる環境で使える共通言語
  • DevTools から即コピー: Chrome / Firefox / Safari の Network タブでリクエストを右クリック → Copy as cURL で完全な再現コマンドを取得できる
  • 再現性の担保: バグ報告や Stack Overflow の質問で curl コマンドを添付すれば、環境差なく相手に同じリクエストを試してもらえる

cURL の主要オプション

最低限押さえるべき cURL オプションは以下です。

オプション用途
-X / --requestHTTP メソッド指定-X POST
-H / --headerリクエストヘッダ追加-H "Content-Type: application/json"
-d / --dataリクエストボディ-d '{"id":1}'
--data-rawエスケープ解釈をしない生データ--data-raw 'a=1&b=2'
-F / --formmultipart/form-data-F "file=@./a.png"
-u / --userBasic 認証-u user:pass
-b / --cookieCookie 送信-b "session=abc"
-L / --locationリダイレクト追跡
-k / --insecureSSL 証明書検証スキップ (開発時のみ)
--compressedgzip 受け入れ

DevTools の「Copy as cURL」で何が得られるか

Chrome / Firefox / Edge で Network タブを開き、任意のリクエストを右クリックすると Copy → Copy as cURL というメニューがあります。これをクリックすると以下が完全に再現されたコマンドがクリップボードにコピーされます。

  • HTTP メソッドとフル URL
  • 送信されたすべてのリクエストヘッダ (Authorization / User-Agent / Accept / Cookie など)
  • リクエストボディ (JSON / form-data / binary)
  • ANSI-C quoting ($'...') によるエスケープ

注意点として、Firefox の「Copy as cURL」は --data-raw を使うのに対し、Chrome は --data-binary を使うなど微妙な差があります。変換ツール側でどちらも認識できる実装になっている必要があります。

cURL オプション → fetch オプション 対応図 cURL fetch -X POST method: 'POST' -H "Key: Val" headers: { Key: 'Val' } -d "body" body: 'body' -F file=@a.txt body: FormData --cookie credentials: 'include' -u user:pass Authorization: Basic
図1: cURL の主要オプションと fetch オプションの対応関係

JavaScript fetch への変換

典型的な JSON POST の変換例を示します。

# cURL
curl -X POST https://api.example.com/users \
  -H 'Content-Type: application/json' \
  -H 'Authorization: Bearer YOUR_TOKEN' \
  -d '{"name":"Alice","email":"alice@example.com"}'
// JavaScript fetch
fetch('https://api.example.com/users', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'Authorization': 'Bearer YOUR_TOKEN',
  },
  body: JSON.stringify({ name: 'Alice', email: 'alice@example.com' }),
})
  .then(r => r.json())
  .then(console.log);

axios 版

import axios from 'axios';

axios.post(
  'https://api.example.com/users',
  { name: 'Alice', email: 'alice@example.com' },
  { headers: { 'Authorization': 'Bearer YOUR_TOKEN' } }
).then(r => console.log(r.data));

Python requests への変換

import requests

response = requests.post(
    'https://api.example.com/users',
    headers={
        'Content-Type': 'application/json',
        'Authorization': 'Bearer YOUR_TOKEN',
    },
    json={'name': 'Alice', 'email': 'alice@example.com'},
)
print(response.json())

ポイントは data= ではなく json= を使うこと。json= を指定すると requests が自動で JSON シリアライズし、Content-Type も自動設定されます。

PHP cURL への変換

<?php
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://api.example.com/users');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'POST');
curl_setopt($ch, CURLOPT_HTTPHEADER, [
    'Content-Type: application/json',
    'Authorization: Bearer YOUR_TOKEN',
]);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode([
    'name'  => 'Alice',
    'email' => 'alice@example.com',
]));

$response = curl_exec($ch);
curl_close($ch);
echo $response;

Go net/http への変換

package main

import (
    "bytes"
    "io"
    "net/http"
)

func main() {
    body := bytes.NewReader([]byte(`{"name":"Alice","email":"alice@example.com"}`))
    req, _ := http.NewRequest("POST", "https://api.example.com/users", body)
    req.Header.Set("Content-Type", "application/json")
    req.Header.Set("Authorization", "Bearer YOUR_TOKEN")

    res, _ := http.DefaultClient.Do(req)
    defer res.Body.Close()
    data, _ := io.ReadAll(res.Body)
    println(string(data))
}

注意: トークンのハードコードは厳禁

cURL コマンドをコードに落とすとき、Authorization ヘッダの値 (Bearer トークンや API Key) を そのままコードに書いてコミット しないように注意してください。

  • 本番トークンは環境変数 (process.env.API_TOKEN / os.environ['API_TOKEN'] / getenv()) 経由で読む
  • コミット前に git diff で秘密情報が混ざってないか確認
  • 既に commit してしまった場合はトークンを即時無効化 (rotation)、そして履歴を書き換える (git filter-repo)

DevLab の cURL 変換ツール

DevLab の cURL ⇄ fetch / axios 変換ツール は、上記すべての変換を ブラウザ完結 でワンクリック実行します。対応ターゲットは 13 種類:

  • JavaScript: fetch / axios / node-fetch / Node.js 標準 https
  • Python: requests / urllib
  • PHP: cURL / file_get_contents
  • Go: net/http
  • Rust: reqwest
  • wget / HTTPie / PowerShell Invoke-WebRequest

cURL 側のオプションは -X -H -d --data-raw --data-binary --data-urlencode -F -u -b -A -e -L -k -I と ANSI-C quoting $'...' に対応しており、Chrome と Firefox の「Copy as cURL」出力をそのまま受け付けます。

まとめ

cURL は言語非依存の HTTP 再現共通言語として極めて便利で、DevTools と組み合わせれば実運用中の API リクエストを即座に再現できます。本記事で示した変換パターンを押さえれば、どの言語からでも同じ挙動を再現できます。手作業で変換すると抜け漏れ (特に Content-Type や引用符のエスケープ) が発生しやすいので、ツール化された自動変換の活用を強くおすすめします。

📚 リファレンス