---
title: "Zbuduj integrację narzędzia (API)"
description: "Pozwól swojemu agentowi wywoływać interfejsy API w trakcie rozmowy — przeszukiwać bazę danych, tworzyć zgłoszenia, sprawdzać zamówienia."
---

**integracja narzędzia** to wielokrotnego użytku punkt końcowy HTTP, który agent może
wywołać podczas rozmowy. Przekazujesz ThunderPhone opis narzędzia w schemacie JSON
oraz adres URL punktu końcowego; agent decyduje, kiedy je wywołać, na podstawie
rozmowy, a ThunderPhone wysyła wychodzące żądanie HTTP ze swoich serwerów i zwraca
odpowiedź agentowi.

<Note>
  Panel obsługuje większość potrzeb związanych z narzędziami bez tego API: **Połączenia
  → Aplikacje** łączy Slack, HubSpot, Salesforce, Kalendarz Google,
  Arkusze Google i Cal.com za pomocą kilku kliknięć OAuth; **Połączenia →
  API** przekształca dowolne API HTTP w działanie agenta (wklej polecenie cURL,
  a kreator AI przygotuje narzędzie z wbudowaną funkcją Testuj żądanie); oraz
  **Połączenia → MCP** dodaje serwery MCP. Zobacz
  [Połączenia](/pl/guides/concepts). Ten przewodnik opisuje bazowe
  API stojące za sekcją API.
</Note>

Ten przewodnik przedstawia kompleksowe tworzenie narzędzia do sprawdzania pogody.

## Elementy narzędzia

Dwa elementy:

1. **Schemat** — definicja funkcji w stylu OpenAI
   (`{type: "function", function: {name, description, parameters}}`),
   która informuje LLM, co robi narzędzie i jakie argumenty przyjmuje.
2. **Punkt końcowy** — adres URL, który serwery ThunderPhone wywołują, gdy
   LLM zdecyduje się użyć narzędzia. Żądanie jest żądaniem JSON POST z
   argumentami wybranymi przez LLM w treści.

## 1. Wybierz edytor

<CardGroup cols={2}>
  <Card title="Panel" icon="window-maximize">
    Otwórz **Połączenia → API**, utwórz lub edytuj połączenie API,
    przełącz edytor parametrów na **JSON** i dodaj tam format.
  </Card>
  <Card title="API integracji" icon="plug">
    Utwórz specyfikację za pomocą `POST /v1/integrations` lub zaktualizuj ją za pomocą
    `PATCH /v1/integrations/{id}`.
  </Card>
</CardGroup>

Obie ścieżki tworzą zapisaną integrację. Po zapisaniu przypisz tę integrację do
agenta. API agentów nie ma zapisywalnego wbudowanego pola `tools`.
Ten przewodnik korzysta ze ścieżki API integracji.

## 2. Utwórz integrację

```bash
curl -X POST https://api.thunderphone.com/v1/integrations \
  -H "Authorization: Bearer sk_live_YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "display_name": "Weather API",
    "spec": {
      "type": "function",
      "function": {
        "name": "get_weather",
        "description": "Return the current weather for a zip code.",
        "parameters": {
          "type": "object",
          "properties": {
            "zip": { "type": "string", "description": "5-digit US ZIP code" }
          },
          "required": ["zip"]
        }
      }
    },
    "endpoint_url":    "https://api.example.com/weather",
    "endpoint_method": "GET",
    "headers": [
      { "key": "X-Api-Key", "value": "your-provider-key" }
    ]
  }'
```

Zapisz zwrócone `id` (UUID). Wartości nagłówków są tylko do zapisu: odpowiedzi
zawierają wyłącznie nazwy nagłówków, a późniejszy `PATCH` może wysłać nagłówek bez
`value`, aby zachować zapisaną wartość.

<Tip>
  Poświęć szczególną uwagę polu `description` narzędzia i każdego
  parametru. LLM używa tych ciągów w czasie działania, aby zdecydować,
  czy i jak wywołać narzędzie. Nieprecyzyjne opisy → nieprecyzyjne wywołania narzędzi.
</Tip>

### Zadeklaruj `format: "email"` dla parametrów adresu e-mail

Parametr, który otrzymuje adres e-mail, powinien to określać w swoim
schemacie:

```json
"email": { "type": "string", "format": "email", "description": "The caller's email address" }
```

`format` to więcej niż wskazówka. W przypadku rozpoznanego schematu e-mail,
zanim zostanie wywołany punkt końcowy, ThunderPhone usuwa spacje z początku i końca wartości,
zamienia domenę na małe litery, przekształca samodzielne angielskie słowa `at`, `dot`,
`underscore`, `dash` i `hyphen` w odpowiadające im znaki oraz usuwa białe znaki
bezpośrednio wokół `@`, `.`, `_` i `-`. Słowa mają to samo znaczenie,
niezależnie od tego, czy transkrypcja zawiera już dosłowny znak `@`:
`"john dot smith at gmail dot com"` staje się
`john.smith@gmail.com`.

Wszelkie inne wewnętrzne białe znaki są odrzucane, zamiast być po cichu łączone.
Wypowiadane słowa separatorów są obsługiwane wyłącznie w języku angielskim; nieangielskie
lub nierozpoznane formy ze spacjami są bezpiecznie odrzucane. Prawidłowe umiędzynarodowione
domeny i części lokalne SMTPUTF8 są akceptowane. Dane wejściowe Punycode pozostają Punycode,
a dane wejściowe domen Unicode pozostają Unicode po normalizacji parsera, więc API otrzymuje
konwencjonalną reprezentację podaną przez rozmówcę. Jeśli końcowa wartość jest nieprawidłowa,
narzędzie **nie jest wywoływane**. Agent otrzymuje
`invalid_email_argument`, informujące go,
aby potwierdził pisownię z rozmówcą i ponownie wysłał dosłowny adres.

Pominięty opcjonalny adres e-mail pozostaje bez zmian. `null`, pusty ciąg lub ciąg
zawierający wyłącznie białe znaki również pozostają bez zmian, gdy właściwość jest opcjonalna
lub dopuszcza wartość null; te same wartości są odrzucane w przypadku wymaganego adresu e-mail
niedopuszczającego wartości null.

Lokalne odwołania do schematu, takie jak `#/$defs/email` i
`#/definitions/email`, a także `anyOf`, `oneOf` i `allOf`, są sprawdzane
z limitami cykli i głębokości. Nielokalne lub nierozwiązywalne `$ref` stanowi znane ograniczenie
egzekwowania i jest przekazywane bez zmian, podobnie jak wywołanie, którego migawka narzędzia
nie zawiera użytecznego schematu. Zachowaj lokalność schematów e-mail, gdy potrzebujesz zastosowania tej kontroli.

Parametry bez egzekwowanego formatu e-mail są przekazywane dokładnie w postaci wygenerowanej przez model.

Obsługiwane formaty to `date-time`, `time`, `date`, `duration`,
`email`, `hostname`, `ipv4`, `ipv6` i `uuid`; obecnie tylko `email` jest
normalizowany i egzekwowany.

## 3. Przetestuj punkt końcowy w piaskownicy

Zanim połączysz integrację z agentem, wyślij podpisane żądanie
z serwerów ThunderPhone, aby potwierdzić łączność:

```bash
curl -X POST https://api.thunderphone.com/v1/integrations/test-request \
  -H "Authorization: Bearer sk_live_YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "url":    "https://api.example.com/weather?zip=94110",
    "method": "GET",
    "headers": { "X-Api-Key": "your-provider-key" }
  }'
```

```json Response
{
  "ok": true,
  "status": 200,
  "elapsed_ms": 187,
  "response_headers": { "content-type": "application/json" },
  "response_preview": "{\"temperature_f\": 64, ...}"
}
```

Ten test wzmacnia również zabezpieczenia ThunderPhone przed SSRF — żądania do
localhost lub prywatnych zakresów IP zwracają `400 code=url_not_allowed`.

## 4. Połącz integrację z agentem

Dołącz za pomocą `integration_ids` podczas tworzenia lub aktualizowania agenta:

```bash
curl -X PATCH https://api.thunderphone.com/v1/agents/12 \
  -H "Authorization: Bearer sk_live_YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "integration_ids": ["f9b5a1a4-..."]
  }'
```

Z jednym agentem możesz połączyć wiele integracji. Prompt agenta może
odwoływać się do nich po nazwie — „użyj `get_weather`, gdy rozmówca pyta
o warunki pogodowe” — albo może wykrywać je niejawnie na podstawie
opisów schematu.

## 5. Zaimplementuj punkt końcowy

Gdy agent wywołuje narzędzie, ThunderPhone wysyła podpisane żądanie POST do
Twojego `endpoint_url`:

```
POST /weather HTTP/1.1
Host: api.example.com
X-Api-Key: your-provider-key
X-ThunderPhone-Signature-V2: t=<unix seconds>,v1=<HMAC-SHA256 hex>
X-ThunderPhone-Signature: <HMAC-SHA256 hex>
X-ThunderPhone-Call-ID: 987654321
Content-Type: application/json

{"zip": "94110"}
```

Twój serwer odpowiada JSON-em, który jest przekazywany z powrotem do LLM:

```json
{"temperature_f": 64, "condition": "Partly cloudy", "wind_mph": 8}
```

LLM przetwarza tę odpowiedź i przekazuje rozmówcy podsumowanie w naturalnym języku.

<Warning>
  Podpis jest obliczany na podstawie surowego treści żądania przy użyciu tego samego
  `secret` co punkt końcowy webhooka. **Zweryfikuj go** — punkty końcowe narzędzi
  są dostępne z internetu i narażone na takie same zagrożenia związane z podszywaniem się jak
  webhooki. Zobacz
  [Weryfikowanie podpisów webhooków](/pl/guides/verify-webhook-signatures).
</Warning>

## 6. Przetestuj cały przepływ

Uruchom [sesję mikrofonową](/api-reference/mic-sessions) z agentem
i zadaj pytanie obsługiwane przez Twoje narzędzie („Jaka jest pogoda w
94110?”). Transkrypcja połączenia pokazuje pełny cykl:

```json
{
  "call_id": 987654321,
  "transcripts": [
    { "role": "user",
      "content": "What's the weather in 94110?" },
    { "role": "tool_call",
      "content": "{\"tool_call\": \"get_weather\", \"arguments\": {\"zip\": \"94110\"}}" },
    { "role": "tool_response",
      "content": "{\"tool_name\": \"get_weather\", \"response\": {\"temperature_f\": 64, \"condition\": \"Partly cloudy\"}}" },
    { "role": "agent",
      "content": "It's 64 degrees and partly cloudy." }
  ]
}
```

Możesz pobrać ją za pomocą
[`GET /v1/calls/{call_id}/transcript`](/api-reference/calls#get-transcript);
surowy strumień zdarzeń (z czasem dla każdego wpisu i przesunięciami audio) znajduje się pod
[`GET /v1/calls/{call_id}/history`](/api-reference/calls#get-history).

W widokach list połączeń i analiz ThunderPhone raportuje teraz połączenia testowe oddzielnie od rzeczywistego ruchu. Testy i symulacje Browser Talk mogą ponownie używać prawdziwego numeru telefonu i mogą wyglądać jak połączenia przychodzące, ale nie są uwzględniane w łącznej liczbie połączeń produkcyjnych, ocenach ani wskaźnikach problemów.

## Typowe pułapki

<AccordionGroup>
  <Accordion title="Agent nigdy nie wywołuje narzędzia">
    LLM podejmuje decyzję na podstawie opisu narzędzia. Jeśli pytanie rozmówcy
    nie odpowiada opisowi, model nie wywoła narzędzia. Doprecyzuj opis
    (dodaj popularne synonimy i sformułowania) albo wspomnij o nim wyraźnie
    w prompcie agenta („Gdy rozmówca pyta o pogodę, użyj `get_weather`.”).
  </Accordion>

  <Accordion title="Narzędzie zwraca zbyt dużo danych">
    Odpowiedzi większe niż 6 kB są obcinane w podglądzie transkrypcji. Zwracaj
    tylko pola potrzebne LLM — nie cały rekord.
  </Accordion>

  <Accordion title="Limity czasu">
    Punkty końcowe narzędzi mają domyślny limit czasu 10 sekund. Jeśli potrzebujesz więcej czasu,
    obsłuż to asynchronicznie: zwróć `{"status": "pending", "request_id": "..."}`
    i udostępnij wynik przez osobne wywołanie narzędzia.
  </Accordion>

  <Accordion title="Wersjonowanie">
    Każde żądanie `PATCH` integracji tworzy nową rewizję. Sprawdź
    [`GET /v1/integrations/{id}/versions`](/api-reference/integrations#version-history),
    aby zobaczyć, kto co zmienił. Jeśli uszkodzisz schemat narzędzia, możesz
    ręcznie przywrócić wcześniejszą wersję, wykonując PATCH ze starszym zrzutem.
  </Accordion>
</AccordionGroup>

---

## Kolejne kroki

<CardGroup cols={2}>
  <Card title="Dokumentacja integracji" icon="plug" href="/api-reference/integrations">
    CRUD, transfer, historia wersji.
  </Card>
  <Card title="Specyfikacja narzędzi funkcji" icon="screwdriver-wrench" href="/pl/tools/overview">
    Pełna gramatyka schematu JSON i umowa dotycząca podpisanego punktu końcowego.
  </Card>
  <Card title="Weryfikowanie podpisów" icon="shield-check" href="/pl/guides/verify-webhook-signatures">
    Zastosuj wzorzec podpisu webhooka do punktów końcowych narzędzi.
  </Card>
  <Card title="API transkrypcji i historii" icon="phone" href="/api-reference/calls">
    Sprawdź pełny cykl wywołania narzędzia.
  </Card>
</CardGroup>
