Skip to content

リクエストとレスポンス

リクエストの送信

パッケージ関数

クライアントを作成せず、直接リクエストを送信します:

go
result, err := httpc.Get("https://api.example.com/data")
if err != nil {
    log.Fatal(err)
}

fmt.Println(result.StatusCode())
fmt.Println(result.Body())

対応 HTTP メソッド:GetPostPutPatchDeleteHeadOptions

クライアントインスタンス

go
client, err := httpc.New()
if err != nil {
    log.Fatal(err)
}
defer client.Close()

result, err := client.Get("https://api.example.com/data")

汎用リクエストメソッド

go
ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)
defer cancel()

result, err := httpc.Request(ctx, "GET", "https://api.example.com/data")

リクエストオプション

リクエストヘッダー

go
result, err := client.Get(url,
    httpc.WithHeader("Authorization", "Bearer token"),
    httpc.WithHeader("X-Custom", "value"),
    httpc.WithHeaderMap(map[string]string{
        "Accept":        "application/json",
        "X-Request-ID":  "123",
    }),
    httpc.WithUserAgent("my-app/1.0"),
)

リクエストボディ

go
// JSON
result, err := client.Post(url, httpc.WithJSON(map[string]any{
    "name": "test",
}))

// XML
result, err := client.Post(url, httpc.WithXML(data))

// フォーム
result, err := client.Post(url, httpc.WithForm(map[string]string{
    "username": "admin",
    "password": "secret",
}))

// バイナリ(デフォルト application/octet-stream)
result, err := client.Post(url, httpc.WithBinary(data))
// タイプ指定
result, err := client.Post(url, httpc.WithBinary(data, "image/png"))

// タイプ自動検出
result, err := client.Post(url, httpc.WithBody(data))
// string → text/plain; charset=utf-8, []byte → application/octet-stream,
// map[string]string → application/x-www-form-urlencoded,
// *FormData → multipart/form-data, io.Reader → passed through,
// その他 → application/json
// 明示的指定も可能:httpc.WithBody(data, httpc.BodyJSON)

クエリパラメータ

go
result, err := client.Get(url,
    httpc.WithQuery("page", 1),
    httpc.WithQuery("limit", 10),
)

// または Map を使用
result, err := client.Get(url,
    httpc.WithQueryMap(map[string]any{
        "page":  1,
        "limit": 10,
    }),
)

認証

go
// Bearer Token
result, err := client.Get(url, httpc.WithBearerToken("my-token"))

// Basic Auth
result, err := client.Get(url, httpc.WithBasicAuth("user", "pass"))
go
result, err := client.Get(url,
    httpc.WithCookie(http.Cookie{Name: "session", Value: "abc"}),
    httpc.WithCookieMap(map[string]string{"session": "abc", "lang": "ja"}),
    httpc.WithCookieString("session=abc; lang=ja"),
)

リクエスト制御

go
// タイムアウト
result, err := client.Get(url, httpc.WithTimeout(10*time.Second))

// リトライ
result, err := client.Get(url, httpc.WithMaxRetries(5))

// リダイレクト
result, err := client.Get(url,
    httpc.WithFollowRedirects(false),    // リダイレクトを禁止
)

WithMaxRedirects(0) は無効化ではない

WithMaxRedirects(0) はリダイレクトを無効にしません。エンジンは 0 を「未設定」とみなし、デフォルト値の 10 にフォールバックします。リダイレクトの追跡を完全に無効にするには、WithFollowRedirects(false) を使用してください。

コールバック

go
result, err := client.Get(url,
    httpc.WithOnRequest(func(req httpc.RequestMutator) error {
        log.Printf("リクエスト送信: %s %s", req.Method(), req.URL())
        return nil
    }),
    httpc.WithOnResponse(func(resp httpc.ResponseMutator) error {
        log.Printf("レスポンス受信:%d", resp.StatusCode())
        return nil
    }),
)

レスポンス処理

go
result, err := client.Get("https://api.example.com/users/1")
if err != nil {
    log.Fatal(err)
}

// ステータス確認
result.StatusCode()     // 200
result.IsSuccess()      // true (2xx)
result.IsRedirect()     // false (3xx)
result.IsClientError()  // false (4xx)
result.IsServerError()  // false (5xx)

// レスポンスの読み取り
result.Body()           // 文字列
result.RawBody()        // []byte
result.Proto()          // "HTTP/1.1"

// JSON 解析
var user User
if err := result.Unmarshal(&user); err != nil {
    log.Fatal(err)
}

// Cookie
cookie := result.GetCookie("session")
if cookie != nil {
    fmt.Println(cookie.Value)
}

// リクエストメタデータ
fmt.Println(result.Meta.Duration)       // リクエスト所要時間
fmt.Println(result.Meta.Attempts)       // リトライ回数
fmt.Println(result.Meta.RedirectCount)  // リダイレクト回数

コンテキスト制御

go
// タイムアウト制御
ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)
defer cancel()
result, err := httpc.Request(ctx, "GET", url)

// キャンセル制御
ctx, cancel := context.WithCancel(context.Background())
go func() {
    time.Sleep(5 * time.Second)
    cancel() // 5 秒後にキャンセル
}()
result, err := httpc.Request(ctx, "GET", url)

ストリーミングレスポンス

WithStreamBody(true) は内部機構であり、ファイルダウンロード時に完全なレスポンスボディがメモリにキャッシュされるのを防ぎます。有効にすると、レスポンスボディは Result に読み込まれません(Body()RawBody() は空の値を返します)。

WARNING

WithStreamBody(true) はファイルダウンロード API が内部的に使用します。レスポンス内容をストリーミングで取得する必要がある場合は、ファイルダウンロード API を使用してください。

大きなファイルをダウンロードする場合は、ダウンロード API を使用してください:

go
cfg := httpc.DefaultDownloadConfig()
cfg.FilePath = "/path/to/file"
result, err := client.Download(context.Background(), url, cfg)

レスポンスの解凍

HTTPC は gzip、deflate などのコンテンツエンコーディングの解凍を自動的に処理します。セキュリティ設定で解凍後のサイズを制限し、解凍爆弾攻撃を防止できます:

go
cfg := httpc.DefaultConfig()
cfg.Security.MaxResponseBodySize = 10 * 1024 * 1024      // レスポンスボディ上限:ストリーミングダウンロード時に強制。非ストリーミング時は解凍後上限のフォールバック
cfg.Security.MaxDecompressedBodySize = 100 * 1024 * 1024  // 解凍後最大 100MB
設定項目デフォルト説明
MaxResponseBodySize10MBストリーミングダウンロード時のレスポンスボディ上限。非ストリーミング時は解凍後上限のフォールバック
MaxDecompressedBodySize100MB解凍後のレスポンスボディのサイズ上限

圧縮されたレスポンスボディのバイト数には、別途 100MB のハードキャップ(maxCompressedSize、設定不可)があり、解凍爆弾への防御として機能し、MaxResponseBodySize とは独立しています。

制限を超えると "exceeds limit" を含むエラーが返されます。ClientError タイプで処理できます。ErrResponseBodyTooLargeResult.Unmarshal() で 50MB の JSON 解析サイズ制限を超えるレスポンスボディを解析する際に返されます(MaxResponseBodySize とは独立)。

次のステップ