> ## Documentation Index
> Fetch the complete documentation index at: https://docs.niadra.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Início rápido

> Da chave de API ao primeiro contexto entregue, em Python, TypeScript ou cURL.

Este início rápido leva um agente do zero ao primeiro contexto entregue: uma chave, o SDK, uma conversa registrada, o contexto lido de volta e uma busca no histórico. Leva uns dez minutos num espaço de sandbox, que nunca se mistura com os dados de produção.

## 1. Pegue uma chave

Todo agente, fornecedor ou sistema que fala com a Niadra é uma **fonte**, com chaves, escopos e finalidade próprios. Crie uma fonte para o seu agente no Console, ou pela [API de controle](/api/control/sources-create), e crie uma chave com os escopos `track`, `context` e `search`.

Uma chave tem este formato:

```text theme={null}
nia_sk_test_us-east-1_acme-sandbox_k7Q2mX9a_<secret>
```

Chaves `test` chegam aos espaços de sandbox; chaves `live`, aos de produção. A região e o espaço dentro da chave dizem ao SDK para onde ir: `https://acme-sandbox.us-east-1.api.niadra.com`. O segredo aparece uma vez só; guarde no seu cofre de segredos e entregue ao agente como variável de ambiente.

```sh theme={null}
export NIADRA_API_KEY="nia_sk_test_us-east-1_acme-sandbox_k7Q2mX9a_..."
```

## 2. Instale o SDK

<CodeGroup>
  ```sh Python theme={null}
  pip install niadra
  ```

  ```sh TypeScript theme={null}
  npm install @niadra/sdk
  ```
</CodeGroup>

Os dois SDKs são de código aberto, sob Apache 2.0. Com HTTP puro não há nada para instalar: toda chamada abaixo tem também a versão em cURL.

## 3. Registre uma conversa

Uma sessão de conversa fixa o contexto, captura os turnos e envia `conversation.ended` ao fechar. As escritas vão para uma fila local e saem em lote, então nunca deixam o agente mais lento.

<CodeGroup>
  ```python Python theme={null}
  from niadra import Niadra, phone

  niadra = Niadra(channel="whatsapp")
  marina = phone("+14155550123")

  with niadra.conversation("wa-8812", subject=marina) as conv:
      conv.customer("The technician never showed up. I am calling you.")
      conv.agent("I am sorry, Marina. I am checking the visit now.")
  # leaving the block sends conversation.ended

  niadra.flush()
  ```

  ```typescript TypeScript theme={null}
  import { Niadra, handles } from "@niadra/sdk";

  const niadra = new Niadra();
  const marina = handles.phone("+14155550123");

  const conv = niadra.conversation({ subject: marina, channel: "whatsapp", conversation_id: "wa-8812" });
  conv.customer("The technician never showed up. I am calling you.");
  conv.agent("I am sorry, Marina. I am checking the visit now.");
  await conv.end(); // sends conversation.ended

  await niadra.flush();
  ```

  ```bash cURL theme={null}
  curl -X POST "https://acme-sandbox.us-east-1.api.niadra.com/v1/batch" \
    -H "Authorization: Bearer $NIADRA_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "items": [
      {"type": "event", "idempotency_key": "wamid.001", "channel": "whatsapp", "conversation_id": "wa-8812",
       "handles": [{"type": "phone_e164", "value": "+14155550123"}], "speaker": {"role": "customer"},
       "content": {"text": "The technician never showed up. I am calling you."}, "occurred_at": "2026-09-22T17:02:11Z"},
      {"type": "event", "idempotency_key": "wamid.002", "channel": "whatsapp", "conversation_id": "wa-8812",
       "handles": [{"type": "phone_e164", "value": "+14155550123"}], "speaker": {"role": "ai_agent"},
       "content": {"text": "I am sorry, Marina. I am checking the visit now."}, "occurred_at": "2026-09-22T17:02:19Z"},
      {"type": "conversation.ended", "idempotency_key": "wa-8812-end-1", "conversation_id": "wa-8812",
       "occurred_at": "2026-09-22T17:03:00Z"}
    ]
  }'
  ```
</CodeGroup>

A API responde `200` quando todos os itens entraram, ou `207` quando algum foi recusado, sempre com `accepted`, `duplicates` e um erro para cada item recusado: um item ruim nunca derruba o lote. Mandar o mesmo `idempotency_key` de novo não tem problema; ele conta como duplicado e é gravado uma vez só.

## 4. Leia o contexto

Agora um agente de voz atende uma ligação do mesmo número. Ele pede o contexto antes de dizer alô:

<CodeGroup>
  ```python Python theme={null}
  ctx = niadra.context(subject=marina, view="voice", conversation_id="call-4471")

  print(ctx.text)           # the pack, ready for the system prompt
  print(ctx.withheld)       # items held back at this verification level
  print(ctx.origin)         # network, cache, stale, last_good or empty
  ```

  ```typescript TypeScript theme={null}
  const ctx = await niadra.context({ subject: marina, view: "voice", conversation_id: "call-4471" });

  console.log(ctx.text);    // the pack, ready for the system prompt
  console.log(ctx.suffix);  // live turns and deltas, for the end of the prompt
  console.log(ctx.source);  // network, cache, stale, fallback or none
  ```

  ```bash cURL theme={null}
  curl -X POST "https://acme-sandbox.us-east-1.api.niadra.com/v1/context" \
    -H "Authorization: Bearer $NIADRA_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{"subject": {"type": "phone_e164", "value": "+14155550123"}, "view": "voice", "conversation_id": "call-4471"}'
  ```
</CodeGroup>

Ponha `text` no prompt de sistema, depois das suas instruções. A mensagem de WhatsApp de agora há pouco já está lá: os turnos ficam legíveis para todos os agentes em menos de um segundo, e a memória derivada (pendências, fatos, o episódio) vem em até um minuto depois do fim da sessão.

<Tip>
  Chame `context()` enquanto o telefone ainda toca, ou assim que a mensagem chega. O SDK tem o próprio tempo máximo (150 ms na view `voice`, 300 ms nas outras), então uma resposta lenta nunca atrasa o seu agente: ele recebe um contexto vazio e segue.
</Tip>

## 5. Busque no histórico

Quando a cliente diz "da outra vez vocês me deram um crédito", o agente confere:

<CodeGroup>
  ```python Python theme={null}
  found = niadra.search(marina, "credit for missed technician visit", conversation_id="call-4471", voice=True)

  for item in found.items:
      print(item.at, item.channel, item.text)
  if found.recurrence:
      print(found.recurrence.occurrences, "times in", found.recurrence.window_days, "days")
  ```

  ```typescript TypeScript theme={null}
  const { data } = await niadra.search({
    subject: marina,
    query: "credit for missed technician visit",
    conversation_id: "call-4471",
    max_tokens: 300,
  });

  for (const item of data?.items ?? []) console.log(item.at, item.channel, item.text);
  ```

  ```bash cURL theme={null}
  curl -X POST "https://acme-sandbox.us-east-1.api.niadra.com/v1/history/search" \
    -H "Authorization: Bearer $NIADRA_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{"subject": {"type": "phone_e164", "value": "+14155550123"}, "query": "credit for missed technician visit", "max_tokens": 300}'
  ```
</CodeGroup>

Para o seu LLM decidir sozinho quando buscar, entregue a ele o kit de ferramentas: `niadra.tools(marina, conversation_id="call-4471")` devolve as definições de função amarradas à Marina e leva as chamadas do modelo de volta à Niadra. Veja [Navegação do histórico](/concepts/history).

## 6. Confira o que aconteceu

Cada leitura deixou um comprovante: qual fonte leu, quais itens recebeu e quais ficaram retidos, sob qual política. Abra o Console para ver as leituras desta conversa, ou liste pela rota [`GET /v1/receipts`](/api/receipts), como pessoa com o papel `security` ou com uma chave de escopo `admin`.

## Próximos passos

<CardGroup cols={2}>
  <Card title="Espaços e chaves" href="/concepts/spaces-and-keys">
    Fontes, escopos, ambientes e o endereço estável.
  </Card>

  <Card title="Eventos e o lote" href="/concepts/events">
    Mensagens, eventos de sistema e ações num formato só.
  </Card>

  <Card title="Agentes de voz" href="/guides/voice-agents">
    Contexto antes do alô, atestado de rede e transbordo.
  </Card>

  <Card title="Agentes internos" href="/guides/internal-agents">
    Tarefas, objetos e ações que fecham pendências.
  </Card>
</CardGroup>
