(ctx context.Context, params openAPICallArgs)
| 453 | type openAPICallArgs map[string]any |
| 454 | |
| 455 | func (h *openAPIHandler) callTool(ctx context.Context, params openAPICallArgs) (*tools.ToolCallResult, error) { |
| 456 | resolvedPath, queryParams, bodyParams := h.classifyParams(params) |
| 457 | |
| 458 | fullURL := h.baseURL + resolvedPath |
| 459 | if len(queryParams) > 0 { |
| 460 | fullURL += "?" + queryParams.Encode() |
| 461 | } |
| 462 | |
| 463 | var reqBody io.Reader = http.NoBody |
| 464 | if len(bodyParams) > 0 { |
| 465 | data, err := json.Marshal(bodyParams) |
| 466 | if err != nil { |
| 467 | return nil, fmt.Errorf("failed to marshal request body: %w", err) |
| 468 | } |
| 469 | reqBody = bytes.NewReader(data) |
| 470 | } |
| 471 | |
| 472 | req, err := http.NewRequestWithContext(ctx, h.method, fullURL, reqBody) |
| 473 | if err != nil { |
| 474 | return nil, fmt.Errorf("failed to create request: %w", err) |
| 475 | } |
| 476 | |
| 477 | if len(bodyParams) > 0 { |
| 478 | req.Header.Set("Content-Type", "application/json") |
| 479 | } |
| 480 | req.Header.Set("Accept", "application/json") |
| 481 | |
| 482 | headers := h.expander.ExpandMap(ctx, h.headers) |
| 483 | setHeaders(req, headers) |
| 484 | |
| 485 | resp, err := httpclient.NewSafeClient(h.timeout, h.allowPrivateIPs).Do(req) |
| 486 | if err != nil { |
| 487 | return nil, fmt.Errorf("request failed: %w", err) |
| 488 | } |
| 489 | defer resp.Body.Close() |
| 490 | |
| 491 | body, err := io.ReadAll(io.LimitReader(resp.Body, 1<<20)) // 1MB limit |
| 492 | if err != nil { |
| 493 | return nil, fmt.Errorf("failed to read response: %w", err) |
| 494 | } |
| 495 | |
| 496 | output := limitOutput(string(body)) |
| 497 | if len(body) >= 1<<20 { |
| 498 | output = "[WARNING: Response truncated at 1MB limit]\n" + output |
| 499 | } |
| 500 | |
| 501 | if resp.StatusCode >= 400 { |
| 502 | return tools.ResultError(fmt.Sprintf("HTTP %d: %s", resp.StatusCode, output)), nil |
| 503 | } |
| 504 | |
| 505 | return tools.ResultSuccess(output), nil |
| 506 | } |
| 507 | |
| 508 | // classifyParams splits tool call arguments into path replacements, query parameters, |
| 509 | // and body parameters based on the OpenAPI path template and "body_" prefix convention. |
nothing calls this directly
no test coverage detected