package main import ( "bytes" "encoding/json" "fmt" "io" "net/http" "time" ) // APIClient はHTTPリクエストを送信するクライアント type APIClient struct { BaseURL string HTTPClient *http.Client } // NewAPIClient は新しいAPIクライアントを作成 func NewAPIClient(baseURL string) *APIClient { return &APIClient{ BaseURL: baseURL, HTTPClient: &http.Client{ Timeout: 30 * time.Second, }, } } // Get はGETリクエストを送信 func (c *APIClient) Get(endpoint string) ([]byte, error) { url := c.BaseURL + endpoint resp, err := c.HTTPClient.Get(url) if err != nil { return nil, fmt.Errorf("GETリクエスト失敗: %w", err) } defer resp.Body.Close() body, err := io.ReadAll(resp.Body) if err != nil { return nil, fmt.Errorf("レスポンス読み込み失敗: %w", err) } if resp.StatusCode != http.StatusOK { return nil, fmt.Errorf("ステータスコード: %d, レスポンス: %s", resp.StatusCode, string(body)) } return body, nil } // Post はPOSTリクエストを送信 func (c *APIClient) Post(endpoint string, data interface{}) ([]byte, error) { url := c.BaseURL + endpoint jsonData, err := json.Marshal(data) if err != nil { return nil, fmt.Errorf("JSONエンコード失敗: %w", err) } resp, err := c.HTTPClient.Post(url, "application/json", bytes.NewBuffer(jsonData)) if err != nil { return nil, fmt.Errorf("POSTリクエスト失敗: %w", err) } defer resp.Body.Close() body, err := io.ReadAll(resp.Body) if err != nil { return nil, fmt.Errorf("レスポンス読み込み失敗: %w", err) } if resp.StatusCode != http.StatusOK && resp.StatusCode != http.StatusCreated { return nil, fmt.Errorf("ステータスコード: %d, レスポンス: %s", resp.StatusCode, string(body)) } return body, nil } // Put はPUTリクエストを送信 func (c *APIClient) Put(endpoint string, data interface{}) ([]byte, error) { url := c.BaseURL + endpoint jsonData, err := json.Marshal(data) if err != nil { return nil, fmt.Errorf("JSONエンコード失敗: %w", err) } req, err := http.NewRequest(http.MethodPut, url, bytes.NewBuffer(jsonData)) if err != nil { return nil, fmt.Errorf("リクエスト作成失敗: %w", err) } req.Header.Set("Content-Type", "application/json") resp, err := c.HTTPClient.Do(req) if err != nil { return nil, fmt.Errorf("PUTリクエスト失敗: %w", err) } defer resp.Body.Close() body, err := io.ReadAll(resp.Body) if err != nil { return nil, fmt.Errorf("レスポンス読み込み失敗: %w", err) } if resp.StatusCode != http.StatusOK { return nil, fmt.Errorf("ステータスコード: %d, レスポンス: %s", resp.StatusCode, string(body)) } return body, nil } // Delete はDELETEリクエストを送信 func (c *APIClient) Delete(endpoint string) ([]byte, error) { url := c.BaseURL + endpoint req, err := http.NewRequest(http.MethodDelete, url, nil) if err != nil { return nil, fmt.Errorf("リクエスト作成失敗: %w", err) } resp, err := c.HTTPClient.Do(req) if err != nil { return nil, fmt.Errorf("DELETEリクエスト失敗: %w", err) } defer resp.Body.Close() body, err := io.ReadAll(resp.Body) if err != nil { return nil, fmt.Errorf("レスポンス読み込み失敗: %w", err) } if resp.StatusCode != http.StatusOK && resp.StatusCode != http.StatusNoContent { return nil, fmt.Errorf("ステータスコード: %d, レスポンス: %s", resp.StatusCode, string(body)) } return body, nil } // 使用例 func main() { // APIクライアントの作成 client := NewAPIClient("https://jsonplaceholder.typicode.com") // GETリクエストの例 fmt.Println("=== GETリクエスト ===") getData, err := client.Get("/posts/1") if err != nil { fmt.Printf("エラー: %v\n", err) } else { fmt.Printf("レスポンス: %s\n\n", string(getData)) } // POSTリクエストの例 fmt.Println("=== POSTリクエスト ===") postData := map[string]interface{}{ "title": "新しい投稿", "body": "これはテスト投稿です", "userId": 1, } postResp, err := client.Post("/posts", postData) if err != nil { fmt.Printf("エラー: %v\n", err) } else { fmt.Printf("レスポンス: %s\n\n", string(postResp)) } // PUTリクエストの例 fmt.Println("=== PUTリクエスト ===") putData := map[string]interface{}{ "id": 1, "title": "更新された投稿", "body": "これは更新されたテスト投稿です", "userId": 1, } putResp, err := client.Put("/posts/1", putData) if err != nil { fmt.Printf("エラー: %v\n", err) } else { fmt.Printf("レスポンス: %s\n\n", string(putResp)) } // DELETEリクエストの例 fmt.Println("=== DELETEリクエスト ===") deleteResp, err := client.Delete("/posts/1") if err != nil { fmt.Printf("エラー: %v\n", err) } else { fmt.Printf("レスポンス: %s\n", string(deleteResp)) } }