---
title: "Get an AMD decision"
method: GET
path: "/v1/amd/calls/{call_id}"
tags: ["AMD"]
---

# Get an AMD decision

`GET /v1/amd/calls/{call_id}`

## Request

- Base URL: `https://api.pyai.com`
- URL: `https://api.pyai.com/v1/amd/calls/{call_id}`
- Auth: one of:
  - HTTP bearer
  - API key in header `x-api-key`

The full decision for one call: `answered_by`, `answered_by_twilio`, `confidence`, `decision_ms`, and the word-level `reason`. Requires `amd:read`.

## Path parameters

- `call_id` string, required

## Response `200`

AMD decision detail

- AmdCall: Optional structured evidence on new AMD decisions; older records may omit it.
  - `object` string
  - `call_id` string
  - `session_label` string, nullable: The opaque tag passed on the connect URL / TwiML, if any.
  - `status` 'completed' | 'failed'
  - `answered_by` 'human' | 'machine' | 'voicemail' | 'live_voicemail' | 'screening' | 'ivr' | 'music' | 'human_gatekeeper' | 'sit_invalid' | 'fax' | 'silence' | 'unknown': PyAI's richer answered-by vocabulary. `machine` means an automated answer without an established subtype; it does not establish voicemail readiness or authorize hanging up. `screening` = an iPhone/Google call-screening assistant; `sit_invalid` = a dead/disconnected number.
  - `answered_by_twilio` string, nullable: Twilio's exact `AnsweredBy` enum (human | machine_start | machine_end_beep | machine_end_silence | machine_end_other | fax | unknown), so a Twilio drop-in keeps its routing logic unchanged.
  - `confidence` number, nullable
  - `decision_ms` number, nullable: Processed inbound audio through the decision, in ms; not elapsed time from carrier answer.
  - `created_at` integer: Unix ms when the decision was written.
  - `engine_version` string: Decision-policy identity.
  - `rule_id` string: Stable decision rule identifier.
  - `decision_timeout_ms` integer: Requested elapsed decision budget. Present when explicitly configured on the stream.
  - `decision_elapsed_ms` integer: Elapsed milliseconds from accepted authenticated start to result preparation; excludes webhook transport. Present when decision_timeout_ms was requested.
  - `speech_ms` integer, nullable: Cumulative voiced audio excluding pauses; null if untracked.
  - `silence_ms` integer: Current contiguous silence in ms.
  - `speech_elapsed_ms` integer, nullable: Audio since speech onset including pauses; null without onset.
  - `thresholds` object: Effective decision thresholds and rule flags.
  - `reason` string, nullable: Human-readable evidence, e.g. "machine phrase: 'please leave a message' at 1.2s".
  - `aggressiveness` number, nullable: Operating point used for this call.
  - `custom_parameters` AmdCustomParameters: Customer correlation parameters, excluding reserved controls and credentials. Names match [A-Za-z0-9][A-Za-z0-9_.-]{0,63}. Each value is bounded to 1024 UTF-8 bytes, and all names plus values to 8192 UTF-8 bytes; character limits alone do not express these byte limits. Nested fields never override AMD result fields.
  - `started_at` integer, nullable: Unix ms when the call was answered.
  - `meta` object, nullable
  - `error` string, nullable: Present when status is failed.

## Other responses

- `401`: Missing or invalid API key (`code: unauthorized`)
- `404`: Resource not found (`code: not_found`)

---

[API](https://skmtc.dev/pyai/apis/pyai-api.md) · [All operations](https://skmtc.dev/pyai/apis/pyai-api/llms.txt) · [OpenAPI document](https://skmtc.dev/pyai/apis/pyai-api/revisions/271a1539185b?raw)
