Bluejay tests and monitors conversational AI agents. An agent is the system under test; a digital human is one test case that calls it; a simulation runs a set of them; a community groups them for reuse.
Read the field descriptions on the digital human tools before authoring one. Behavior belongs in fields, not in `intent` prose, and each field's description says what it owns.
Before creating a batch: read an existing digital human in the same organization to pick up that team's conventions, then create and run ONE and read the transcript. Nothing rejects a well-formed config that does nothing, so an unmatched trigger and a discarded opener both return 200.
Discoverability
0 of 6 checks0/100
Client listings and public setup information.
mcp.json or server-card.json
Either mcp.json or an MCP Server Card declaring this endpoint passes.
How to fix: On each tool, declare annotations.readOnlyHint, annotations.destructiveHint, and annotations.openWorldHint as booleans. The policy review separately assesses whether their values match the tool's actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description79/100
Create an agent via Bluejay add-agent endpoint.
Pass ``eleven_labs_agent_id`` to link the agent to an ElevenLabs Convai
agent; the endpoint then defaults ``provider`` to ELEVENLABS. ``provider``
can be set explicitly to override that default.
``provider_request_data`` is the agent variables map, e.g. ``{"account_number": "A-111"}``.
Every digital human of the agent inherits them at run time and fills ``{{name}}`` tokens
with them; a digital human's trait with the same name overrides one.
For AMELIA_CHAT / AMELIA_VOICE pass ``amelia_base_url`` and
``amelia_domain_code`` (both required), plus ``amelia_flow_name`` or
``amelia_agent_name`` if you want workflow sync; ``provider`` then defaults
to AMELIA.
For SIERRA_VOICE pass ``sierra_agent_token`` (the agent token from the Sierra
Voice Protocol URL); ``sierra_release`` pins a release target or hash and
``sierra_agent_parameters`` is the string map the agent receives at open. The
org's Sierra headless API token is configured under integrations, not here.
Pass ``dynamic_sip_webhook_url`` to make this a SIP agent whose destination
URI is fetched from your webhook at dial time (per call) instead of a static
sip_uri. Mutually exclusive with the other connection fields.
For an email agent pass ``mode="EMAIL"``, ``connection_type="EMAIL"`` and
``email_address`` (the inbox digital humans email during simulations, e.g.
[email protected]). If that agent answers from other addresses, list them in
``email_reply_addresses``; a reply from any of them is accepted. Run it with
``queue_email_simulation_run``. That inbox
must allowlist Bluejay's sending domain (bluejaysims.com), or corporate mail
(Google Workspace, Microsoft 365) quarantines the test. For an outbound email
agent (your system emails the DH first) also pass ``agent_type="OUTBOUND"`` and
``outbound_trigger_webhook_url``; put ``{{digital_human.email}}`` in
``outbound_trigger_payload_template`` to receive the per-test address to email.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 33 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
name
Not provided
Missing description. Explain what this value means and how to supply it.
system_prompt
Not provided
Missing description. Explain what this value means and how to supply it.
knowledge_base
Not provided
Missing description. Explain what this value means and how to supply it.
goals
Not provided
Missing description. Explain what this value means and how to supply it.
phone_number
Not provided
Missing description. Explain what this value means and how to supply it.
email_address
Not provided
Missing description. Explain what this value means and how to supply it.
email_reply_addresses
Not provided
Missing description. Explain what this value means and how to supply it.
agent_type
Not provided
Missing description. Explain what this value means and how to supply it.
connection_type
Not provided
Missing description. Explain what this value means and how to supply it.
mode
Not provided
Missing description. Explain what this value means and how to supply it.
keyterms
Not provided
Missing description. Explain what this value means and how to supply it.
follow_up_sms_sender_numbers
Not provided
Missing description. Explain what this value means and how to supply it.
external_agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
folder
Not provided
Missing description. Explain what this value means and how to supply it.
http_webhook
Not provided
Missing description. Explain what this value means and how to supply it.
dynamic_sip_webhook_url
Not provided
Missing description. Explain what this value means and how to supply it.
outbound_trigger_webhook_url
Not provided
Missing description. Explain what this value means and how to supply it.
outbound_trigger_payload_template
Not provided
Missing description. Explain what this value means and how to supply it.
websocket_url
Not provided
Missing description. Explain what this value means and how to supply it.
websocket_username
Not provided
Missing description. Explain what this value means and how to supply it.
websocket_password
Not provided
Missing description. Explain what this value means and how to supply it.
retell_agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
eleven_labs_agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_base_url
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_domain_code
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_flow_name
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_agent_name
Not provided
Missing description. Explain what this value means and how to supply it.
sierra_agent_token
Not provided
Missing description. Explain what this value means and how to supply it.
sierra_release
Not provided
Missing description. Explain what this value means and how to supply it.
sierra_agent_parameters
Not provided
Missing description. Explain what this value means and how to supply it.
provider_request_data
Not provided
Missing description. Explain what this value means and how to supply it.
provider
Not provided
Missing description. Explain what this value means and how to supply it.
simulations_disabled
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description92/100
Update an existing agent via Bluejay POST /v1/update-agent.
``system_prompt`` saves a new prompt version and moves the agent's "latest" label to
it, unless it matches the "latest" prompt; it does not rewrite the agent row. Agent reads return the "latest" version's
prompt, so get_agent shows the new text right away. Earlier versions stay in
list_prompt_versions.
``provider`` can be set to correct an agent's source label — e.g. re-stamping
an ElevenLabs agent that was saved as CUSTOM. Switching ``connection_type`` to
AMELIA_CHAT / AMELIA_VOICE does not restamp ``provider``, so pass
``provider=AMELIA`` too if the workflow tools should see it as Amelia.
``amelia_base_url`` / ``amelia_domain_code`` / ``amelia_flow_name`` /
``amelia_agent_name`` configure an Amelia agent; workflow sync pulls the
cognitive agent if named, else the flow.
``sierra_agent_token`` / ``sierra_release`` / ``sierra_agent_parameters``
configure a SIERRA_VOICE agent (Sierra Voice Protocol).
Pass ``dynamic_sip_webhook_url`` to point a SIP agent at a webhook that
returns its destination URI per call at dial time (replaces a static sip_uri).
``agent_id`` is whichever id you have and ``id_type`` says which one it is:
"bluejay" for the numeric id this API returns, "external" for the id from your
own system stored on the agent as external_agent_id. The external route writes
a smaller field set — it cannot change external_agent_id, the websocket
credentials or eleven_labs_agent_id, and rejects the call rather than dropping
them.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 35 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
id_type
Not provided
Missing description. Explain what this value means and how to supply it.
name
Not provided
Missing description. Explain what this value means and how to supply it.
system_prompt
Not provided
Missing description. Explain what this value means and how to supply it.
knowledge_base
Not provided
Missing description. Explain what this value means and how to supply it.
goals
Not provided
Missing description. Explain what this value means and how to supply it.
phone_number
Not provided
Missing description. Explain what this value means and how to supply it.
email_address
Not provided
Missing description. Explain what this value means and how to supply it.
email_reply_addresses
Not provided
Missing description. Explain what this value means and how to supply it.
agent_type
Not provided
Missing description. Explain what this value means and how to supply it.
connection_type
Not provided
Missing description. Explain what this value means and how to supply it.
mode
Not provided
Missing description. Explain what this value means and how to supply it.
keyterms
Not provided
Missing description. Explain what this value means and how to supply it.
follow_up_sms_sender_numbers
Not provided
Missing description. Explain what this value means and how to supply it.
external_agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
folder
Not provided
Missing description. Explain what this value means and how to supply it.
http_webhook
Not provided
Missing description. Explain what this value means and how to supply it.
dynamic_sip_webhook_url
Not provided
Missing description. Explain what this value means and how to supply it.
outbound_trigger_webhook_url
Not provided
Missing description. Explain what this value means and how to supply it.
outbound_trigger_payload_template
Not provided
Missing description. Explain what this value means and how to supply it.
websocket_url
Not provided
Missing description. Explain what this value means and how to supply it.
websocket_username
Not provided
Missing description. Explain what this value means and how to supply it.
websocket_password
Not provided
Missing description. Explain what this value means and how to supply it.
retell_agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
eleven_labs_agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_base_url
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_domain_code
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_flow_name
Not provided
Missing description. Explain what this value means and how to supply it.
amelia_agent_name
Not provided
Missing description. Explain what this value means and how to supply it.
sierra_agent_token
Not provided
Missing description. Explain what this value means and how to supply it.
sierra_release
Not provided
Missing description. Explain what this value means and how to supply it.
sierra_agent_parameters
Not provided
Missing description. Explain what this value means and how to supply it.
provider_request_data
Not provided
Missing description. Explain what this value means and how to supply it.
provider
Not provided
Missing description. Explain what this value means and how to supply it.
simulations_disabled
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description80/100
Retrieve a single agent via Bluejay GET /v1/agents/{agent_id}.
`agent_id` is whichever id you have; `id_type` says which one it is —
"bluejay" for the numeric id this API returns and list_agents reports,
"external" for the id from your own system that was stored on the agent as
external_agent_id.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
id_type
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema13/100
Declare the result fields and their types in the output schema.
{
"name": "get_agent",
"title": "Get agent",
"description": "Retrieve a single agent via Bluejay GET /v1/agents/{agent_id}.\n\n`agent_id` is whichever id you have; `id_type` says which one it is —\n\"bluejay\" for the numeric id this API returns and list_agents reports,\n\"external\" for the id from your own system that was stored on the agent as\nexternal_agent_id.\n",
"inputSchema": {
"type": "object",
"title": "get_agentArguments",
"required": [
"agent_id"
],
"properties": {
"id_type": {
"enum": [
"bluejay",
"external"
],
"type": "string",
"title": "Id Type",
"default": "bluejay"
},
"agent_id": {
"type": "string",
"title": "Agent Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "get_agentDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description94/100
List agents via Bluejay GET /v1/all-agents.
Returns {id, name} for every agent in the org. `folder_id` narrows the listing
to one folder (from list_folders) and returns the full agent rows for it.
`total_count` is the number of agents returned; use it for "how many" instead of counting.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
folder_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema8/100
Declare the result fields and their types in the output schema.
{
"name": "list_agents",
"title": "List agents",
"description": "List agents via Bluejay GET /v1/all-agents.\n\nReturns {id, name} for every agent in the org. `folder_id` narrows the listing\nto one folder (from list_folders) and returns the full agent rows for it.\n`total_count` is the number of agents returned; use it for \"how many\" instead of counting.\n",
"inputSchema": {
"type": "object",
"title": "list_agentsArguments",
"properties": {
"folder_id": {
"anyOf": [
{
"type": "string",
"format": "uuid"
},
{
"type": "null"
}
],
"title": "Folder Id",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "list_agentsDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description79/100
Delete an agent via Bluejay DELETE /v1/agent/{agent_id}.
confirm: pass true only after the user agrees to stop an always-on number or a
simulation that is still running. Without it those deletes return HTTP 409.
Explain mutations, irreversible effects, or prerequisites that matter before calling this tool.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
confirm
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description87/100
List simulations via Bluejay GET /v1/get-all-simulations.
Returns {id, name, created_at} for up to 100 simulations in the org.
`agent_id` narrows the listing to the simulations that run against that one
agent and returns the full simulation rows for it.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema7/100
Declare the result fields and their types in the output schema.
{
"name": "list_simulations",
"title": "List simulations",
"description": "List simulations via Bluejay GET /v1/get-all-simulations.\n\nReturns {id, name, created_at} for up to 100 simulations in the org.\n`agent_id` narrows the listing to the simulations that run against that one\nagent and returns the full simulation rows for it.\n",
"inputSchema": {
"type": "object",
"title": "list_simulationsArguments",
"properties": {
"agent_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Agent Id",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "list_simulationsDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description95/100
Create one or many digital humans in ONE call (POST /v1/create-digital-humans).
Three rules a good digital human follows (docs: /key-concepts/digital-humans/best-practices):
1. intent and success_criteria stay one or two sentences. Detail that grows them belongs
elsewhere: configuration for the caller, a custom metric for the grading.
2. Every "if the agent says X, the caller does Y" moves out of prose into a field —
traits for case facts the caller recites, scripted_responses for verbatim lines / DTMF /
silence, speaks_first_config for the opener, and lower creativity for repeatability.
3. Ground the case in the agent's real context (get_agent, get_workflow_summary) so the
scenario resembles a call this agent actually takes.
Pass a single-item list to create one. `digital_humans` carries each digital
human's config (intent, traits, voice, transcripts); `simulation_ids` is separate because
the endpoint attaches the SAME simulations to every item in the call. To give
items different simulations, create them here and then set membership per digital
human with bulk_set_digital_human_simulations.
language/accent/gender must form a valid combination — call get_voice_options
first to see the valid language -> accent pairings.
background_noise="custom" requires custom_background_noise_url: a storage_path
from the org's noise library (list_custom_background_noises, or upload via
create_custom_background_noise_upload_url + create_custom_background_noise).
Returns `created` (the new digital humans) and `errors` (per-item failures by index);
a partially successful batch returns both.
The description explains the capability, when to use it, and what to expect.
Inputs80/100
75 of 86 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › DigitalHumanRequestData › intent
The scenario the digital human enacts, in ONE OR TWO SENTENCES: what this caller wants, not how to behave. It fills one slot in a prompt that ALREADY renders traits, verbosity, fluency, a not-the-agent guardrail and end-of-call instructions, so restating those here is duplicate prompt. Anything shaped like 'if the agent says X, do Y' does not belong here — it belongs in a field, and prose makes it non-deterministic. Move it: case facts the agent may ask for (member ID, DOB, order number, policy number) to `traits`; lines that must be said verbatim, a keypad entry, or a deliberate pause to `scripted_responses`; who opens the call to `speaks_first_config`; language, accent, fluency, verbosity, background noise, audio quality, interruptions, hangup and silence behavior to their own fields; and lower `creativity` for repeatability. If you reach for 'correctly', 'appropriately' or 'successfully' you are describing what the AGENT should do — that goes in `success_criteria`, not here. Leave empty when enriched_playback is set; the agent uses playback instead.
The pass/fail condition for this one test, in ONE OR TWO observable outcomes the transcript can settle (e.g. 'the agent verified the member ID and booked a callback'). It is not a rubric: a scored checklist, a per-dimension score, or a condition you want graded on every call in the suite belongs in a custom metric (`create_custom_metrics`) attached to the simulation, not in this string. Describe the AGENT's outcome here, never the digital human's own actions — those are `intent`. Leave empty when enriched_playback is set; the agent uses playback instead.
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › name
Name of the digital human
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › tag
Tag for categorizing the digital human
Explain the meaning of this value, not just its name.
$defs › DigitalHumanRequestData › tags
Full tag list (takes precedence over `tag`). Free-form labels; use `type` for voicemail, replay and the other kinds.
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › type
What kind of digital human this is. Set it instead of putting sentinel values in tags; tags are free-form labels. Legacy sentinel tags (e.g. 'voicemail-custom', or 'transcript_generated' + 'smart') still set it when this is omitted.
The quoted system-prompt rules this digital human covers, shown on its card.
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › language
Language the digital human speaks
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › accent
Accent of the digital human
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › gender
Gender of the digital human
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › custom_voice_id
ElevenLabs voice_id of a cloned voice. When set, the agent speaks with this voice instead of the accent's stock voice (language/accent still drive prompts and STT).
Seconds the digital human waits before it replies. Named patience in the UI, and accepted under either name.
Clear enough to supply this argument.
$defs › DigitalHumanRequestData › creativity
Model temperature for the digital human's own speech. Lower it (0.0-0.3) when you want the same call twice — regression tests and anything you will compare run over run. Keep it near the 0.7 default for exploratory or red-team cases.
Freeform instructions for how/when to hang up. The literal string "default" (or null) keeps the tuned built-in end-of-call behavior, which already handles ordinary goodbyes; any other string REPLACES it, so write one only for a condition the default would miss.
Who this caller is, in one short line (e.g. 'retiree on a family plan, not comfortable with phone menus'). It owns identity and disposition only. What they are calling about is `intent`; the facts they can recite are `traits`; how they sound is language/accent/fluency/verbosity. Never put internal or agent-side information here — the digital human only knows what a real caller would know.
Clear enough to supply this argument.
$defs › Trait › trait_name
Name of the fact, as the agent would ask for it: 'member_id', 'date_of_birth', 'order_number'. Traits are org-level, so reuse the existing name across the suite rather than coining a variant. A trait is always something the CALLER knows and can say out loud — never internal or agent-side information (CRM contents, what the agent should look up or say, grader notes).
Clear enough to supply this argument.
$defs › Trait › trait_data_type
BOOLEAN, STRING, DATE (ISO 8601 string) or NUMBER. Must match `value`, which is coerced to this type.
Clear enough to supply this argument.
$defs › Trait › value
The concrete value this caller gives (stored as JSONB). Fixing it here is what makes the call repeatable — leave it out of `intent` prose, where the model would improvise a different one each run.
Clear enough to supply this argument.
$defs › Trait › is_sip_header
Send this trait as a SIP header on the call instead of as something the caller says. Leave false for ordinary case facts.
Clear enough to supply this argument.
$defs › SimpleInterruptionConfig › type
Interruption level: none, low, medium, or high
Clear enough to supply this argument.
$defs › KeywordsInterruptionConfig › type
Type discriminator for keywords interruption (required)
Clear enough to supply this argument.
$defs › KeywordResponse › keyword
The keyword to listen for and interrupt on
Clear enough to supply this argument.
$defs › KeywordResponse › response
Response to say when keyword is detected
Clear enough to supply this argument.
$defs › KeywordResponse › probability
Probability of responding (0.0-1.0) - defaults to 1.0
How match_phrase is compared to the agent's turn. 'exact' is a fuzzy string comparison. Use it when you have the agent's literal line from a transcript, since it is stricter and costs no LLM call. 'context' asks an LLM whether the two utterances mean the same thing. Use it when the agent could phrase the same intent several ways.
Clear enough to supply this argument.
$defs › ScriptedResponse › match_phrase
An utterance the AGENT would say, which releases this response, e.g. 'Can I have your account number?'. Matching compares utterance to utterance, so a description of what the agent is doing ('the agent finished answering and is inviting another question') never matches anything: the rule saves and silently never fires. Write the line you expect to hear. Empty string is only meaningful when the digital human has scripted_responses_ordered set, where it fires on the digital human's next turn regardless of what the agent said.
Clear enough to supply this argument.
$defs › ScriptedResponse › response_type
Type of response: 'phrase', 'silence', 'dtmf', or 'audio'
Clear enough to supply this argument.
$defs › ScriptedResponse › response_value
The response text (required for 'phrase' and 'dtmf', optional for 'silence', unused for 'audio')
Skywatch bucket path of an uploaded audio file. AUDIO rows only — the agent downloads and plays this verbatim.
Clear enough to supply this argument.
$defs › ScriptedResponse › occurrence_mode
When to apply: 'always' or 'first_n'. Ignored when the digital human has scripted_responses_ordered set, where every step fires exactly once regardless.
Clear enough to supply this argument.
$defs › ScriptedResponse › occurrence_n
Number of times to apply (required if occurrence_mode is 'first_n', must be > 0)
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › ScriptedResponse › silence_duration
Duration in seconds for silence period (only used when response_type is 'silence', must be > 0 if provided)
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
When true, scripted_responses run as a script in list order: only the next unfired one is armed, each fires once, and a blank match_phrase fires on the digital human's next turn. When false (default) any scripted response fires whenever its match_phrase comes up.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › speaks_first
Whether the digital human speaks first in the call
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › mode
When speaks_first is true: 'custom' (user-provided message) or 'ai_generated' (no message)
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › message
When mode is 'custom', the message the digital human says first
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › dynamic
When speaks_first is true: wait up to 5s for the agent to open; speak first only if it stays quiet. If the agent does open, the digital human yields and a mode='custom' message is DISCARDED, not spoken after the greeting, so on any agent that greets callers, a dynamic custom opener is never heard. Set false to speak it every time, at the top of the call and possibly over the greeting. Defaults on, so configs saved before this field existed become dynamic
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
{
"name": "create_digital_humans",
"title": "Create digital humans",
"description": "Create one or many digital humans in ONE call (POST /v1/create-digital-humans).\n\nThree rules a good digital human follows (docs: /key-concepts/digital-humans/best-practices):\n1. intent and success_criteria stay one or two sentences. Detail that grows them belongs\n elsewhere: configuration for the caller, a custom metric for the grading.\n2. Every \"if the agent says X, the caller does Y\" moves out of prose into a field —\n traits for case facts the caller recites, scripted_responses for verbatim lines / DTMF /\n silence, speaks_first_config for the opener, and lower creativity for repeatability.\n3. Ground the case in the agent's real context (get_agent, get_workflow_summary) so the\n scenario resembles a call this agent actually takes.\n\nPass a single-item list to create one. `digital_humans` carries each digital\nhuman's config (intent, traits, voice, transcripts); `simulation_ids` is separate because\nthe endpoint attaches the SAME simulations to every item in the call. To give\nitems different simulations, create them here and then set membership per digital\nhuman with bulk_set_digital_human_simulations.\n\nlanguage/accent/gender must form a valid combination — call get_voice_options\nfirst to see the valid language -> accent pairings.\n\nbackground_noise=\"custom\" requires custom_background_noise_url: a storage_path\nfrom the org's noise library (list_custom_background_noises, or upload via\ncreate_custom_background_noise_upload_url + create_custom_background_noise).\n\nReturns `created` (the new digital humans) and `errors` (per-item failures by index);\na partially successful batch returns both.\n",
"inputSchema": {
"type": "object",
"$defs": {
"Trait": {
"type": "object",
"title": "Trait",
"required": [
"trait_name",
"trait_data_type",
"value"
],
"properties": {
"value": {
"title": "Value",
"description": "The concrete value this caller gives (stored as JSONB). Fixing it here is what makes the call repeatable — leave it out of `intent` prose, where the model would improvise a different one each run."
},
"trait_name": {
"type": "string",
"title": "Trait Name",
"description": "Name of the fact, as the agent would ask for it: 'member_id', 'date_of_birth', 'order_number'. Traits are org-level, so reuse the existing name across the suite rather than coining a variant. A trait is always something the CALLER knows and can say out loud — never internal or agent-side information (CRM contents, what the agent should look up or say, grader notes)."
},
"is_sip_header": {
"type": "boolean",
"title": "Is Sip Header",
"default": false,
"description": "Send this trait as a SIP header on the call instead of as something the caller says. Leave false for ordinary case facts."
},
"trait_data_type": {
"$ref": "#/$defs/TraitDataType",
"description": "BOOLEAN, STRING, DATE (ISO 8601 string) or NUMBER. Must match `value`, which is coerced to this type."
}
},
"description": "Model for a single trait."
},
"MatchType": {
"enum": [
"exact",
"context"
],
"type": "string",
"title": "MatchType",
"description": "Enum for scripted response match types."
},
"AccentType": {
"enum": [
"multilingual",
"american",
"american2",
"mature",
"southern",
"italian",
"indian",
"british",
"australian",
"scottish",
"irish",
"welsh",
"mexican",
"spanish",
"portuguese",
"french",
"turkish",
"japanese",
"hindi",
"arabic",
"egyptian",
"levantine",
"hebrew",
"russian",
"chinese",
"german",
"korean",
"urdu",
"telugu",
"tamil",
"malayalam",
"kannada",
"marathi",
"gujarati",
"vietnamese",
"cantonese",
"tagalog",
"greek",
"autodetect",
"watson",
"watsonbritish",
"watsonaustralian",
"watsoncanadian"
],
"type": "string",
"title": "AccentType",
"description": "Enum for accent options."
},
"GenderType": {
"enum": [
"male",
"female"
],
"type": "string",
"title": "GenderType",
"description": "Enum for gender options."
},
"FluencyType": {
"enum": [
"beginner",
"intermediate",
"native"
],
"type": "string",
"title": "FluencyType",
"description": "Enum for fluency level options."
},
"JourneyStep": {
"type": "object",
"title": "JourneyStep",
"required": [
"step"
],
"properties": {
"step": {
"type": "integer",
"title": "Step",
"minimum": 0
},
"intent": {
"type": "string",
"title": "Intent",
"default": ""
},
"modality": {
"enum": [
"voice",
"sms"
],
"type": "string",
"title": "Modality",
"default": "voice"
},
"direction": {
"anyOf": [
{
"enum": [
"inbound",
"outbound"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Direction",
"default": null
},
"phone_number": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Phone Number",
"default": null
},
"unresponsive": {
"type": "boolean",
"title": "Unresponsive",
"default": false
},
"wait_seconds": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "Wait Seconds",
"default": null
},
"success_criteria": {
"type": "string",
"title": "Success Criteria",
"default": ""
},
"response_window_seconds": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "Response Window Seconds",
"default": null
}
}
},
"LanguageType": {
"enum": [
"en",
"es",
"pt",
"ja",
"tr",
"hi",
"ar",
"he",
"ru",
"zh",
"ml",
"fr",
"yue",
"vi",
"de",
"ko",
"ur",
"te",
"ta",
"mal",
"kn",
"mr",
"gu",
"tl",
"el",
"ad"
],
"type": "string",
"title": "LanguageType",
"description": "Enum for supported language types."
},
"ResponseType": {
"enum": [
"phrase",
"silence",
"dtmf",
"audio"
],
"type": "string",
"title": "ResponseType",
"description": "Enum for scripted response types."
},
"TraitDataType": {
"enum": [
"BOOLEAN",
"STRING",
"DATE",
"NUMBER"
],
"type": "string",
"title": "TraitDataType",
"description": "Enum for trait data types."
},
"VerbosityType": {
"enum": [
"low",
"medium",
"high"
],
"type": "string",
"title": "VerbosityType",
"description": "Enum for verbosity level options."
},
"OccurrenceMode": {
"enum": [
"always",
"first_n"
],
"type": "string",
"title": "OccurrenceMode",
"description": "Enum for scripted response occurrence modes."
},
"VoiceSpeedType": {
"enum": [
"slowest",
"slow",
"normal",
"fast",
"fastest"
],
"type": "string",
"title": "VoiceSpeedType",
"description": "Enum for voice speed options."
},
"KeywordResponse": {
"type": "object",
"title": "KeywordResponse",
"required": [
"keyword",
"response"
],
"properties": {
"keyword": {
"type": "string",
"title": "Keyword",
"description": "The keyword to listen for and interrupt on"
},
"response": {
"type": "string",
"title": "Response",
"description": "Response to say when keyword is detected"
},
"probability": {
"type": "number",
"title": "Probability",
"default": 1,
"maximum": 1,
"minimum": 0,
"description": "Probability of responding (0.0-1.0) - defaults to 1.0"
}
},
"description": "Model for a keyword response configuration."
},
"AudioQualityType": {
"enum": [
"high",
"medium",
"low",
"horrible"
],
"type": "string",
"title": "AudioQualityType",
"description": "Enum for audio quality options."
},
"DigitalHumanType": {
"enum": [
"voicemail_custom",
"voicemail_ai",
"replay_smart",
"replay_strict",
"red_team",
"scenario",
"workflow",
"persona",
"journey"
],
"type": "string",
"title": "DigitalHumanType",
"description": "What kind of digital human this is. Stored in test_cases.type; tags are free-form labels."
},
"DtmfOrVoicedType": {
"enum": [
"voiced",
"dtmf"
],
"type": "string",
"title": "DtmfOrVoicedType",
"description": "Enum for DTMF vs voiced input mode."
},
"ExpectedToolCall": {
"type": "object",
"title": "ExpectedToolCall",
"required": [
"name"
],
"properties": {
"name": {
"type": "string",
"title": "Name",
"description": "Name of the expected tool call"
},
"output": {
"anyOf": [
{},
{
"type": "null"
}
],
"title": "Output",
"default": null,
"description": "Expected output returned by the tool call"
},
"parameters": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Parameters",
"default": null,
"description": "Expected parameters passed to the tool call"
}
},
"description": "Represents an expected tool call during a conversation."
},
"ScriptedResponse": {
"type": "object",
"title": "ScriptedResponse",
"required": [
"match_type",
"match_phrase",
"response_type",
"occurrence_mode"
],
"properties": {
"match_type": {
"$ref": "#/$defs/MatchType",
"description": "How match_phrase is compared to the agent's turn. 'exact' is a fuzzy string comparison. Use it when you have the agent's literal line from a transcript, since it is stricter and costs no LLM call. 'context' asks an LLM whether the two utterances mean the same thing. Use it when the agent could phrase the same intent several ways."
},
"match_phrase": {
"type": "string",
"title": "Match Phrase",
"description": "An utterance the AGENT would say, which releases this response, e.g. 'Can I have your account number?'. Matching compares utterance to utterance, so a description of what the agent is doing ('the agent finished answering and is inviting another question') never matches anything: the rule saves and silently never fires. Write the line you expect to hear. Empty string is only meaningful when the digital human has scripted_responses_ordered set, where it fires on the digital human's next turn regardless of what the agent said."
},
"occurrence_n": {
"anyOf": [
{
"type": "integer",
"exclusiveMinimum": 0
},
{
"type": "null"
}
],
"title": "Occurrence N",
"default": null,
"description": "Number of times to apply (required if occurrence_mode is 'first_n', must be > 0)"
},
"response_type": {
"$ref": "#/$defs/ResponseType",
"description": "Type of response: 'phrase', 'silence', 'dtmf', or 'audio'"
},
"response_value": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Response Value",
"default": null,
"description": "The response text (required for 'phrase' and 'dtmf', optional for 'silence', unused for 'audio')"
},
"occurrence_mode": {
"$ref": "#/$defs/OccurrenceMode",
"description": "When to apply: 'always' or 'first_n'. Ignored when the digital human has scripted_responses_ordered set, where every step fires exactly once regardless."
},
"silence_duration": {
"anyOf": [
{
"type": "integer",
"exclusiveMinimum": 0
},
{
"type": "null"
}
],
"title": "Silence Duration",
"default": null,
"description": "Duration in seconds for silence period (only used when response_type is 'silence', must be > 0 if provided)"
},
"scripted_response_audio_snippet_url": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Scripted Response Audio Snippet Url",
"default": null,
"description": "Skywatch bucket path of an uploaded audio file. AUDIO rows only — the agent downloads and plays this verbatim."
}
},
"description": "Model for a scripted response configuration."
},
"SpeaksFirstConfig": {
"type": "object",
"title": "SpeaksFirstConfig",
"required": [
"speaks_first"
],
"properties": {
"mode": {
"anyOf": [
{
"enum": [
"custom",
"ai_generated"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Mode",
"default": null,
"description": "When speaks_first is true: 'custom' (user-provided message) or 'ai_generated' (no message)"
},
"dynamic": {
"type": "boolean",
"title": "Dynamic",
"default": true,
"description": "When speaks_first is true: wait up to 5s for the agent to open; speak first only if it stays quiet. If the agent does open, the digital human yields and a mode='custom' message is DISCARDED, not spoken after the greeting, so on any agent that greets callers, a dynamic custom opener is never heard. Set false to speak it every time, at the top of the call and possibly over the greeting. Defaults on, so configs saved before this field existed become dynamic"
},
"message": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Message",
"default": null,
"description": "When mode is 'custom', the message the digital human says first"
},
"speaks_first": {
"type": "boolean",
"title": "Speaks First",
"description": "Whether the digital human speaks first in the call"
}
},
"description": "Configuration for whether the digital human speaks first and how.\nStored as JSONB in Supabase (speaks_first_config)."
},
"BackgroundNoiseType": {
"enum": [
"none",
"office",
"talking",
"traffic",
"cafe",
"park",
"tv",
"noisy_restaurant",
"hospital",
"airport",
"birdsong",
"bus_station",
"car_interior",
"city_night",
"city_traffic",
"construction",
"driving",
"factory",
"hotel_lobby",
"hotel_restaurant",
"keyboard_typing",
"light_rain",
"night_insects",
"office_open_plan",
"playground",
"pub",
"quiet_home",
"rain",
"restaurant_busy",
"restaurant_party",
"road_traffic",
"school",
"shopping_centre",
"street",
"subway_station",
"subway_train",
"supermarket",
"thunderstorm",
"train_station",
"urban",
"urban_park",
"wind",
"kitchen",
"living_room",
"meeting_room",
"small_office",
"cafeteria",
"restaurant",
"town_square",
"bus_ride",
"babble_light",
"babble_crowd",
"custom"
],
"type": "string",
"title": "BackgroundNoiseType",
"description": "Enum for background noise options."
},
"DigitalHumanRequestData": {
"type": "object",
"title": "DigitalHumanRequestData",
"properties": {
"tag": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Tag",
"default": null,
"description": "Tag for categorizing the digital human"
},
"name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Name",
"default": null,
"description": "Name of the digital human"
},
"tags": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Tags",
"default": null,
"description": "Full tag list (takes precedence over `tag`). Free-form labels; use `type` for voicemail, replay and the other kinds."
},
"type": {
"anyOf": [
{
"$ref": "#/$defs/DigitalHumanType"
},
{
"type": "null"
}
],
"default": null,
"description": "What kind of digital human this is. Set it instead of putting sentinel values in tags; tags are free-form labels. Legacy sentinel tags (e.g. 'voicemail-custom', or 'transcript_generated' + 'smart') still set it when this is omitted."
},
"accent": {
"anyOf": [
{
"$ref": "#/$defs/AccentType"
},
{
"type": "null"
}
],
"default": null,
"description": "Accent of the digital human"
},
"gender": {
"anyOf": [
{
"$ref": "#/$defs/GenderType"
},
{
"type": "null"
}
],
"default": null,
"description": "Gender of the digital human"
},
"intent": {
"type": "string",
"title": "Intent",
"default": "",
"description": "The scenario the digital human enacts, in ONE OR TWO SENTENCES: what this caller wants, not how to behave. It fills one slot in a prompt that ALREADY renders traits, verbosity, fluency, a not-the-agent guardrail and end-of-call instructions, so restating those here is duplicate prompt. Anything shaped like 'if the agent says X, do Y' does not belong here — it belongs in a field, and prose makes it non-deterministic. Move it: case facts the agent may ask for (member ID, DOB, order number, policy number) to `traits`; lines that must be said verbatim, a keypad entry, or a deliberate pause to `scripted_responses`; who opens the call to `speaks_first_config`; language, accent, fluency, verbosity, background noise, audio quality, interruptions, hangup and silence behavior to their own fields; and lower `creativity` for repeatability. If you reach for 'correctly', 'appropriately' or 'successfully' you are describing what the AGENT should do — that goes in `success_criteria`, not here. Leave empty when enriched_playback is set; the agent uses playback instead."
},
"traits": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/Trait"
}
},
{
"type": "null"
}
],
"title": "Traits",
"description": "Case facts THIS CALLER holds and can recite when the agent asks — member ID, DOB, order number, policy number, zip. Each is an org-level trait (name + BOOLEAN/STRING/DATE/NUMBER type + value), so the same fact stays a stable fixture across the suite instead of a number the model invents mid-call. Traits are the determinism lever: any case-specific value mentioned in `intent` prose should be a trait instead. They are NOT a place for internal or agent-side information (what the CRM holds, what the agent should look up or say, expected tool arguments, notes for the grader) — the schema has no notion of an internal trait, and a caller cannot know those. Expected tool arguments go in `expected_tool_calls`; grading notes go in `success_criteria` or a custom metric."
},
"fluency": {
"anyOf": [
{
"$ref": "#/$defs/FluencyType"
},
{
"type": "null"
}
],
"default": "native",
"description": "Fluency level of the digital human's speech"
},
"language": {
"anyOf": [
{
"$ref": "#/$defs/LanguageType"
},
{
"type": "null"
}
],
"default": "en",
"description": "Language the digital human speaks"
},
"num_runs": {
"anyOf": [
{
"type": "integer",
"minimum": 1
},
{
"type": "null"
}
],
"title": "Num Runs",
"default": 1,
"description": "Number of times this digital human is run per simulation run (run count)."
},
"extension": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Extension",
"default": null,
"description": "Extension dialed as DTMF after connecting when this DH calls an inbound agent"
},
"test_name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Test Name",
"default": null,
"description": "User-facing label for this digital human"
},
"verbosity": {
"anyOf": [
{
"$ref": "#/$defs/VerbosityType"
},
{
"type": "null"
}
],
"default": "medium",
"description": "Verbosity level of the digital human's responses"
},
"creativity": {
"anyOf": [
{
"type": "number",
"maximum": 2,
"minimum": 0
},
{
"type": "null"
}
],
"title": "Creativity",
"default": 0.7,
"description": "Model temperature for the digital human's own speech. Lower it (0.0-0.3) when you want the same call twice — regression tests and anything you will compare run over run. Keep it near the 0.7 default for exploratory or red-team cases."
},
"attack_plan": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Attack Plan",
"default": null,
"description": "Crescendo escalation ladder {objective, breach_predicate, ladder}."
},
"attack_type": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Attack Type",
"default": null,
"description": "Umbrella attack category (recon | social_engineering | prompt_injection | audio_native)."
},
"tested_path": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Tested Path",
"default": null,
"description": "Ordered names of the workflow path steps this DH was generated from (Generate-From-Workflow only)."
},
"voice_speed": {
"anyOf": [
{
"$ref": "#/$defs/VoiceSpeedType"
},
{
"type": "null"
}
],
"default": "normal",
"description": "Speed of the digital human's voice"
},
"phone_number": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Phone Number",
"default": null,
"description": "Phone number for the digital human"
},
"attack_vector": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Attack Vector",
"default": null,
"description": "Attack tactic key from VECTOR_CATALOG. NULL for non-red-team."
},
"audio_quality": {
"anyOf": [
{
"$ref": "#/$defs/AudioQualityType"
},
{
"type": "null"
}
],
"default": "high",
"description": "Audio quality of the digital human's voice"
},
"interruptions": {
"anyOf": [
{
"$ref": "#/$defs/SimpleInterruptionConfig"
},
{
"$ref": "#/$defs/KeywordsInterruptionConfig"
},
{
"$ref": "#/$defs/ContextualInterruptionConfig"
},
{
"type": "null"
}
],
"title": "Interruptions",
"default": null,
"description": "Interruption configuration for the digital human"
},
"journey_steps": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/JourneyStep"
}
},
{
"type": "null"
}
],
"title": "Journey Steps",
"default": null
},
"always_on_mode": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Always On Mode",
"default": false,
"description": "Whether always-on mode is enabled"
},
"hangup_phrases": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Hangup Phrases",
"description": "Phrases that trigger hangup"
},
"workflow_v2_id": {
"anyOf": [
{
"type": "string",
"format": "uuid"
},
{
"type": "null"
}
],
"title": "Workflow V2 Id",
"default": null,
"description": "Source workflow_v2 UUID — set when this DH is generated from a workflow"
},
"allow_dtmf_tool": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Allow Dtmf Tool",
"default": true,
"description": "Allow the digital human to use the DTMF tool"
},
"custom_voice_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Custom Voice Id",
"default": null,
"description": "ElevenLabs voice_id of a cloned voice. When set, the agent speaks with this voice instead of the accent's stock voice (language/accent still drive prompts and STT)."
},
"silence_timeout": {
"anyOf": [
{
"type": "integer",
"minimum": 15
},
{
"type": "null"
}
],
"title": "Silence Timeout",
"default": null,
"description": "Silence timeout in seconds"
},
"always_on_active": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Always On Active",
"default": null,
"description": "When true, this DH actively receives calls on phone_number. Defaults to True when phone_number is set."
},
"background_noise": {
"anyOf": [
{
"$ref": "#/$defs/BackgroundNoiseType"
},
{
"type": "null"
}
],
"default": "none",
"description": "Type of background noise"
},
"livekit_metadata": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Livekit Metadata",
"default": null,
"description": "LiveKit-specific configuration and metadata for this digital human"
},
"role_description": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Role Description",
"default": null,
"description": "Who this caller is, in one short line (e.g. 'retiree on a family plan, not comfortable with phone menus'). It owns identity and disposition only. What they are calling about is `intent`; the facts they can recite are `traits`; how they sound is language/accent/fluency/verbosity. Never put internal or agent-side information here — the digital human only knows what a real caller would know."
},
"success_criteria": {
"type": "string",
"title": "Success Criteria",
"default": "",
"description": "The pass/fail condition for this one test, in ONE OR TWO observable outcomes the transcript can settle (e.g. 'the agent verified the member ID and booked a callback'). It is not a rubric: a scored checklist, a per-dimension score, or a condition you want graded on every call in the suite belongs in a custom metric (`create_custom_metrics`) attached to the simulation, not in this string. Describe the AGENT's outcome here, never the digital human's own actions — those are `intent`. Leave empty when enriched_playback is set; the agent uses playback instead."
},
"endpointing_delay": {
"anyOf": [
{
"type": "number"
},
{
"type": "null"
}
],
"title": "Endpointing Delay",
"default": 1.5,
"description": "Seconds the digital human waits before it replies. Named patience in the UI, and accepted under either name."
},
"enriched_playback": {
"anyOf": [
{
"type": "array",
"items": {
"type": "object",
"additionalProperties": true
}
},
{
"type": "null"
}
],
"title": "Enriched Playback",
"default": null,
"description": "Workflow playbook v2 (JSON list). Speech steps use type \"message\" only. User: intent and/or exact_message. Agent: criteria and/or exact_match_text."
},
"allow_silence_tool": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Allow Silence Tool",
"default": true,
"description": "Allow the digital human to use the silence tool"
},
"bluejay_as_code_id": {
"anyOf": [
{
"type": "string",
"format": "uuid"
},
{
"type": "null"
}
],
"title": "Bluejay As Code Id",
"default": null,
"description": "Stable code-addressable identifier"
},
"scripted_responses": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/ScriptedResponse"
}
},
{
"type": "null"
}
],
"title": "Scripted Responses",
"description": "The 'if the agent says X, the caller does Y' rules for this test, as data instead of prose. Reach for one whenever a reply must be identical every run: a verbatim line, a keypad entry (DTMF), or a deliberate silence. Each row pairs an agent utterance (`match_phrase`) with the response. Writing the same rule into `intent` makes it advisory; putting it here makes it deterministic."
},
"allow_end_call_tool": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Allow End Call Tool",
"default": true,
"description": "Allow the digital human to end the tool call"
},
"expected_tool_calls": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/ExpectedToolCall"
}
},
{
"type": "null"
}
],
"title": "Expected Tool Calls",
"description": "Expected tool call outputs"
},
"hangup_instructions": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Hangup Instructions",
"default": null,
"description": "Freeform instructions for how/when to hang up. The literal string \"default\" (or null) keeps the tuned built-in end-of-call behavior, which already handles ordinary goodbyes; any other string REPLACES it, so write one only for a condition the default would miss."
},
"original_transcript": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Original Transcript",
"default": null,
"description": "Original transcript text to replay. When provided (and formatted_transcript not provided), utterances are extracted via LLM and used as the intent."
},
"speaks_first_config": {
"anyOf": [
{
"$ref": "#/$defs/SpeaksFirstConfig"
},
{
"type": "null"
}
],
"default": null,
"description": "Who opens the call, and the caller's opening line when it must be fixed. Owns the opener so it does not have to be described in `intent`. Read the `dynamic` field before setting a custom message: on an agent that greets callers, a dynamic custom opener is discarded and never heard."
},
"workflow_path_index": {
"anyOf": [
{
"type": "integer",
"minimum": 0
},
{
"type": "null"
}
],
"title": "Workflow Path Index",
"default": null,
"description": "0-based path index within enumerate_workflow_v2_paths output"
},
"formatted_transcript": {
"anyOf": [
{
"type": "array",
"items": {
"type": "object",
"additionalProperties": {
"type": "string"
}
}
},
{
"type": "null"
}
],
"title": "Formatted Transcript",
"default": null,
"description": "Pre-computed structured transcript as [{role, utterance}]. When provided, skips the format-transcript LLM call."
},
"outbound_text_number": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Outbound Text Number",
"default": null,
"description": "Outbound text number"
},
"default_dtmf_or_voiced": {
"anyOf": [
{
"$ref": "#/$defs/DtmfOrVoicedType"
},
{
"type": "null"
}
],
"default": "voiced"
},
"system_prompt_rule_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "System Prompt Rule Ids",
"default": null,
"description": "Ids of the system-prompt rules this digital human covers, from generate."
},
"background_noise_volume": {
"anyOf": [
{
"type": "number",
"maximum": 1,
"minimum": 0
},
{
"type": "null"
}
],
"title": "Background Noise Volume",
"default": 0.8,
"description": "Volume of background noise"
},
"silence_tool_instructions": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Silence Tool Instructions",
"default": "default",
"description": "Tool instructions; use \"default\" for built-in behavior or custom text"
},
"system_prompt_rule_quotes": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "System Prompt Rule Quotes",
"default": null,
"description": "The quoted system-prompt rules this digital human covers, shown on its card."
},
"scripted_responses_ordered": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Scripted Responses Ordered",
"default": false,
"description": "When true, scripted_responses run as a script in list order: only the next unfired one is armed, each fires once, and a blank match_phrase fires on the digital human's next turn. When false (default) any scripted response fires whenever its match_phrase comes up."
},
"custom_background_noise_url": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Custom Background Noise Url",
"default": null,
"description": "Bucket-relative path of the uploaded custom background noise audio; required when background_noise is 'custom'"
},
"follow_up_sms_success_criteria": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Follow Up Sms Success Criteria",
"default": null,
"description": "Criteria the captured follow-up SMS is graded against"
}
},
"description": "Digital human data model for requests (without id and created_at)."
},
"SimpleInterruptionConfig": {
"type": "object",
"title": "Default",
"required": [
"type"
],
"properties": {
"type": {
"enum": [
"none",
"low",
"medium",
"high"
],
"type": "string",
"title": "Type",
"description": "Interruption level: none, low, medium, or high"
}
},
"description": "Simple interruption configuration with predefined levels."
},
"KeywordsInterruptionConfig": {
"type": "object",
"title": "Keywords",
"required": [
"type",
"keyword_responses"
],
"properties": {
"type": {
"type": "string",
"const": "keywords",
"title": "Type",
"description": "Type discriminator for keywords interruption (required)"
},
"keyword_responses": {
"type": "array",
"items": {
"$ref": "#/$defs/KeywordResponse"
},
"title": "Keyword Responses",
"description": "Array of keyword response objects, each with keyword, response, and optional probability"
}
},
"description": "Keywords-based interruption configuration."
},
"ContextualInterruptionConfig": {
"type": "object",
"title": "Contextual",
"required": [
"type",
"contextual_prompt"
],
"properties": {
"type": {
"type": "string",
"const": "contextual",
"title": "Type",
"description": "Type discriminator for contextual interruption"
},
"contextual_prompt": {
"type": "string",
"title": "Contextual Prompt",
"description": "Contextual prompt for LLM-based interruptions"
}
},
"description": "Contextual/LLM-based interruption configuration."
}
},
"title": "create_digital_humansArguments",
"required": [
"digital_humans"
],
"properties": {
"digital_humans": {
"type": "array",
"items": {
"$ref": "#/$defs/DigitalHumanRequestData"
},
"title": "Digital Humans"
},
"simulation_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "integer"
}
},
{
"type": "null"
}
],
"title": "Simulation Ids",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "create_digital_humansDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description97/100
Update one or many digital humans in ONE call (PUT /v1/update-digital-humans).
Pass a single-item list to update one. Each item is {digital_human_id, update}:
`digital_human_id` picks the row, `update` carries only the fields to change —
intent, success_criteria, traits, expected_tool_calls, voice settings,
simulation_ids. Omitted fields keep their stored values. Most list fields you
pass REPLACE rather than append. Traits are different: when you send traits,
traits_mode defaults to "merge" (change only the listed trait_name rows; read
traits with list_digital_humans first). Set traits_mode="replace" to delete
every stored trait and keep only the list you send. Duplicate digital_human_id
values are rejected.
Pass update.phone_number="" to clear an assigned number and turn off
always_on_active. On a 409 ALWAYS_ON_PHONE_CONFLICT, retry that item with
update.override_conflict=True to move the number off the conflicting digital human.
Returns updated_count, updated_ids and per-item errors; read one row back with
get_digital_human.
The description explains the capability, when to use it, and what to expect.
Inputs79/100
79 of 90 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
$defs › BulkDigitalHumanUpdate › digital_human_id
ID of the digital human to update
Clear enough to supply this argument.
$defs › UpdateDigitalHumanRequest › intent
The scenario the digital human enacts, in ONE OR TWO SENTENCES: what this caller wants, not how to behave. It fills one slot in a prompt that ALREADY renders traits, verbosity, fluency, a not-the-agent guardrail and end-of-call instructions, so restating those here is duplicate prompt. Anything shaped like 'if the agent says X, do Y' does not belong here — prose makes it non-deterministic. Move it: case facts the agent may ask for (member ID, DOB, order number) to `traits`; lines that must be said verbatim, a keypad entry, or a deliberate pause to `scripted_responses`; who opens the call to `speaks_first_config`; voice and call conditions to their own fields; and lower `creativity` for repeatability. If you reach for 'correctly', 'appropriately' or 'successfully' you are describing what the AGENT should do — that goes in `success_criteria`.
Clear enough to supply this argument.
$defs › SuccessCriterionInput › text
Not provided
Missing description. Explain what this value means and how to supply it.
$defs › SuccessCriterionInput › id
Not provided
Missing description. Explain what this value means and how to supply it.
$defs › UpdateDigitalHumanRequest › name
Name of the digital human
Clear enough to supply this argument.
$defs › UpdateDigitalHumanRequest › tag
Tag for categorizing the digital human
Clear enough to supply this argument.
$defs › UpdateDigitalHumanRequest › tags
Full tag list, replacing the current tags; [] clears them. Takes precedence over `tag`, where an empty string leaves tags unchanged.
Clear enough to supply this argument.
$defs › UpdateDigitalHumanRequest › type
What kind of digital human this is. Set it instead of putting sentinel values in tags; tags are free-form labels. Legacy sentinel tags (e.g. 'voicemail-custom', or 'transcript_generated' + 'smart') still set it when this is omitted.
Controls whether the agent submits numerical values via DTMF or voice. 'voiced' = speak numbers (default), 'dtmf' = use DTMF tones for eligible numerical inputs
Seconds the digital human waits before it replies. Named patience in the UI, and accepted under either name.
Clear enough to supply this argument.
$defs › UpdateDigitalHumanRequest › creativity
Model temperature for the digital human's own speech. Lower it (0.0-0.3) when you want the same call twice — regression tests and anything compared run over run. Keep near the 0.7 default for exploratory or red-team cases.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
Freeform instructions for how/when to hang up. Omit the field to leave the stored value alone; send the literal string "default" to reset to the tuned built-in end-of-call behavior, which already handles ordinary goodbyes. Any other string REPLACES it, so write one only for a condition the default would miss.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
Array of simulation IDs to associate with this digital human. If provided, completely replaces existing associations.
Clear enough to supply this argument.
$defs › Trait › trait_name
Name of the fact, as the agent would ask for it: 'member_id', 'date_of_birth', 'order_number'. Traits are org-level, so reuse the existing name across the suite rather than coining a variant. A trait is always something the CALLER knows and can say out loud — never internal or agent-side information (CRM contents, what the agent should look up or say, grader notes).
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › Trait › trait_data_type
BOOLEAN, STRING, DATE (ISO 8601 string) or NUMBER. Must match `value`, which is coerced to this type.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › Trait › value
The concrete value this caller gives (stored as JSONB). Fixing it here is what makes the call repeatable — leave it out of `intent` prose, where the model would improvise a different one each run.
Clear enough to supply this argument.
$defs › Trait › is_sip_header
Send this trait as a SIP header on the call instead of as something the caller says. Leave false for ordinary case facts.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › UpdateDigitalHumanRequest › traits_mode
How `traits` apply when you send traits on an update. Omitted or "merge" upserts only the listed traits by trait_name and keeps every other stored trait. "replace" deletes all stored traits first, then writes only the list — use this to remove traits or to set the full trait set from scratch.
Clear enough to supply this argument.
$defs › SimpleInterruptionConfig › type
Interruption level: none, low, medium, or high
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › KeywordsInterruptionConfig › type
Type discriminator for keywords interruption (required)
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › KeywordResponse › keyword
The keyword to listen for and interrupt on
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › KeywordResponse › response
Response to say when keyword is detected
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › KeywordResponse › probability
Probability of responding (0.0-1.0) - defaults to 1.0
How match_phrase is compared to the agent's turn. 'exact' is a fuzzy string comparison. Use it when you have the agent's literal line from a transcript, since it is stricter and costs no LLM call. 'context' asks an LLM whether the two utterances mean the same thing. Use it when the agent could phrase the same intent several ways.
Clear enough to supply this argument.
$defs › ScriptedResponse › match_phrase
An utterance the AGENT would say, which releases this response, e.g. 'Can I have your account number?'. Matching compares utterance to utterance, so a description of what the agent is doing ('the agent finished answering and is inviting another question') never matches anything: the rule saves and silently never fires. Write the line you expect to hear. Empty string is only meaningful when the digital human has scripted_responses_ordered set, where it fires on the digital human's next turn regardless of what the agent said.
Clear enough to supply this argument.
$defs › ScriptedResponse › response_type
Type of response: 'phrase', 'silence', 'dtmf', or 'audio'
Clear enough to supply this argument.
$defs › ScriptedResponse › response_value
The response text (required for 'phrase' and 'dtmf', optional for 'silence', unused for 'audio')
Skywatch bucket path of an uploaded audio file. AUDIO rows only — the agent downloads and plays this verbatim.
Clear enough to supply this argument.
$defs › ScriptedResponse › occurrence_mode
When to apply: 'always' or 'first_n'. Ignored when the digital human has scripted_responses_ordered set, where every step fires exactly once regardless.
Clear enough to supply this argument.
$defs › ScriptedResponse › occurrence_n
Number of times to apply (required if occurrence_mode is 'first_n', must be > 0)
Clear enough to supply this argument.
$defs › ScriptedResponse › silence_duration
Duration in seconds for silence period (only used when response_type is 'silence', must be > 0 if provided)
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
When true, scripted_responses run as a script in list order: only the next unfired one is armed, each fires once, and a blank match_phrase fires on the digital human's next turn. When false any scripted response fires whenever its match_phrase comes up.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
Who this caller is, in one short line. Identity and disposition only: what they are calling about is `intent`, the facts they can recite are `traits`, how they sound is language/accent/fluency/verbosity. Never internal or agent-side information — the digital human only knows what a real caller would know.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › speaks_first
Whether the digital human speaks first in the call
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › mode
When speaks_first is true: 'custom' (user-provided message) or 'ai_generated' (no message)
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › message
When mode is 'custom', the message the digital human says first
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › SpeaksFirstConfig › dynamic
When speaks_first is true: wait up to 5s for the agent to open; speak first only if it stays quiet. If the agent does open, the digital human yields and a mode='custom' message is DISCARDED, not spoken after the greeting, so on any agent that greets callers, a dynamic custom opener is never heard. Set false to speak it every time, at the top of the call and possibly over the greeting. Defaults on, so configs saved before this field existed become dynamic
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
Per-digital-human variables handed to the provider when it originates the call (Bland request_data, Vapi variableValues, Retell dynamic variables). Overrides the agent's template. If provided, completely replaces existing data; pass {} to clear.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
{
"name": "update_digital_humans",
"title": "Update digital humans",
"description": "Update one or many digital humans in ONE call (PUT /v1/update-digital-humans).\n\nPass a single-item list to update one. Each item is {digital_human_id, update}:\n`digital_human_id` picks the row, `update` carries only the fields to change —\nintent, success_criteria, traits, expected_tool_calls, voice settings,\nsimulation_ids. Omitted fields keep their stored values. Most list fields you\npass REPLACE rather than append. Traits are different: when you send traits,\ntraits_mode defaults to \"merge\" (change only the listed trait_name rows; read\ntraits with list_digital_humans first). Set traits_mode=\"replace\" to delete\nevery stored trait and keep only the list you send. Duplicate digital_human_id\nvalues are rejected.\n\nPass update.phone_number=\"\" to clear an assigned number and turn off\nalways_on_active. On a 409 ALWAYS_ON_PHONE_CONFLICT, retry that item with\nupdate.override_conflict=True to move the number off the conflicting digital human.\n\nReturns updated_count, updated_ids and per-item errors; read one row back with\nget_digital_human.\n",
"inputSchema": {
"type": "object",
"$defs": {
"Trait": {
"type": "object",
"title": "Trait",
"required": [
"trait_name",
"trait_data_type",
"value"
],
"properties": {
"value": {
"title": "Value",
"description": "The concrete value this caller gives (stored as JSONB). Fixing it here is what makes the call repeatable — leave it out of `intent` prose, where the model would improvise a different one each run."
},
"trait_name": {
"type": "string",
"title": "Trait Name",
"description": "Name of the fact, as the agent would ask for it: 'member_id', 'date_of_birth', 'order_number'. Traits are org-level, so reuse the existing name across the suite rather than coining a variant. A trait is always something the CALLER knows and can say out loud — never internal or agent-side information (CRM contents, what the agent should look up or say, grader notes)."
},
"is_sip_header": {
"type": "boolean",
"title": "Is Sip Header",
"default": false,
"description": "Send this trait as a SIP header on the call instead of as something the caller says. Leave false for ordinary case facts."
},
"trait_data_type": {
"$ref": "#/$defs/TraitDataType",
"description": "BOOLEAN, STRING, DATE (ISO 8601 string) or NUMBER. Must match `value`, which is coerced to this type."
}
},
"description": "Model for a single trait."
},
"MatchType": {
"enum": [
"exact",
"context"
],
"type": "string",
"title": "MatchType",
"description": "Enum for scripted response match types."
},
"AccentType": {
"enum": [
"multilingual",
"american",
"american2",
"mature",
"southern",
"italian",
"indian",
"british",
"australian",
"scottish",
"irish",
"welsh",
"mexican",
"spanish",
"portuguese",
"french",
"turkish",
"japanese",
"hindi",
"arabic",
"egyptian",
"levantine",
"hebrew",
"russian",
"chinese",
"german",
"korean",
"urdu",
"telugu",
"tamil",
"malayalam",
"kannada",
"marathi",
"gujarati",
"vietnamese",
"cantonese",
"tagalog",
"greek",
"autodetect",
"watson",
"watsonbritish",
"watsonaustralian",
"watsoncanadian"
],
"type": "string",
"title": "AccentType",
"description": "Enum for accent options."
},
"GenderType": {
"enum": [
"male",
"female"
],
"type": "string",
"title": "GenderType",
"description": "Enum for gender options."
},
"FluencyType": {
"enum": [
"beginner",
"intermediate",
"native"
],
"type": "string",
"title": "FluencyType",
"description": "Enum for fluency level options."
},
"JourneyStep": {
"type": "object",
"title": "JourneyStep",
"required": [
"step"
],
"properties": {
"step": {
"type": "integer",
"title": "Step",
"minimum": 0
},
"intent": {
"type": "string",
"title": "Intent",
"default": ""
},
"modality": {
"enum": [
"voice",
"sms"
],
"type": "string",
"title": "Modality",
"default": "voice"
},
"direction": {
"anyOf": [
{
"enum": [
"inbound",
"outbound"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Direction",
"default": null
},
"phone_number": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Phone Number",
"default": null
},
"unresponsive": {
"type": "boolean",
"title": "Unresponsive",
"default": false
},
"wait_seconds": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "Wait Seconds",
"default": null
},
"success_criteria": {
"type": "string",
"title": "Success Criteria",
"default": ""
},
"response_window_seconds": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "Response Window Seconds",
"default": null
}
}
},
"LanguageType": {
"enum": [
"en",
"es",
"pt",
"ja",
"tr",
"hi",
"ar",
"he",
"ru",
"zh",
"ml",
"fr",
"yue",
"vi",
"de",
"ko",
"ur",
"te",
"ta",
"mal",
"kn",
"mr",
"gu",
"tl",
"el",
"ad"
],
"type": "string",
"title": "LanguageType",
"description": "Enum for supported language types."
},
"ResponseType": {
"enum": [
"phrase",
"silence",
"dtmf",
"audio"
],
"type": "string",
"title": "ResponseType",
"description": "Enum for scripted response types."
},
"TraitDataType": {
"enum": [
"BOOLEAN",
"STRING",
"DATE",
"NUMBER"
],
"type": "string",
"title": "TraitDataType",
"description": "Enum for trait data types."
},
"VerbosityType": {
"enum": [
"low",
"medium",
"high"
],
"type": "string",
"title": "VerbosityType",
"description": "Enum for verbosity level options."
},
"OccurrenceMode": {
"enum": [
"always",
"first_n"
],
"type": "string",
"title": "OccurrenceMode",
"description": "Enum for scripted response occurrence modes."
},
"VoiceSpeedType": {
"enum": [
"slowest",
"slow",
"normal",
"fast",
"fastest"
],
"type": "string",
"title": "VoiceSpeedType",
"description": "Enum for voice speed options."
},
"KeywordResponse": {
"type": "object",
"title": "KeywordResponse",
"required": [
"keyword",
"response"
],
"properties": {
"keyword": {
"type": "string",
"title": "Keyword",
"description": "The keyword to listen for and interrupt on"
},
"response": {
"type": "string",
"title": "Response",
"description": "Response to say when keyword is detected"
},
"probability": {
"type": "number",
"title": "Probability",
"default": 1,
"maximum": 1,
"minimum": 0,
"description": "Probability of responding (0.0-1.0) - defaults to 1.0"
}
},
"description": "Model for a keyword response configuration."
},
"AudioQualityType": {
"enum": [
"high",
"medium",
"low",
"horrible"
],
"type": "string",
"title": "AudioQualityType",
"description": "Enum for audio quality options."
},
"DigitalHumanType": {
"enum": [
"voicemail_custom",
"voicemail_ai",
"replay_smart",
"replay_strict",
"red_team",
"scenario",
"workflow",
"persona",
"journey"
],
"type": "string",
"title": "DigitalHumanType",
"description": "What kind of digital human this is. Stored in test_cases.type; tags are free-form labels."
},
"DtmfOrVoicedType": {
"enum": [
"voiced",
"dtmf"
],
"type": "string",
"title": "DtmfOrVoicedType",
"description": "Enum for DTMF vs voiced input mode."
},
"ExpectedToolCall": {
"type": "object",
"title": "ExpectedToolCall",
"required": [
"name"
],
"properties": {
"name": {
"type": "string",
"title": "Name",
"description": "Name of the expected tool call"
},
"output": {
"anyOf": [
{},
{
"type": "null"
}
],
"title": "Output",
"default": null,
"description": "Expected output returned by the tool call"
},
"parameters": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Parameters",
"default": null,
"description": "Expected parameters passed to the tool call"
}
},
"description": "Represents an expected tool call during a conversation."
},
"ScriptedResponse": {
"type": "object",
"title": "ScriptedResponse",
"required": [
"match_type",
"match_phrase",
"response_type",
"occurrence_mode"
],
"properties": {
"match_type": {
"$ref": "#/$defs/MatchType",
"description": "How match_phrase is compared to the agent's turn. 'exact' is a fuzzy string comparison. Use it when you have the agent's literal line from a transcript, since it is stricter and costs no LLM call. 'context' asks an LLM whether the two utterances mean the same thing. Use it when the agent could phrase the same intent several ways."
},
"match_phrase": {
"type": "string",
"title": "Match Phrase",
"description": "An utterance the AGENT would say, which releases this response, e.g. 'Can I have your account number?'. Matching compares utterance to utterance, so a description of what the agent is doing ('the agent finished answering and is inviting another question') never matches anything: the rule saves and silently never fires. Write the line you expect to hear. Empty string is only meaningful when the digital human has scripted_responses_ordered set, where it fires on the digital human's next turn regardless of what the agent said."
},
"occurrence_n": {
"anyOf": [
{
"type": "integer",
"exclusiveMinimum": 0
},
{
"type": "null"
}
],
"title": "Occurrence N",
"default": null,
"description": "Number of times to apply (required if occurrence_mode is 'first_n', must be > 0)"
},
"response_type": {
"$ref": "#/$defs/ResponseType",
"description": "Type of response: 'phrase', 'silence', 'dtmf', or 'audio'"
},
"response_value": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Response Value",
"default": null,
"description": "The response text (required for 'phrase' and 'dtmf', optional for 'silence', unused for 'audio')"
},
"occurrence_mode": {
"$ref": "#/$defs/OccurrenceMode",
"description": "When to apply: 'always' or 'first_n'. Ignored when the digital human has scripted_responses_ordered set, where every step fires exactly once regardless."
},
"silence_duration": {
"anyOf": [
{
"type": "integer",
"exclusiveMinimum": 0
},
{
"type": "null"
}
],
"title": "Silence Duration",
"default": null,
"description": "Duration in seconds for silence period (only used when response_type is 'silence', must be > 0 if provided)"
},
"scripted_response_audio_snippet_url": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Scripted Response Audio Snippet Url",
"default": null,
"description": "Skywatch bucket path of an uploaded audio file. AUDIO rows only — the agent downloads and plays this verbatim."
}
},
"description": "Model for a scripted response configuration."
},
"SpeaksFirstConfig": {
"type": "object",
"title": "SpeaksFirstConfig",
"required": [
"speaks_first"
],
"properties": {
"mode": {
"anyOf": [
{
"enum": [
"custom",
"ai_generated"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Mode",
"default": null,
"description": "When speaks_first is true: 'custom' (user-provided message) or 'ai_generated' (no message)"
},
"dynamic": {
"type": "boolean",
"title": "Dynamic",
"default": true,
"description": "When speaks_first is true: wait up to 5s for the agent to open; speak first only if it stays quiet. If the agent does open, the digital human yields and a mode='custom' message is DISCARDED, not spoken after the greeting, so on any agent that greets callers, a dynamic custom opener is never heard. Set false to speak it every time, at the top of the call and possibly over the greeting. Defaults on, so configs saved before this field existed become dynamic"
},
"message": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Message",
"default": null,
"description": "When mode is 'custom', the message the digital human says first"
},
"speaks_first": {
"type": "boolean",
"title": "Speaks First",
"description": "Whether the digital human speaks first in the call"
}
},
"description": "Configuration for whether the digital human speaks first and how.\nStored as JSONB in Supabase (speaks_first_config)."
},
"BackgroundNoiseType": {
"enum": [
"none",
"office",
"talking",
"traffic",
"cafe",
"park",
"tv",
"noisy_restaurant",
"hospital",
"airport",
"birdsong",
"bus_station",
"car_interior",
"city_night",
"city_traffic",
"construction",
"driving",
"factory",
"hotel_lobby",
"hotel_restaurant",
"keyboard_typing",
"light_rain",
"night_insects",
"office_open_plan",
"playground",
"pub",
"quiet_home",
"rain",
"restaurant_busy",
"restaurant_party",
"road_traffic",
"school",
"shopping_centre",
"street",
"subway_station",
"subway_train",
"supermarket",
"thunderstorm",
"train_station",
"urban",
"urban_park",
"wind",
"kitchen",
"living_room",
"meeting_room",
"small_office",
"cafeteria",
"restaurant",
"town_square",
"bus_ride",
"babble_light",
"babble_crowd",
"custom"
],
"type": "string",
"title": "BackgroundNoiseType",
"description": "Enum for background noise options."
},
"SuccessCriterionInput": {
"type": "object",
"title": "SuccessCriterionInput",
"required": [
"text"
],
"properties": {
"id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Id",
"default": null
},
"text": {
"type": "string",
"title": "Text",
"minLength": 1
}
}
},
"BulkDigitalHumanUpdate": {
"type": "object",
"title": "BulkDigitalHumanUpdate",
"required": [
"digital_human_id",
"update"
],
"properties": {
"update": {
"$ref": "#/$defs/UpdateDigitalHumanRequest",
"description": "Only the fields to change on this digital human; everything omitted keeps its stored value"
},
"digital_human_id": {
"type": "integer",
"title": "Digital Human Id",
"description": "ID of the digital human to update"
}
}
},
"SimpleInterruptionConfig": {
"type": "object",
"title": "Default",
"required": [
"type"
],
"properties": {
"type": {
"enum": [
"none",
"low",
"medium",
"high"
],
"type": "string",
"title": "Type",
"description": "Interruption level: none, low, medium, or high"
}
},
"description": "Simple interruption configuration with predefined levels."
},
"UpdateDigitalHumanRequest": {
"type": "object",
"title": "UpdateDigitalHumanRequest",
"properties": {
"tag": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Tag",
"default": null,
"description": "Tag for categorizing the digital human"
},
"name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Name",
"default": null,
"description": "Name of the digital human"
},
"tags": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Tags",
"default": null,
"description": "Full tag list, replacing the current tags; [] clears them. Takes precedence over `tag`, where an empty string leaves tags unchanged."
},
"type": {
"anyOf": [
{
"$ref": "#/$defs/DigitalHumanType"
},
{
"type": "null"
}
],
"default": null,
"description": "What kind of digital human this is. Set it instead of putting sentinel values in tags; tags are free-form labels. Legacy sentinel tags (e.g. 'voicemail-custom', or 'transcript_generated' + 'smart') still set it when this is omitted."
},
"accent": {
"anyOf": [
{
"$ref": "#/$defs/AccentType"
},
{
"type": "null"
}
],
"default": null,
"description": "Accent of the digital human"
},
"gender": {
"anyOf": [
{
"$ref": "#/$defs/GenderType"
},
{
"type": "null"
}
],
"default": null,
"description": "Gender of the digital human"
},
"intent": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Intent",
"default": null,
"description": "The scenario the digital human enacts, in ONE OR TWO SENTENCES: what this caller wants, not how to behave. It fills one slot in a prompt that ALREADY renders traits, verbosity, fluency, a not-the-agent guardrail and end-of-call instructions, so restating those here is duplicate prompt. Anything shaped like 'if the agent says X, do Y' does not belong here — prose makes it non-deterministic. Move it: case facts the agent may ask for (member ID, DOB, order number) to `traits`; lines that must be said verbatim, a keypad entry, or a deliberate pause to `scripted_responses`; who opens the call to `speaks_first_config`; voice and call conditions to their own fields; and lower `creativity` for repeatability. If you reach for 'correctly', 'appropriately' or 'successfully' you are describing what the AGENT should do — that goes in `success_criteria`."
},
"traits": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/Trait"
}
},
{
"type": "null"
}
],
"title": "Traits",
"default": null,
"description": "Case facts THIS CALLER holds and can recite when the agent asks — member ID, DOB, order number, policy number, zip. Traits are the determinism lever: any case-specific value written into `intent` prose should be a trait instead. NOT a place for internal or agent-side information (what the CRM holds, what the agent should say or look up, expected tool arguments, grader notes) — a caller cannot know those, and the schema has no notion of an internal trait. If provided, updates the listed traits. Unlisted traits stay unless traits_mode is \"replace\". Call list_digital_humans or get_digital_human first to read stored traits."
},
"fluency": {
"anyOf": [
{
"$ref": "#/$defs/FluencyType"
},
{
"type": "null"
}
],
"default": null,
"description": "Fluency level of the digital human's speech"
},
"language": {
"anyOf": [
{
"$ref": "#/$defs/LanguageType"
},
{
"type": "null"
}
],
"default": null,
"description": "Language the digital human speaks"
},
"num_runs": {
"anyOf": [
{
"type": "integer",
"minimum": 1
},
{
"type": "null"
}
],
"title": "Num Runs",
"default": null,
"description": "Number of times this digital human is run per simulation run (run count)."
},
"extension": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Extension",
"default": null,
"description": "Extension dialed as DTMF after connecting when this DH calls an inbound agent. Send null or an empty string to clear it."
},
"test_name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Test Name",
"default": null,
"description": "User-facing label for this digital human"
},
"verbosity": {
"anyOf": [
{
"$ref": "#/$defs/VerbosityType"
},
{
"type": "null"
}
],
"default": null,
"description": "Verbosity level of the digital human's responses"
},
"creativity": {
"anyOf": [
{
"type": "number",
"maximum": 2,
"minimum": 0
},
{
"type": "null"
}
],
"title": "Creativity",
"default": null,
"description": "Model temperature for the digital human's own speech. Lower it (0.0-0.3) when you want the same call twice — regression tests and anything compared run over run. Keep near the 0.7 default for exploratory or red-team cases."
},
"attack_plan": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Attack Plan",
"default": null,
"description": "Crescendo escalation ladder {objective, breach_predicate, ladder}."
},
"attack_type": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Attack Type",
"default": null,
"description": "Umbrella attack category (recon | social_engineering | prompt_injection | audio_native)."
},
"tested_path": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Tested Path",
"default": null,
"description": "Ordered names of the workflow path steps this DH was generated from (Generate-From-Workflow only)."
},
"traits_mode": {
"anyOf": [
{
"enum": [
"replace",
"merge"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Traits Mode",
"default": null,
"description": "How `traits` apply when you send traits on an update. Omitted or \"merge\" upserts only the listed traits by trait_name and keeps every other stored trait. \"replace\" deletes all stored traits first, then writes only the list — use this to remove traits or to set the full trait set from scratch."
},
"voice_speed": {
"anyOf": [
{
"$ref": "#/$defs/VoiceSpeedType"
},
{
"type": "null"
}
],
"default": null,
"description": "Speed of the digital human's voice"
},
"phone_number": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Phone Number",
"default": null,
"description": "Phone number for the digital human"
},
"attack_vector": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Attack Vector",
"default": null,
"description": "Attack tactic key from VECTOR_CATALOG. NULL for non-red-team."
},
"audio_quality": {
"anyOf": [
{
"$ref": "#/$defs/AudioQualityType"
},
{
"type": "null"
}
],
"default": null,
"description": "Audio quality of the digital human's voice"
},
"interruptions": {
"anyOf": [
{
"$ref": "#/$defs/SimpleInterruptionConfig"
},
{
"$ref": "#/$defs/KeywordsInterruptionConfig"
},
{
"$ref": "#/$defs/ContextualInterruptionConfig"
},
{
"type": "null"
}
],
"title": "Interruptions",
"default": null,
"description": "Interruption configuration for the digital human. If provided, completely replaces existing interruption config."
},
"journey_steps": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/JourneyStep"
}
},
{
"type": "null"
}
],
"title": "Journey Steps",
"default": null,
"description": "Ordered journey steps. If provided, completely replaces existing journey steps."
},
"always_on_mode": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Always On Mode",
"default": null,
"description": "Whether always-on mode is enabled for this digital human"
},
"hangup_phrases": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Hangup Phrases",
"default": null,
"description": "Phrases that trigger hangup"
},
"simulation_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "integer"
}
},
{
"type": "null"
}
],
"title": "Simulation Ids",
"default": null,
"description": "Array of simulation IDs to associate with this digital human. If provided, completely replaces existing associations."
},
"workflow_v2_id": {
"anyOf": [
{
"type": "string",
"format": "uuid"
},
{
"type": "null"
}
],
"title": "Workflow V2 Id",
"default": null,
"description": "Source workflow_v2 UUID — set when this DH is generated from a workflow"
},
"allow_dtmf_tool": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Allow Dtmf Tool",
"default": null,
"description": "Allow the digital human to use the DTMF tool"
},
"custom_voice_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Custom Voice Id",
"default": null,
"description": "ElevenLabs voice_id of a cloned voice. Send empty string or null to clear and revert to the stock accent voice."
},
"silence_timeout": {
"anyOf": [
{
"type": "integer",
"minimum": 15
},
{
"type": "null"
}
],
"title": "Silence Timeout",
"default": null,
"description": "Silence timeout in seconds"
},
"always_on_active": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Always On Active",
"default": null,
"description": "When true, this DH actively receives calls on phone_number; when false, number is assigned but inactive"
},
"background_noise": {
"anyOf": [
{
"$ref": "#/$defs/BackgroundNoiseType"
},
{
"type": "null"
}
],
"default": null,
"description": "Type of background noise"
},
"livekit_metadata": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Livekit Metadata",
"default": null,
"description": "LiveKit-specific configuration and metadata for this digital human. If provided, completely replaces existing metadata."
},
"role_description": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Role Description",
"default": null,
"description": "Who this caller is, in one short line. Identity and disposition only: what they are calling about is `intent`, the facts they can recite are `traits`, how they sound is language/accent/fluency/verbosity. Never internal or agent-side information — the digital human only knows what a real caller would know."
},
"success_criteria": {
"anyOf": [
{
"type": "string"
},
{
"type": "array",
"items": {
"anyOf": [
{
"type": "string"
},
{
"$ref": "#/$defs/SuccessCriterionInput"
}
]
}
},
{
"type": "null"
}
],
"title": "Success Criteria",
"default": null,
"description": "The pass/fail condition for this one test. v1: a string. Also accepts [{id, text}, ...] — sending the field replaces the whole list."
},
"endpointing_delay": {
"anyOf": [
{
"type": "number"
},
{
"type": "null"
}
],
"title": "Endpointing Delay",
"default": null,
"description": "Seconds the digital human waits before it replies. Named patience in the UI, and accepted under either name."
},
"enriched_playback": {
"anyOf": [
{
"type": "array",
"items": {
"type": "object",
"additionalProperties": true
}
},
{
"type": "null"
}
],
"title": "Enriched Playback",
"default": null,
"description": "Optional enriched playback stored as JSONB: a list of turn objects"
},
"override_conflict": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Override Conflict",
"default": false,
"description": "When true, allows activation to replace an existing always-on active DH using the same phone number."
},
"allow_silence_tool": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Allow Silence Tool",
"default": null,
"description": "Allow the digital human to use the silence tool"
},
"scripted_responses": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/ScriptedResponse"
}
},
{
"type": "null"
}
],
"title": "Scripted Responses",
"default": null,
"description": "The 'if the agent says X, the caller does Y' rules for this test, as data instead of prose — a verbatim line, a keypad entry (DTMF), or a deliberate silence. Writing the same rule into `intent` makes it advisory; putting it here makes it deterministic. If provided, completely replaces existing scripted responses."
},
"allow_end_call_tool": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Allow End Call Tool",
"default": null,
"description": "Allow the digital human to end the tool call"
},
"expected_tool_calls": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/ExpectedToolCall"
}
},
{
"type": "null"
}
],
"title": "Expected Tool Calls",
"default": null,
"description": "Expected tool call outputs"
},
"hangup_instructions": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Hangup Instructions",
"default": null,
"description": "Freeform instructions for how/when to hang up. Omit the field to leave the stored value alone; send the literal string \"default\" to reset to the tuned built-in end-of-call behavior, which already handles ordinary goodbyes. Any other string REPLACES it, so write one only for a condition the default would miss."
},
"original_transcript": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Original Transcript",
"default": null,
"description": "Original transcript text. If changed from the current value, utterances are re-extracted and the intent is regenerated."
},
"speaks_first_config": {
"anyOf": [
{
"$ref": "#/$defs/SpeaksFirstConfig"
},
{
"type": "null"
}
],
"default": null,
"description": "Who opens the call, and the caller's opening line when it must be fixed — owns the opener so `intent` does not have to describe it. Read the `dynamic` field before setting a custom message: on an agent that greets callers, a dynamic custom opener is discarded. If provided, completely replaces existing speaks first config."
},
"workflow_path_index": {
"anyOf": [
{
"type": "integer",
"minimum": 0
},
{
"type": "null"
}
],
"title": "Workflow Path Index",
"default": null,
"description": "0-based path index within enumerate_workflow_v2_paths output"
},
"formatted_transcript": {
"anyOf": [
{
"type": "array",
"items": {
"type": "object",
"additionalProperties": {
"type": "string"
}
}
},
{
"type": "null"
}
],
"title": "Formatted Transcript",
"default": null,
"description": "Pre-computed structured transcript as [{role, utterance}]. When provided alongside original_transcript, skips the LLM formatting call."
},
"outbound_text_number": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Outbound Text Number",
"default": null,
"description": "Outbound text number"
},
"provider_request_data": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Provider Request Data",
"default": null,
"description": "Per-digital-human variables handed to the provider when it originates the call (Bland request_data, Vapi variableValues, Retell dynamic variables). Overrides the agent's template. If provided, completely replaces existing data; pass {} to clear."
},
"default_dtmf_or_voiced": {
"anyOf": [
{
"$ref": "#/$defs/DtmfOrVoicedType"
},
{
"type": "null"
}
],
"default": null,
"description": "Controls whether the agent submits numerical values via DTMF or voice. 'voiced' = speak numbers (default), 'dtmf' = use DTMF tones for eligible numerical inputs"
},
"system_prompt_rule_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "System Prompt Rule Ids",
"default": null,
"description": "Ids of the system-prompt rules this digital human covers, from generate."
},
"background_noise_volume": {
"anyOf": [
{
"type": "number",
"maximum": 1,
"minimum": 0
},
{
"type": "null"
}
],
"title": "Background Noise Volume",
"default": null,
"description": "Volume of background noise"
},
"silence_tool_instructions": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Silence Tool Instructions",
"default": null,
"description": "Tool instructions; set to \"default\" for built-in behavior or custom text"
},
"system_prompt_rule_quotes": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "System Prompt Rule Quotes",
"default": null,
"description": "The quoted system-prompt rules this digital human covers, shown on its card."
},
"scripted_responses_ordered": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Scripted Responses Ordered",
"default": null,
"description": "When true, scripted_responses run as a script in list order: only the next unfired one is armed, each fires once, and a blank match_phrase fires on the digital human's next turn. When false any scripted response fires whenever its match_phrase comes up."
},
"custom_background_noise_url": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Custom Background Noise Url",
"default": null,
"description": "Bucket-relative path of the uploaded custom background noise audio; required when background_noise is 'custom'"
},
"follow_up_sms_success_criteria": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Follow Up Sms Success Criteria",
"default": null,
"description": "Criteria the captured follow-up SMS is graded against"
}
},
"description": "Request model for updating a digital human — only provided fields are changed.\n\nEvery field must default to None: a non-None default gets filled in by Pydantic\non partial payloads and silently overwrites the stored value on every update\n(MCP, bluejay-as-code, and FE bulk edits all send partial payloads)."
},
"KeywordsInterruptionConfig": {
"type": "object",
"title": "Keywords",
"required": [
"type",
"keyword_responses"
],
"properties": {
"type": {
"type": "string",
"const": "keywords",
"title": "Type",
"description": "Type discriminator for keywords interruption (required)"
},
"keyword_responses": {
"type": "array",
"items": {
"$ref": "#/$defs/KeywordResponse"
},
"title": "Keyword Responses",
"description": "Array of keyword response objects, each with keyword, response, and optional probability"
}
},
"description": "Keywords-based interruption configuration."
},
"ContextualInterruptionConfig": {
"type": "object",
"title": "Contextual",
"required": [
"type",
"contextual_prompt"
],
"properties": {
"type": {
"type": "string",
"const": "contextual",
"title": "Type",
"description": "Type discriminator for contextual interruption"
},
"contextual_prompt": {
"type": "string",
"title": "Contextual Prompt",
"description": "Contextual prompt for LLM-based interruptions"
}
},
"description": "Contextual/LLM-based interruption configuration."
}
},
"title": "update_digital_humansArguments",
"required": [
"updates"
],
"properties": {
"updates": {
"type": "array",
"items": {
"$ref": "#/$defs/BulkDigitalHumanUpdate"
},
"title": "Updates"
}
}
},
"outputSchema": {
"type": "object",
"title": "update_digital_humansDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description89/100
Set simulation membership for up to 100 digital humans in ONE call.
Membership-only wrapper over update_digital_humans; replaces each digital
human's associations with exactly `simulation_ids`. Pass [] to detach from all.
Explain mutations, irreversible effects, or prerequisites that matter before calling this tool.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
digital_human_ids
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_ids
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description96/100
Every call one digital human has made, newest first, via Bluejay GET /v1/digital-human/{digital_human_id}/run-history.
Returns totals (simulations, simulation_runs, calls, passed, failed, success_rate) over all
calls, plus one page of calls with simulation, agent, run id, duration and outcome
(true passed, false failed, null not graded). limit max 1000; page with offset until
offset + limit >= totals.calls. Use get_simulation_result with a call_id for its transcript.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
digital_human_id
Not provided
Missing description. Explain what this value means and how to supply it.
limit
Not provided
Missing description. Explain what this value means and how to supply it.
offset
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema4/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description71/100
Batch-generate digital humans via Bluejay POST /v1/generate-digital-humans.
Generation quality is bounded by the agent context it reads, so make sure the agent's
description and workflow are accurate before leaning on this.
Three rules a good digital human follows (docs: /key-concepts/digital-humans/best-practices):
1. intent and success_criteria stay one or two sentences. Detail that grows them belongs
elsewhere: configuration for the caller, a custom metric for the grading.
2. Every "if the agent says X, the caller does Y" moves out of prose into a field —
traits for case facts the caller recites, scripted_responses for verbatim lines / DTMF /
silence, speaks_first_config for the opener, and lower creativity for repeatability.
3. Ground the case in the agent's real context (get_agent, get_workflow_summary) so the
scenario resembles a call this agent actually takes.
system_prompt generates from the agent version's locked prompt rules instead of a brief. Each
rule is tested from both sides, so full coverage is two digital humans per rule: one caller the
agent must help, one it must push back on. Pass an even number; a lower one covers fewer rules
rather than half-testing every rule.
The description explains the capability, when to use it, and what to expect.
Inputs48/100
12 of 23 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
count
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
prompt_id
Not provided
Missing description. Explain what this value means and how to supply it.
knowledge_base_id
Not provided
Missing description. Explain what this value means and how to supply it.
$defs › GoalAdherence › goal
Description of the goal
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › GoalAdherence › num_calls
Number of calls that adhered to the goal
Clear enough to supply this argument.
workflow_adherence
Not provided
Missing description. Explain what this value means and how to supply it.
$defs › ReplayTranscriptFromText › transcript
The transcript text to analyze and replay
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
Success criteria for the scenario (auto-generated if not provided)
Clear enough to supply this argument.
$defs › ReplayTranscriptFromConversation › mode
Mode for transcript replay: 'strict', 'smart' (default), or 'persona'
Clear enough to supply this argument.
load_testing
Not provided
Missing description. Explain what this value means and how to supply it.
system_prompt
Not provided
Missing description. Explain what this value means and how to supply it.
red_teaming
Not provided
Missing description. Explain what this value means and how to supply it.
$defs › Trait › trait_name
Name of the fact, as the agent would ask for it: 'member_id', 'date_of_birth', 'order_number'. Traits are org-level, so reuse the existing name across the suite rather than coining a variant. A trait is always something the CALLER knows and can say out loud — never internal or agent-side information (CRM contents, what the agent should look up or say, grader notes).
Clear enough to supply this argument.
$defs › Trait › trait_data_type
BOOLEAN, STRING, DATE (ISO 8601 string) or NUMBER. Must match `value`, which is coerced to this type.
Clear enough to supply this argument.
$defs › Trait › value
The concrete value this caller gives (stored as JSONB). Fixing it here is what makes the call repeatable — leave it out of `intent` prose, where the model would improvise a different one each run.
Clear enough to supply this argument.
$defs › Trait › is_sip_header
Send this trait as a SIP header on the call instead of as something the caller says. Leave false for ordinary case facts.
Clear enough to supply this argument.
num_runs
Not provided
Missing description. Explain what this value means and how to supply it.
language
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "generate_digital_humans",
"title": "Generate digital humans",
"description": "Batch-generate digital humans via Bluejay POST /v1/generate-digital-humans.\n\nGeneration quality is bounded by the agent context it reads, so make sure the agent's\ndescription and workflow are accurate before leaning on this.\n\nThree rules a good digital human follows (docs: /key-concepts/digital-humans/best-practices):\n1. intent and success_criteria stay one or two sentences. Detail that grows them belongs\n elsewhere: configuration for the caller, a custom metric for the grading.\n2. Every \"if the agent says X, the caller does Y\" moves out of prose into a field —\n traits for case facts the caller recites, scripted_responses for verbatim lines / DTMF /\n silence, speaks_first_config for the opener, and lower creativity for repeatability.\n3. Ground the case in the agent's real context (get_agent, get_workflow_summary) so the\n scenario resembles a call this agent actually takes.\n\nsystem_prompt generates from the agent version's locked prompt rules instead of a brief. Each\nrule is tested from both sides, so full coverage is two digital humans per rule: one caller the\nagent must help, one it must push back on. Pass an even number; a lower one covers fewer rules\nrather than half-testing every rule.\n",
"inputSchema": {
"type": "object",
"$defs": {
"Trait": {
"type": "object",
"title": "Trait",
"required": [
"trait_name",
"trait_data_type",
"value"
],
"properties": {
"value": {
"title": "Value",
"description": "The concrete value this caller gives (stored as JSONB). Fixing it here is what makes the call repeatable — leave it out of `intent` prose, where the model would improvise a different one each run."
},
"trait_name": {
"type": "string",
"title": "Trait Name",
"description": "Name of the fact, as the agent would ask for it: 'member_id', 'date_of_birth', 'order_number'. Traits are org-level, so reuse the existing name across the suite rather than coining a variant. A trait is always something the CALLER knows and can say out loud — never internal or agent-side information (CRM contents, what the agent should look up or say, grader notes)."
},
"is_sip_header": {
"type": "boolean",
"title": "Is Sip Header",
"default": false,
"description": "Send this trait as a SIP header on the call instead of as something the caller says. Leave false for ordinary case facts."
},
"trait_data_type": {
"$ref": "#/$defs/TraitDataType",
"description": "BOOLEAN, STRING, DATE (ISO 8601 string) or NUMBER. Must match `value`, which is coerced to this type."
}
},
"description": "Model for a single trait."
},
"GoalAdherence": {
"type": "object",
"title": "GoalAdherence",
"required": [
"goal",
"num_calls"
],
"properties": {
"goal": {
"type": "string",
"title": "Goal",
"description": "Description of the goal"
},
"num_calls": {
"type": "integer",
"title": "Num Calls",
"description": "Number of calls that adhered to the goal"
}
},
"description": "Goal adherence scenario for batch digital human generation."
},
"TraitDataType": {
"enum": [
"BOOLEAN",
"STRING",
"DATE",
"NUMBER"
],
"type": "string",
"title": "TraitDataType",
"description": "Enum for trait data types."
},
"ReplayTranscriptFromText": {
"type": "object",
"title": "Replay Transcript From Text",
"required": [
"transcript"
],
"properties": {
"mode": {
"enum": [
"strict",
"smart",
"persona"
],
"type": "string",
"title": "Mode",
"default": "smart",
"description": "Mode for transcript replay: 'strict', 'smart' (default), or 'persona'"
},
"transcript": {
"type": "string",
"title": "Transcript",
"description": "The transcript text to analyze and replay"
},
"success_criteria": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Success Criteria",
"default": null,
"description": "Success criteria for the scenario (auto-generated if not provided)"
}
},
"description": "Replay transcript by providing the transcript text directly."
},
"ReplayTranscriptFromConversation": {
"type": "object",
"title": "Replay Transcript From Conversation ID",
"required": [
"conversation_id"
],
"properties": {
"mode": {
"enum": [
"strict",
"smart",
"persona"
],
"type": "string",
"title": "Mode",
"default": "smart",
"description": "Mode for transcript replay: 'strict', 'smart' (default), or 'persona'"
},
"conversation_id": {
"type": "string",
"title": "Conversation Id",
"description": "ID of an existing conversation log to retrieve transcript from"
},
"success_criteria": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Success Criteria",
"default": null,
"description": "Success criteria for the scenario (auto-generated if not provided)"
}
},
"description": "Replay transcript by referencing an existing conversation ID."
}
},
"title": "generate_digital_humansArguments",
"required": [
"agent_id",
"count"
],
"properties": {
"count": {
"type": "integer",
"title": "Count"
},
"traits": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/Trait"
}
},
{
"type": "null"
}
],
"title": "Traits",
"default": null
},
"agent_id": {
"type": "string",
"title": "Agent Id"
},
"language": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Language",
"default": null
},
"num_runs": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "Num Runs",
"default": null
},
"prompt_id": {
"anyOf": [
{
"type": "string",
"format": "uuid"
},
{
"type": "null"
}
],
"title": "Prompt Id",
"default": null
},
"red_teaming": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "Red Teaming",
"default": null
},
"load_testing": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "Load Testing",
"default": null
},
"simulation_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Simulation Id",
"default": null
},
"system_prompt": {
"anyOf": [
{
"type": "integer"
},
{
"type": "null"
}
],
"title": "System Prompt",
"default": null
},
"goal_adherence": {
"anyOf": [
{
"type": "array",
"items": {
"$ref": "#/$defs/GoalAdherence"
}
},
{
"type": "null"
}
],
"title": "Goal Adherence",
"default": null
},
"knowledge_base_id": {
"anyOf": [
{
"type": "string",
"format": "uuid"
},
{
"type": "null"
}
],
"title": "Knowledge Base Id",
"default": null
},
"replay_transcript": {
"anyOf": [
{
"type": "array",
"items": {
"anyOf": [
{
"$ref": "#/$defs/ReplayTranscriptFromText"
},
{
"$ref": "#/$defs/ReplayTranscriptFromConversation"
}
]
}
},
{
"type": "null"
}
],
"title": "Replay Transcript",
"default": null
},
"workflow_adherence": {
"anyOf": [
{
"type": "object",
"additionalProperties": {
"type": "integer"
}
},
{
"type": "null"
}
],
"title": "Workflow Adherence",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "generate_digital_humansDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description91/100
Duplicate a digital human via Bluejay POST /v1/digital-human/{id}/duplicate.
Server-side full copy: cloned voice, custom/ambience background noise,
interruption + speaks-first configs, transcripts, audio quirks, traits,
scripted responses and expected tool calls are all preserved without
re-validation. The copy starts without a phone number and always-on
inactive — assign one with update_digital_humans(phone_number=...,
always_on_active=True). simulation_ids picks the copy's simulations;
omit to inherit the source's associations, pass [] for none. name
defaults to "<original> (Copy)".
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
digital_human_id
Not provided
Missing description. Explain what this value means and how to supply it.
name
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_ids
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description99/100
List digital humans in your organization via Bluejay GET /v1/digital-humans (paginated).
Digital humans are org-wide and exist independently of simulations, so the
default listing is every digital human in the org — use it to discover existing
ones before creating new ones. `simulation_id` narrows the listing to the
digital humans already attached to that one simulation; that filtered form
ignores page/page_size and returns only id/intent/success_criteria/traits per row.
`type` keeps only digital humans of that type, `tag` only those carrying that exact tag.
Otherwise returns per-DH summaries (with traits) plus total_count/page/total_pages; page
through until page == total_pages (page_size max 100). Use get_digital_human
for one DH's full config.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 5 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
page
Not provided
Missing description. Explain what this value means and how to supply it.
page_size
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
type
Not provided
Missing description. Explain what this value means and how to supply it.
tag
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema7/100
Declare the result fields and their types in the output schema.
{
"name": "list_digital_humans",
"title": "List digital humans",
"description": "List digital humans in your organization via Bluejay GET /v1/digital-humans (paginated).\n\nDigital humans are org-wide and exist independently of simulations, so the\ndefault listing is every digital human in the org — use it to discover existing\nones before creating new ones. `simulation_id` narrows the listing to the\ndigital humans already attached to that one simulation; that filtered form\nignores page/page_size and returns only id/intent/success_criteria/traits per row.\n`type` keeps only digital humans of that type, `tag` only those carrying that exact tag.\nOtherwise returns per-DH summaries (with traits) plus total_count/page/total_pages; page\nthrough until page == total_pages (page_size max 100). Use get_digital_human\nfor one DH's full config.\n",
"inputSchema": {
"type": "object",
"$defs": {
"DigitalHumanType": {
"enum": [
"voicemail_custom",
"voicemail_ai",
"replay_smart",
"replay_strict",
"red_team",
"scenario",
"workflow",
"persona",
"journey"
],
"type": "string",
"title": "DigitalHumanType",
"description": "What kind of digital human this is. Stored in test_cases.type; tags are free-form labels."
}
},
"title": "list_digital_humansArguments",
"properties": {
"tag": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Tag",
"default": null
},
"page": {
"type": "integer",
"title": "Page",
"default": 1
},
"type": {
"anyOf": [
{
"$ref": "#/$defs/DigitalHumanType"
},
{
"type": "null"
}
],
"default": null
},
"page_size": {
"type": "integer",
"title": "Page Size",
"default": 20
},
"simulation_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Simulation Id",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "list_digital_humansDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description85/100
List the valid language -> accent -> genders voice catalog for digital humans.
Call this before setting language/accent/gender on create_digital_humans or
update_digital_humans: those three fields must form a valid combination
(e.g. language "en" pairs with accent "american", not "mexican"). Static
catalog; access_token is unused but kept for tool-registration uniformity.
Describe the returned information so the agent knows whether it will answer the request.
Inputs100/100
This tool declares no inputs, so argument descriptions are not needed.
No input fields.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema6/100
Declare the result fields and their types in the output schema.
{
"name": "get_voice_options",
"title": "Get voice options",
"description": "List the valid language -> accent -> genders voice catalog for digital humans.\n\nCall this before setting language/accent/gender on create_digital_humans or\nupdate_digital_humans: those three fields must form a valid combination\n(e.g. language \"en\" pairs with accent \"american\", not \"mexican\"). Static\ncatalog; access_token is unused but kept for tool-registration uniformity.\n",
"inputSchema": {
"type": "object",
"title": "get_voice_optionsArguments",
"properties": {}
},
"outputSchema": {
"type": "object",
"title": "get_voice_optionsDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description97/100
Mint a signed upload URL via Bluejay POST /v1/custom-background-noises/upload-url.
Returns upload_url (HTTP PUT the raw MP3/WAV bytes to it, e.g.
curl -X PUT --upload-file noise.mp3 -H "Content-Type: audio/mpeg" <upload_url>)
and storage_path. After uploading, register the file with
create_custom_background_noise so digital humans can reference it.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
filename
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description89/100
Register an uploaded noise in the org library via Bluejay POST /v1/custom-background-noises.
storage_path comes from create_custom_background_noise_upload_url (upload the
audio there first). The registered storage_path is what a digital human's
custom_background_noise_url must be set to (with background_noise="custom").
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
name
Not provided
Missing description. Explain what this value means and how to supply it.
storage_path
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description84/100
List the org's custom background noise library via Bluejay GET /v1/custom-background-noises.
Each entry's storage_path is a valid custom_background_noise_url for
create_digital_humans / update_digital_humans with background_noise="custom".
Describe the returned information so the agent knows whether it will answer the request.
Inputs100/100
This tool declares no inputs, so argument descriptions are not needed.
No input fields.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema6/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description80/100
Queue a simulation run.
`channel` picks how the digital humans reach the agent, and which endpoint runs:
"voice" places phone/SIP calls (POST /v1/queue-simulation-run), "sms" sends text
messages over the SMS agent (POST /v1/queue-sms-simulation-run), "http_text"
drives the agent's HTTP text webhook (POST /v1/queue-http-text-simulation-run).
simulation_id, digital_human_ids, prompt_id, knowledge_base_id and
runs_per_digital_human apply on every channel. The dialing overrides
(phone_number, sip_uri, livekit_*, pipecat_*) are voice-only, and
terminate_overlapping_simulations is SMS-only; passing one on the wrong channel
is rejected rather than ignored.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 14 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
channel
Not provided
Missing description. Explain what this value means and how to supply it.
digital_human_ids
Not provided
Missing description. Explain what this value means and how to supply it.
prompt_id
Not provided
Missing description. Explain what this value means and how to supply it.
knowledge_base_id
Not provided
Missing description. Explain what this value means and how to supply it.
phone_number
Not provided
Missing description. Explain what this value means and how to supply it.
sip_uri
Not provided
Missing description. Explain what this value means and how to supply it.
livekit_agent_name
Not provided
Missing description. Explain what this value means and how to supply it.
livekit_metadata
Not provided
Missing description. Explain what this value means and how to supply it.
pipecat_agent_name
Not provided
Missing description. Explain what this value means and how to supply it.
pipecat_agent_configuration
Not provided
Missing description. Explain what this value means and how to supply it.
pipecat_room_properties
Not provided
Missing description. Explain what this value means and how to supply it.
terminate_overlapping_simulations
Not provided
Missing description. Explain what this value means and how to supply it.
runs_per_digital_human
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description73/100
Retrieve one page of a run's results via Bluejay GET /v1/retrieve-simulation-results/{simulation_run_id}.
`limit` is how many results to return (1-100) and `offset` how many to skip.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
simulation_run_id
Not provided
Missing description. Explain what this value means and how to supply it.
limit
Not provided
Missing description. Explain what this value means and how to supply it.
offset
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema6/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description94/100
Read what was actually said on one simulation conversation.
Returns the turns themselves — ``[{"speaker": ..., "utterance": ...}, ...]`` in spoken
order — so a transcript can be quoted or tabled without fetching a URL. `test_result_id`
is the `id` of a row from get_simulation_results.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
test_result_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema8/100
Declare the result fields and their types in the output schema.
{
"name": "get_simulation_transcript",
"title": "Get simulation transcript",
"description": "Read what was actually said on one simulation conversation.\n\nReturns the turns themselves — ``[{\"speaker\": ..., \"utterance\": ...}, ...]`` in spoken\norder — so a transcript can be quoted or tabled without fetching a URL. `test_result_id`\nis the `id` of a row from get_simulation_results.\n",
"inputSchema": {
"type": "object",
"title": "get_simulation_transcriptArguments",
"required": [
"test_result_id"
],
"properties": {
"test_result_id": {
"type": "string",
"title": "Test Result Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "get_simulation_transcriptDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description98/100
Count simulated conversations (each is one digital human's pass through a simulation run).
Returns `total` and `runs` (distinct simulation runs) for everything matching the filters.
Set group_by for counts per group, which is what a "how many" question about simulations needs:
- 'status': how they ended. Only COMPLETED ones carry a real verdict; NO_ANSWER, NO_CONNECTION,
SYSTEM_ERROR and the like never really happened, so report them apart.
- 'agent', 'simulation', 'run', 'digital_human', 'day': as named. Every group also carries `runs`,
so "how many simulation runs per agent" is group_by='agent', reading `runs`.
- 'metric_value' with metric_name: how one metric came out. The goal metric is usually named
'success'; its 'true' share of `total` is the pass rate. Not-applicable results are counted
apart and human corrections win, as in the app.
Filter with simulation_run_ids for one run, simulation_ids for one simulation (group_by='run' to
compare its runs) or agent_ids for one agent (group_by='simulation' for its simulations). Agent,
simulation and run groups come back with their `name`; runs also with `started_at`.
`last` is 1day, 3days, 7days, 30days, 90days or all, by when the conversation was created.
Left out, it is all time when a run, simulation or agent filter is set, otherwise the last 7
days; the response's `since` says which, so state the window you used. Get agent ids from
list_agents, simulation ids from list_simulations and run ids from get_simulation_runs. For one
run's conversations themselves, use get_simulation_results.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 8 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
status
Not provided
Missing description. Explain what this value means and how to supply it.
agent_ids
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_ids
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_run_ids
Not provided
Missing description. Explain what this value means and how to supply it.
group_by
Not provided
Missing description. Explain what this value means and how to supply it.
metric_name
Not provided
Missing description. Explain what this value means and how to supply it.
metric_id
Not provided
Missing description. Explain what this value means and how to supply it.
last
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema5/100
Declare the result fields and their types in the output schema.
{
"name": "list_simulated_conversations",
"title": "List simulated conversations",
"description": "\nCount simulated conversations (each is one digital human's pass through a simulation run).\n\nReturns `total` and `runs` (distinct simulation runs) for everything matching the filters.\nSet group_by for counts per group, which is what a \"how many\" question about simulations needs:\n\n- 'status': how they ended. Only COMPLETED ones carry a real verdict; NO_ANSWER, NO_CONNECTION,\n SYSTEM_ERROR and the like never really happened, so report them apart.\n- 'agent', 'simulation', 'run', 'digital_human', 'day': as named. Every group also carries `runs`,\n so \"how many simulation runs per agent\" is group_by='agent', reading `runs`.\n- 'metric_value' with metric_name: how one metric came out. The goal metric is usually named\n 'success'; its 'true' share of `total` is the pass rate. Not-applicable results are counted\n apart and human corrections win, as in the app.\n\nFilter with simulation_run_ids for one run, simulation_ids for one simulation (group_by='run' to\ncompare its runs) or agent_ids for one agent (group_by='simulation' for its simulations). Agent,\nsimulation and run groups come back with their `name`; runs also with `started_at`.\n\n`last` is 1day, 3days, 7days, 30days, 90days or all, by when the conversation was created.\nLeft out, it is all time when a run, simulation or agent filter is set, otherwise the last 7\ndays; the response's `since` says which, so state the window you used. Get agent ids from\nlist_agents, simulation ids from list_simulations and run ids from get_simulation_runs. For one\nrun's conversations themselves, use get_simulation_results.\n",
"inputSchema": {
"type": "object",
"title": "list_simulated_conversationsArguments",
"properties": {
"last": {
"anyOf": [
{
"enum": [
"1day",
"3days",
"7days",
"30days",
"90days",
"all"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Last",
"default": null
},
"status": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Status",
"default": null
},
"group_by": {
"anyOf": [
{
"enum": [
"status",
"agent",
"simulation",
"run",
"digital_human",
"day",
"metric_value"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Group By",
"default": null
},
"agent_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "integer"
}
},
{
"type": "null"
}
],
"title": "Agent Ids",
"default": null
},
"metric_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Metric Id",
"default": null
},
"metric_name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Metric Name",
"default": null
},
"simulation_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "integer"
}
},
{
"type": "null"
}
],
"title": "Simulation Ids",
"default": null
},
"simulation_run_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "integer"
}
},
{
"type": "null"
}
],
"title": "Simulation Run Ids",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "list_simulated_conversationsDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description85/100
List all dashboards in the organization, each with the 'url' that opens it in the app.
Optionally filter by data_type ('observability' or 'simulation').
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
data_type
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema7/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description96/100
Create an empty dashboard, then fill it with widgets. Returns 'url', the link to give the
user. Never construct that link yourself; simulation and observability dashboards live on
different pages.
data_type is 'observability' (live calls) or 'simulation' (test runs).
A dashboard is only useful if its widgets answer different questions. Aim for six, and do not
stop at two variations of call count. Cover volume over time, outcome quality, latency,
and at least one breakdown that splits the same data by a dimension. Call list_custom_metrics,
list_labels, list_agents and list_simulations first so the widgets use what this org actually
records. A workable default, dropping any part the org has no data for:
1. call volume over time (line, metric 'call_count', time_bucket 'day')
2. volume split by agent or label (bar, group_by 'agent' or 'labels')
3. pass rate per custom metric (bar, metric 'custom_metric', aggregation 'breakdown')
4. goal completion (bar or pie, metric 'goal')
5. latency percentiles (line, metric 'latency', aggregation ['p50','p90','p95'])
6. a KPI or table for the single number or row list the user cares most about
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
name
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
data_type
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "create_dashboard",
"title": "Create dashboard",
"description": "Create an empty dashboard, then fill it with widgets. Returns 'url', the link to give the\nuser. Never construct that link yourself; simulation and observability dashboards live on\ndifferent pages.\n\ndata_type is 'observability' (live calls) or 'simulation' (test runs).\n\nA dashboard is only useful if its widgets answer different questions. Aim for six, and do not\nstop at two variations of call count. Cover volume over time, outcome quality, latency,\nand at least one breakdown that splits the same data by a dimension. Call list_custom_metrics,\nlist_labels, list_agents and list_simulations first so the widgets use what this org actually\nrecords. A workable default, dropping any part the org has no data for:\n 1. call volume over time (line, metric 'call_count', time_bucket 'day')\n 2. volume split by agent or label (bar, group_by 'agent' or 'labels')\n 3. pass rate per custom metric (bar, metric 'custom_metric', aggregation 'breakdown')\n 4. goal completion (bar or pie, metric 'goal')\n 5. latency percentiles (line, metric 'latency', aggregation ['p50','p90','p95'])\n 6. a KPI or table for the single number or row list the user cares most about\n",
"inputSchema": {
"type": "object",
"title": "create_dashboardArguments",
"required": [
"name"
],
"properties": {
"name": {
"type": "string",
"title": "Name"
},
"data_type": {
"type": "string",
"title": "Data Type",
"default": "observability"
},
"description": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Description",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "create_dashboardDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description74/100
Set widget positions on a dashboard. Widgets that are not on this dashboard are ignored. layouts is a list of
{"widget_id": "<uuid>", "layout": {"x": <row, 1-based>, "y": <column 1-6>, "w": <width in columns 1-6>, "h": <height in 50px steps, 2-18>}}.
The names are older than the grid: x is the row and y is the column. The dashboard is six
columns wide, and h counts 50px steps, so h=6 is 300px and the range 2..18 is 100px..900px.
Explain mutations, irreversible effects, or prerequisites that matter before calling this tool.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
dashboard_id
Not provided
Missing description. Explain what this value means and how to supply it.
layouts
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "update_dashboard_layout",
"title": "Update dashboard layout",
"description": "Set widget positions on a dashboard. Widgets that are not on this dashboard are ignored. layouts is a list of\n{\"widget_id\": \"<uuid>\", \"layout\": {\"x\": <row, 1-based>, \"y\": <column 1-6>, \"w\": <width in columns 1-6>, \"h\": <height in 50px steps, 2-18>}}.\n\nThe names are older than the grid: x is the row and y is the column. The dashboard is six\ncolumns wide, and h counts 50px steps, so h=6 is 300px and the range 2..18 is 100px..900px.",
"inputSchema": {
"type": "object",
"title": "update_dashboard_layoutArguments",
"required": [
"dashboard_id",
"layouts"
],
"properties": {
"layouts": {
"type": "array",
"items": {
"type": "object",
"additionalProperties": true
},
"title": "Layouts"
},
"dashboard_id": {
"type": "string",
"title": "Dashboard Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "update_dashboard_layoutDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description81/100
Create a widget (a chart configuration) on a dashboard. A widget belongs to exactly one
dashboard; to show the same chart on two dashboards, create it twice or use duplicate_widget.
chart_type: 'line' | 'bar' | 'pie' | 'table' | 'kpi' | 'pivot_table' | 'histogram'.
metrics: required unless chart_type='table'; each item is
{"metric": "<key>", "custom_metric_id"?, "goal"?, "tool_call_id"?, "metadata_path"?, "metadata_type"?}
where metric keys include 'call_count', 'latency', 'custom_metric', 'goal', 'tool_call', 'trace_attribute'.
chart_mode: 'time_series' | 'categorical'. aggregation items: 'count', 'average', 'sum',
'percent_of_total', 'p50', 'p90', 'p95', 'p99', 'percentiles', 'breakdown'.
time_bucket: 'hour' | 'day' | 'week' | 'month'. group_by: 'agent' | 'labels' | 'tool_call' |
'age' | 'gender' | 'simulation' (simulation requires simulation_ids), or
'metadata:<path>' for one series per value of a conversation metadata field.
filters restrict which conversations any widget counts, on top of the dashboard's
agents/labels/time range; each item is a logs-page filter object.
column_visibility applies to table + observability widgets only.
color_overrides: {"<label the chart draws>": "#rrggbb"} for a series or slice; labels are
matched case-insensitively and omitted labels keep the default palette.
center_label: pie only, {"slice": "<label>", "clamp_pct": <0..50 exclusive>, "label": "<caption>"}.
slice omitted uses the largest slice; clamp_pct collapses the rounding edges, so 1 turns
99.6% into ">99%" and 0.4% into "<1%". On a numeric line or bar chart or a histogram, {"benchmark": <number>}
draws a dashed reference line at that value. On a KPI, {"compare_previous": false} hides the
change against the previous period. {"unit": "pts"} is shown after values on metrics that
have no unit of their own.
show_legend: draw the colour key under the chart (pie, bar and line). Defaults to true.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 18 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
name
Not provided
Missing description. Explain what this value means and how to supply it.
chart_type
Not provided
Missing description. Explain what this value means and how to supply it.
dashboard_id
Not provided
Missing description. Explain what this value means and how to supply it.
metrics
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
chart_mode
Not provided
Missing description. Explain what this value means and how to supply it.
data_type
Not provided
Missing description. Explain what this value means and how to supply it.
bar_mode
Not provided
Missing description. Explain what this value means and how to supply it.
aggregation
Not provided
Missing description. Explain what this value means and how to supply it.
time_bucket
Not provided
Missing description. Explain what this value means and how to supply it.
group_by
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_ids
Not provided
Missing description. Explain what this value means and how to supply it.
show_indeterminate
Not provided
Missing description. Explain what this value means and how to supply it.
filters
Not provided
Missing description. Explain what this value means and how to supply it.
column_visibility
Not provided
Missing description. Explain what this value means and how to supply it.
color_overrides
Not provided
Missing description. Explain what this value means and how to supply it.
center_label
Not provided
Missing description. Explain what this value means and how to supply it.
show_legend
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description82/100
Replace a widget's configuration and metrics (full replace, same field semantics as create_widget).
Always send the complete desired config — metrics replace the existing set. data_type cannot change.
color_overrides, center_label and show_legend are the exception: omit one and the widget keeps
what it already has.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 17 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
widget_id
Not provided
Missing description. Explain what this value means and how to supply it.
name
Not provided
Missing description. Explain what this value means and how to supply it.
chart_type
Not provided
Missing description. Explain what this value means and how to supply it.
metrics
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
chart_mode
Not provided
Missing description. Explain what this value means and how to supply it.
bar_mode
Not provided
Missing description. Explain what this value means and how to supply it.
aggregation
Not provided
Missing description. Explain what this value means and how to supply it.
time_bucket
Not provided
Missing description. Explain what this value means and how to supply it.
group_by
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_ids
Not provided
Missing description. Explain what this value means and how to supply it.
show_indeterminate
Not provided
Missing description. Explain what this value means and how to supply it.
filters
Not provided
Missing description. Explain what this value means and how to supply it.
column_visibility
Not provided
Missing description. Explain what this value means and how to supply it.
color_overrides
Not provided
Missing description. Explain what this value means and how to supply it.
center_label
Not provided
Missing description. Explain what this value means and how to supply it.
show_legend
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description89/100
Duplicate a widget ('Copy of <name>') with its metrics onto dashboard_id, which may be a
different dashboard from the one the source widget is on. The copy is independent of the source.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
widget_id
Not provided
Missing description. Explain what this value means and how to supply it.
dashboard_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description86/100
Create one or many custom metrics in ONE call (POST /v1/create-custom-metrics).
Pass a single-item list to create one. Each item is a full metric definition;
response_type decides which of min_value/max_value, enum_options and json_schema
are required. Returns the created metrics.
Describe the returned information so the agent knows whether it will answer the request.
Inputs93/100
Input documentation gives an agent enough context to populate the arguments.
$defs › NewCustomMetric › name
Metric name, shown in results and dashboards
Clear enough to supply this argument.
$defs › NewCustomMetric › prompt
The LLM judge's instruction: what to look for in the conversation; omit for a metric_type that does not judge
Clear enough to supply this argument.
$defs › NewCustomMetric › response_type
Verdict shape the judge must return (pass_fail, quantitative, enum, json, ...)
Clear enough to supply this argument.
$defs › NewCustomMetric › agent_ids
Agents this metric is evaluated on; omit to leave it unattached
Clear enough to supply this argument.
$defs › NewCustomMetric › min_value
Low end of the score range; required when response_type is quantitative
Clear enough to supply this argument.
$defs › NewCustomMetric › max_value
High end of the score range; required when response_type is quantitative
Clear enough to supply this argument.
$defs › NewCustomMetric › enum_options
The allowed verdict strings; required when response_type is enum
Clear enough to supply this argument.
$defs › NewCustomMetric › json_schema
Schema of the object the judge must return; required when response_type is json
Clear enough to supply this argument.
$defs › NewCustomMetric › metric_type
Metric kind; omit for llm_judge. Set 'tool_call' to check for tool_names instead of judging, 'trace_span' to pass when the linked OpenTelemetry trace contains every span in settings.span_names (or none of them, with settings.condition 'does_not_contain'), or 'transfer_landed' to prove a handoff reached one of your digital humans
Clear enough to supply this argument.
$defs › NewCustomMetric › settings
Type-specific and gating configuration. Per-type keys such as the pattern a transcript_regex metric matches, a trace_span metric's {"span_names": [<span names to look for>], "condition": "contains" (default) | "does_not_contain"}, or a transfer_landed metric's {"receiver_test_case_id": <the digital human that answers the transferred call, a positive id and the only required key>, "window_seconds": <optional, how late that call may land, default 180, at most 900>}, plus two that any type accepts. `fire_conditions` evaluates the metric only when the conversation matches: {"join": "and"|"or", "groups": [{"join": ..., "conditions": [{"type": "metric", "metric_id": ..., "operator": "equals"|"greater_than"|..., "value": ...} | {"type": "tool_call", "tool_name": ...} | {"type": "workflow_node", "node_id": ...}]}]}. `composite` computes this metric from other metrics' results, with metric_type="composite" and no prompt: {"output_type": "quantitative"|"categorical", "variables": [{"metric_id": ..., "value_map": {label: number}}], "master_formula": ..., "rules": [{"output": ..., "conditions": {...}}]}, where master_formula is the one expression read for a quantitative output and rules are read for a categorical one, and value_map turns a categorical or boolean input into the number the formula can use. A formula reads each declared metric by its id in double quotes, e.g. round(100 * ("<metric id>" / 5)); a bare name is refused, and a rule condition names the metric_id it compares the same way. Every metric a gate or a composite reads must be one that always evaluates: referencing a composite, or a metric with its own fire conditions, is rejected because it may have no result to read.
Clear enough to supply this argument.
$defs › NewCustomMetric › tool_names
Tool names a tool_call metric checks for; requires metric_type='tool_call'
Clear enough to supply this argument.
$defs › NewCustomMetric › category
Grouping label used to organize metrics in the UI
Clear enough to supply this argument.
$defs › NewCustomMetric › tags
Free-form tags for filtering metrics
Clear enough to supply this argument.
$defs › NewCustomMetric › scoring_guidance
Extra rubric text appended to the judge prompt, e.g. how to weigh partial credit
Clear enough to supply this argument.
$defs › NewCustomMetric › eval_route
Which judge lane evaluates this metric: AUTO, TEXT (transcript) or AUDIO (recording)
Clear enough to supply this argument.
$defs › NewCustomMetric › model
Text judge model override; omit for gpt-6-luna
Clear enough to supply this argument.
$defs › NewCustomMetric › audio_model
Audio judge model override; omit for the org default
Clear enough to supply this argument.
$defs › NewCustomMetric › temperature
Judge sampling temperature
Clear enough to supply this argument.
$defs › NewCustomMetric › allow_not_applicable
When true the judge may answer not_applicable instead of forcing a verdict
Clear enough to supply this argument.
$defs › NewCustomMetric › template_id
Library template this metric is created from
Clear enough to supply this argument.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "create_custom_metrics",
"title": "Create custom metrics",
"description": "Create one or many custom metrics in ONE call (POST /v1/create-custom-metrics).\n\nPass a single-item list to create one. Each item is a full metric definition;\nresponse_type decides which of min_value/max_value, enum_options and json_schema\nare required. Returns the created metrics.\n",
"inputSchema": {
"type": "object",
"$defs": {
"EvalRoute": {
"enum": [
"AUDIO",
"TEXT",
"AUTO"
],
"type": "string",
"title": "EvalRoute",
"description": "Enum representing the evaluation route of a call."
},
"ResponseType": {
"enum": [
"pass_fail",
"yes_no",
"qualitative",
"quantitative",
"json",
"enum",
"int",
"float",
"boolean",
"tool_call"
],
"type": "string",
"title": "ResponseType",
"description": "Enum representing the possible response types for custom metrics."
},
"NewCustomMetric": {
"type": "object",
"title": "NewCustomMetric",
"required": [
"name",
"response_type"
],
"properties": {
"name": {
"type": "string",
"title": "Name",
"description": "Metric name, shown in results and dashboards"
},
"tags": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Tags",
"default": null,
"description": "Free-form tags for filtering metrics"
},
"model": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Model",
"default": null,
"description": "Text judge model override; omit for gpt-6-luna"
},
"prompt": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Prompt",
"default": null,
"description": "The LLM judge's instruction: what to look for in the conversation; omit for a metric_type that does not judge"
},
"category": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Category",
"default": null,
"description": "Grouping label used to organize metrics in the UI"
},
"settings": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Settings",
"default": null,
"description": "Type-specific and gating configuration. Per-type keys such as the pattern a transcript_regex metric matches, a trace_span metric's {\"span_names\": [<span names to look for>], \"condition\": \"contains\" (default) | \"does_not_contain\"}, or a transfer_landed metric's {\"receiver_test_case_id\": <the digital human that answers the transferred call, a positive id and the only required key>, \"window_seconds\": <optional, how late that call may land, default 180, at most 900>}, plus two that any type accepts. `fire_conditions` evaluates the metric only when the conversation matches: {\"join\": \"and\"|\"or\", \"groups\": [{\"join\": ..., \"conditions\": [{\"type\": \"metric\", \"metric_id\": ..., \"operator\": \"equals\"|\"greater_than\"|..., \"value\": ...} | {\"type\": \"tool_call\", \"tool_name\": ...} | {\"type\": \"workflow_node\", \"node_id\": ...}]}]}. `composite` computes this metric from other metrics' results, with metric_type=\"composite\" and no prompt: {\"output_type\": \"quantitative\"|\"categorical\", \"variables\": [{\"metric_id\": ..., \"value_map\": {label: number}}], \"master_formula\": ..., \"rules\": [{\"output\": ..., \"conditions\": {...}}]}, where master_formula is the one expression read for a quantitative output and rules are read for a categorical one, and value_map turns a categorical or boolean input into the number the formula can use. A formula reads each declared metric by its id in double quotes, e.g. round(100 * (\"<metric id>\" / 5)); a bare name is refused, and a rule condition names the metric_id it compares the same way. Every metric a gate or a composite reads must be one that always evaluates: referencing a composite, or a metric with its own fire conditions, is rejected because it may have no result to read."
},
"agent_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Agent Ids",
"default": null,
"description": "Agents this metric is evaluated on; omit to leave it unattached"
},
"max_value": {
"anyOf": [
{
"type": "number"
},
{
"type": "null"
}
],
"title": "Max Value",
"default": null,
"description": "High end of the score range; required when response_type is quantitative"
},
"min_value": {
"anyOf": [
{
"type": "number"
},
{
"type": "null"
}
],
"title": "Min Value",
"default": null,
"description": "Low end of the score range; required when response_type is quantitative"
},
"eval_route": {
"anyOf": [
{
"$ref": "#/$defs/EvalRoute"
},
{
"type": "null"
}
],
"default": null,
"description": "Which judge lane evaluates this metric: AUTO, TEXT (transcript) or AUDIO (recording)"
},
"tool_names": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Tool Names",
"default": null,
"description": "Tool names a tool_call metric checks for; requires metric_type='tool_call'"
},
"audio_model": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Audio Model",
"default": null,
"description": "Audio judge model override; omit for the org default"
},
"json_schema": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Json Schema",
"default": null,
"description": "Schema of the object the judge must return; required when response_type is json"
},
"metric_type": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Metric Type",
"default": null,
"description": "Metric kind; omit for llm_judge. Set 'tool_call' to check for tool_names instead of judging, 'trace_span' to pass when the linked OpenTelemetry trace contains every span in settings.span_names (or none of them, with settings.condition 'does_not_contain'), or 'transfer_landed' to prove a handoff reached one of your digital humans"
},
"temperature": {
"anyOf": [
{
"type": "number"
},
{
"type": "null"
}
],
"title": "Temperature",
"default": null,
"description": "Judge sampling temperature"
},
"template_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Template Id",
"default": null,
"description": "Library template this metric is created from"
},
"enum_options": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Enum Options",
"default": null,
"description": "The allowed verdict strings; required when response_type is enum"
},
"response_type": {
"$ref": "#/$defs/ResponseType",
"description": "Verdict shape the judge must return (pass_fail, quantitative, enum, json, ...)"
},
"scoring_guidance": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Scoring Guidance",
"default": null,
"description": "Extra rubric text appended to the judge prompt, e.g. how to weigh partial credit"
},
"allow_not_applicable": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Allow Not Applicable",
"default": null,
"description": "When true the judge may answer not_applicable instead of forcing a verdict"
}
},
"description": "One metric definition for create_custom_metrics."
}
},
"title": "create_custom_metricsArguments",
"required": [
"metrics"
],
"properties": {
"metrics": {
"type": "array",
"items": {
"$ref": "#/$defs/NewCustomMetric"
},
"title": "Metrics"
}
}
},
"outputSchema": {
"type": "object",
"title": "create_custom_metricsDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description83/100
List custom metrics via GET /v1/custom-metrics.
`agent_id` narrows the listing to the metrics attached to that one agent; omit
it for every metric in the org. page/page_size are 1-based pagination.
`source` ("custom" = the org's own, "standard" = Bluejay's builtins) filters the
org-wide listing; omit it for both. `total_count` is the number of matching
metrics across all pages, so a count needs one call with page_size=1.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 4 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
page
Not provided
Missing description. Explain what this value means and how to supply it.
page_size
Not provided
Missing description. Explain what this value means and how to supply it.
source
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema5/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description39/100
Update a custom metric via PUT /v1/update-custom-metric/{metric_id}.
`settings` replaces the metric's settings object wholesale; see NewCustomMetric.settings
for the `fire_conditions` and `composite` shapes, and for `metric_type`, which must be sent
alongside a settings object whose keys belong to a different type than the metric has.
Resolve contradictions between the description, input schema, and annotations.
Inputs0/100
0 of 18 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
metric_id
Not provided
Missing description. Explain what this value means and how to supply it.
name
Not provided
Missing description. Explain what this value means and how to supply it.
prompt
Not provided
Missing description. Explain what this value means and how to supply it.
response_type
Not provided
Missing description. Explain what this value means and how to supply it.
agent_ids
Not provided
Missing description. Explain what this value means and how to supply it.
min_value
Not provided
Missing description. Explain what this value means and how to supply it.
max_value
Not provided
Missing description. Explain what this value means and how to supply it.
category
Not provided
Missing description. Explain what this value means and how to supply it.
tags
Not provided
Missing description. Explain what this value means and how to supply it.
scoring_guidance
Not provided
Missing description. Explain what this value means and how to supply it.
model
Not provided
Missing description. Explain what this value means and how to supply it.
temperature
Not provided
Missing description. Explain what this value means and how to supply it.
enum_options
Not provided
Missing description. Explain what this value means and how to supply it.
tool_names
Not provided
Missing description. Explain what this value means and how to supply it.
json_schema
Not provided
Missing description. Explain what this value means and how to supply it.
allow_not_applicable
Not provided
Missing description. Explain what this value means and how to supply it.
metric_type
Not provided
Missing description. Explain what this value means and how to supply it.
settings
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description99/100
Delete one or many custom metrics in ONE call (POST /v1/delete-custom-metrics).
Pass a single-item list to delete one. Deleting a metric removes its future
evaluations, not the results it already produced. Returns deleted_count and
deleted_metric_ids; every id must exist, be writable and not be a builtin, or
the whole call is rejected and nothing is deleted.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
custom_metric_ids
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "delete_custom_metrics",
"title": "Delete custom metrics",
"description": "Delete one or many custom metrics in ONE call (POST /v1/delete-custom-metrics).\n\nPass a single-item list to delete one. Deleting a metric removes its future\nevaluations, not the results it already produced. Returns deleted_count and\ndeleted_metric_ids; every id must exist, be writable and not be a builtin, or\nthe whole call is rejected and nothing is deleted.\n",
"inputSchema": {
"type": "object",
"title": "delete_custom_metricsArguments",
"required": [
"custom_metric_ids"
],
"properties": {
"custom_metric_ids": {
"type": "array",
"items": {
"type": "string"
},
"title": "Custom Metric Ids"
}
}
},
"outputSchema": {
"type": "object",
"title": "delete_custom_metricsDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description86/100
List the organization's alerts via GET /v1/alerts.
Each alert carries ``entity_type`` (e.g. 'custom_metric', 'standard_metric'),
``entity_field`` (for custom-metric alerts this is the custom_metric UUID;
``entity_field_display`` holds the human name), ``trigger_count``, and
``in_alert``. To find the custom metric firing the most alerts, filter to
``entity_type == 'custom_metric'`` and sort by ``trigger_count`` descending.
Args:
source_scope: Optional filter — 'all', 'observability', or 'simulation'.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
source_scope
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema4/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description92/100
Get an alert's recent triggers (fired events) via GET /v1/alerts/{alert_id}/results.
Use this to review what an alert has been firing on. Results are newest-first
and page-paginated. Each event resolves to the entity that caused it: for
simulation alerts the simulation + run (+ test result); for observability
alerts the call. ``actual_value`` / ``expected_value`` / ``operator_used``
describe the breach.
For a custom-metric alert, the resolved obs/sim conversations are the candidate
cases for false-alarm analysis: read the metric with get_custom_metric (the
alert's entity_field is the metric UUID), then pull the suspect cases into a
Metrics Lab with create_lab to inspect the metric's verdicts and improve it.
Args:
source: Optional filter — 'simulation' or 'observability'.
page: 1-based page number.
page_size: Items per page (1-100).
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 4 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
alert_id
Not provided
Missing description. Explain what this value means and how to supply it.
source
Not provided
Missing description. Explain what this value means and how to supply it.
page
Not provided
Missing description. Explain what this value means and how to supply it.
page_size
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description62/100
Create an alert via POST /v1/create-alert.
Args:
entity_type: 'custom_metric', 'standard_metric', 'custom_goal',
'metadata_field', or 'system_failure'.
entity_field: The field/metric monitored. For a custom-metric alert this
is the custom_metric UUID.
operator: 'equals', 'not_equals', 'greater_than', 'less_than',
'greater_than_or_equal', 'less_than_or_equal', 'contains', 'not_contains'.
comparison_value: Threshold value (as a string).
notification_channels: List of {"type": "email"|"slack"|"webhook"|"pagerduty"|"betterstack"|"incidentio",
"target": "..."}.
agent_ids: Required when applies_to_all_agents is False.
source_scope: 'all', 'observability', or 'simulation'. simulation_id may
only be set when source_scope is 'simulation'.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 18 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
name
Not provided
Missing description. Explain what this value means and how to supply it.
entity_type
Not provided
Missing description. Explain what this value means and how to supply it.
entity_field
Not provided
Missing description. Explain what this value means and how to supply it.
operator
Not provided
Missing description. Explain what this value means and how to supply it.
comparison_value
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
is_enabled
Not provided
Missing description. Explain what this value means and how to supply it.
notification_channels
Not provided
Missing description. Explain what this value means and how to supply it.
applies_to_all_agents
Not provided
Missing description. Explain what this value means and how to supply it.
agent_ids
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
evaluation_scope
Not provided
Missing description. Explain what this value means and how to supply it.
aggregation
Not provided
Missing description. Explain what this value means and how to supply it.
threshold_time_interval
Not provided
Missing description. Explain what this value means and how to supply it.
min_events
Not provided
Missing description. Explain what this value means and how to supply it.
min_events_type
Not provided
Missing description. Explain what this value means and how to supply it.
source_scope
Not provided
Missing description. Explain what this value means and how to supply it.
sample_size
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description76/100
Update an alert via PUT /v1/update-alert/{alert_id}.
Only the fields you pass are changed (partial update). See create_alert for
the allowed enum values of entity_type / operator / source_scope.
Args:
clear_fields: Names of nullable fields to explicitly set to null (clear),
since passing None for a parameter means "leave unchanged". Allowed:
'simulation_id', 'description', 'evaluation_scope', 'aggregation',
'threshold_time_interval', 'min_events', 'sample_size'. For example, clearing
'simulation_id' makes a simulation alert agent-scoped again.
Explain mutations, irreversible effects, or prerequisites that matter before calling this tool.
Inputs0/100
0 of 20 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
alert_id
Not provided
Missing description. Explain what this value means and how to supply it.
name
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
is_enabled
Not provided
Missing description. Explain what this value means and how to supply it.
entity_type
Not provided
Missing description. Explain what this value means and how to supply it.
entity_field
Not provided
Missing description. Explain what this value means and how to supply it.
operator
Not provided
Missing description. Explain what this value means and how to supply it.
comparison_value
Not provided
Missing description. Explain what this value means and how to supply it.
notification_channels
Not provided
Missing description. Explain what this value means and how to supply it.
applies_to_all_agents
Not provided
Missing description. Explain what this value means and how to supply it.
agent_ids
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
evaluation_scope
Not provided
Missing description. Explain what this value means and how to supply it.
aggregation
Not provided
Missing description. Explain what this value means and how to supply it.
threshold_time_interval
Not provided
Missing description. Explain what this value means and how to supply it.
min_events
Not provided
Missing description. Explain what this value means and how to supply it.
min_events_type
Not provided
Missing description. Explain what this value means and how to supply it.
source_scope
Not provided
Missing description. Explain what this value means and how to supply it.
sample_size
Not provided
Missing description. Explain what this value means and how to supply it.
clear_fields
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description82/100
List the organization's uptime monitors via GET /v1/uptime/monitors.
Each monitor carries agent_id, frequency (an "<n>m" minutes token like "5m"),
checks, notifications, enabled, last_status, and last_checked_at.
The description explains the capability, when to use it, and what to expect.
Inputs100/100
This tool declares no inputs, so argument descriptions are not needed.
No input fields.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description98/100
Outcome counts, uptime % and response-latency percentiles per bucket via GET /v1/uptime/monitors/{monitor_id}/series.
Args:
monitor_id: The monitor to read.
days: Lookback window in days, 1 to 365. Defaults to 7.
bucket: Aggregation granularity, one of "15m", "hour", "day", "week", "month". Omit to
get a width that suits the window (quarter hours up to 6 hours, hourly up to 2 days,
then daily, weekly, monthly).
check: Grade one health check instead of the monitor's own verdict — its check_type
("connection", "agent_malfunction", "latency") or a custom metric's id.
label: The check's display name. Runs recorded before custom metrics were keyed by id
stored the name instead, so pass it alongside `check` to grade those too.
Returns {"series": {"bucket", "from", "to", "series": [...], "latency": {...},
"window": {...}}}. Each point in `series` is {date, uptime_pct, up, down, unknown, pending,
avg_latency_ms, p50_latency_ms, p75_latency_ms, p90_latency_ms, p95_latency_ms,
p99_latency_ms}; uptime_pct and the latency fields are null for a bucket with nothing to
measure. `latency` holds the mean and the same five percentiles over the whole window, which
is not the mean of the buckets'.
`window` is {uptime_pct, incidents} for the monitor's own verdict over that window, where an
incident is the start of an unresolved DOWN streak. Every bucket in the window is returned, so a stretch with no
runs comes back with null rates rather than being missing. Requires a user access token: an
API key is rejected.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 5 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
monitor_id
Not provided
Missing description. Explain what this value means and how to supply it.
days
Not provided
Missing description. Explain what this value means and how to supply it.
bucket
Not provided
Missing description. Explain what this value means and how to supply it.
check
Not provided
Missing description. Explain what this value means and how to supply it.
label
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema2/100
Declare the result fields and their types in the output schema.
{
"name": "get_uptime_monitor_series",
"title": "Get uptime monitor series",
"description": "Outcome counts, uptime % and response-latency percentiles per bucket via GET /v1/uptime/monitors/{monitor_id}/series.\n\nArgs:\n monitor_id: The monitor to read.\n days: Lookback window in days, 1 to 365. Defaults to 7.\n bucket: Aggregation granularity, one of \"15m\", \"hour\", \"day\", \"week\", \"month\". Omit to\n get a width that suits the window (quarter hours up to 6 hours, hourly up to 2 days,\n then daily, weekly, monthly).\n check: Grade one health check instead of the monitor's own verdict — its check_type\n (\"connection\", \"agent_malfunction\", \"latency\") or a custom metric's id.\n label: The check's display name. Runs recorded before custom metrics were keyed by id\n stored the name instead, so pass it alongside `check` to grade those too.\n\nReturns {\"series\": {\"bucket\", \"from\", \"to\", \"series\": [...], \"latency\": {...},\n\"window\": {...}}}. Each point in `series` is {date, uptime_pct, up, down, unknown, pending,\navg_latency_ms, p50_latency_ms, p75_latency_ms, p90_latency_ms, p95_latency_ms,\np99_latency_ms}; uptime_pct and the latency fields are null for a bucket with nothing to\nmeasure. `latency` holds the mean and the same five percentiles over the whole window, which\nis not the mean of the buckets'.\n`window` is {uptime_pct, incidents} for the monitor's own verdict over that window, where an\nincident is the start of an unresolved DOWN streak. Every bucket in the window is returned, so a stretch with no\nruns comes back with null rates rather than being missing. Requires a user access token: an\nAPI key is rejected.\n",
"inputSchema": {
"type": "object",
"title": "get_uptime_monitor_seriesArguments",
"required": [
"monitor_id"
],
"properties": {
"days": {
"type": "integer",
"title": "Days",
"default": 7
},
"check": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Check",
"default": null
},
"label": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Label",
"default": null
},
"bucket": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Bucket",
"default": null
},
"monitor_id": {
"type": "string",
"title": "Monitor Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "get_uptime_monitor_seriesDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description89/100
Create an uptime monitor via POST /v1/uptime/monitors (also provisions it).
Returns the new monitor's id and whether provisioning succeeded. See this
module's docstring for the checks and notifications shapes.
Args:
agent_id: The agent to monitor.
frequency: Recurring interval as an "<n>m" minutes token, e.g. "5m". Defaults to "5m".
active_window: Days/hours the monitor may run, e.g. {"days": ["monday"],
"start_time": "09:00", "end_time": "17:00", "timezone": "America/Los_Angeles"}.
Omit to run it around the clock.
start_at: ISO 8601 first-check time with a timezone (e.g. "2026-07-22T15:00:00Z");
omit to start immediately.
The description explains the capability, when to use it, and what to expect.
Inputs23/100
4 of 10 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
frequency
Not provided
Missing description. Explain what this value means and how to supply it.
$defs › ActiveWindow › days
Days to run on; empty means every day
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › ActiveWindow › start_time
HH:MM start of the daily window
Resolve the mismatch between this description and its schema constraints.
$defs › ActiveWindow › end_time
HH:MM end of the daily window
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › ActiveWindow › timezone
IANA timezone the cron expression is read in. Null means UTC.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
checks
Not provided
Missing description. Explain what this value means and how to supply it.
notifications
Not provided
Missing description. Explain what this value means and how to supply it.
enabled
Not provided
Missing description. Explain what this value means and how to supply it.
start_at
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description88/100
Update an uptime monitor via PUT /v1/uptime/monitors/{monitor_id} (re-provisions it).
Only the fields you pass are changed (partial update). Changing checks or the
agent rebuilds the backing simulation; other edits just re-point the schedule.
See this module's docstring for the checks and notifications shapes.
Args:
enabled: Set false to pause the monitor, true to resume it.
active_window: Days/hours the monitor may run — see create_uptime_monitor.
clear_active_window: Set true to drop the window and run around the clock.
Omitting active_window leaves the existing window untouched, so clearing
one needs this flag.
start_at: ISO 8601 first-check time with a timezone; omit to start immediately.
Explain mutations, irreversible effects, or prerequisites that matter before calling this tool.
Inputs25/100
4 of 12 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
monitor_id
Not provided
Missing description. Explain what this value means and how to supply it.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
frequency
Not provided
Missing description. Explain what this value means and how to supply it.
$defs › ActiveWindow › days
Days to run on; empty means every day
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › ActiveWindow › start_time
HH:MM start of the daily window
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › ActiveWindow › end_time
HH:MM end of the daily window
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
$defs › ActiveWindow › timezone
IANA timezone the cron expression is read in. Null means UTC.
Remove validation rules already expressed in this field’s schema; describe its meaning and usage instead.
clear_active_window
Not provided
Missing description. Explain what this value means and how to supply it.
checks
Not provided
Missing description. Explain what this value means and how to supply it.
notifications
Not provided
Missing description. Explain what this value means and how to supply it.
enabled
Not provided
Missing description. Explain what this value means and how to supply it.
start_at
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description97/100
Get a lab's full state via GET /v1/metrics-lab/lab/{lab_id}.
Returns conversations, metrics, ai_evaluations (base metric verdicts),
human_evaluations (ground truth), metric_revisions, and lab_ai_evaluations
(per-revision verdicts). Poll this to observe async evaluation progress via
each evaluation's ``status`` (QUEUED/EVALUATING/COMPLETED/INCOMPLETED/…).
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
lab_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema6/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description93/100
Create a Metrics Lab to iterate on a custom metric against real conversations.
POST /v1/metrics-lab/lab. A lab pins a metric to a set of conversations
(e.g. the suspect cases from get_alert_results) so you can inspect the
metric's verdicts and improve it. Existing evaluations for each (metric,
conversation) pair are copied in automatically; pairs with no prior result
are queued for fresh evaluation — so current (often wrong) verdicts appear
immediately and cheaply.
Typical loop after creating the lab:
1. get_lab_detail(lab_id) — read ai_evaluations (response_value + reasoning)
to confirm which cases are false alarms. Poll until status COMPLETED.
2. create_metric_revision(lab_id, custom_metric_id, ...) — a candidate fix
(sharper description / scoring_guidance).
3. evaluate_conversation(... metric_type='custom_metric_revision') for the
cases, then get_lab_detail to compare the revision's lab_ai_evaluations
against the base ai_evaluations. Repeat 2-3 until the cases flip.
4. Promote the winning wording onto the metric with update_custom_metric.
Args:
conversations: List of {"call_id": "<uuid>"} or {"test_result_id": <int>}.
Each item must have exactly one of the two.
metric_ids: Custom metric UUIDs to attach.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 5 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
name
Not provided
Missing description. Explain what this value means and how to supply it.
conversations
Not provided
Missing description. Explain what this value means and how to supply it.
metric_ids
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
tags
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "create_lab",
"title": "Create lab",
"description": "Create a Metrics Lab to iterate on a custom metric against real conversations.\n\nPOST /v1/metrics-lab/lab. A lab pins a metric to a set of conversations\n(e.g. the suspect cases from get_alert_results) so you can inspect the\nmetric's verdicts and improve it. Existing evaluations for each (metric,\nconversation) pair are copied in automatically; pairs with no prior result\nare queued for fresh evaluation — so current (often wrong) verdicts appear\nimmediately and cheaply.\n\nTypical loop after creating the lab:\n 1. get_lab_detail(lab_id) — read ai_evaluations (response_value + reasoning)\n to confirm which cases are false alarms. Poll until status COMPLETED.\n 2. create_metric_revision(lab_id, custom_metric_id, ...) — a candidate fix\n (sharper description / scoring_guidance).\n 3. evaluate_conversation(... metric_type='custom_metric_revision') for the\n cases, then get_lab_detail to compare the revision's lab_ai_evaluations\n against the base ai_evaluations. Repeat 2-3 until the cases flip.\n 4. Promote the winning wording onto the metric with update_custom_metric.\n\nArgs:\n conversations: List of {\"call_id\": \"<uuid>\"} or {\"test_result_id\": <int>}.\n Each item must have exactly one of the two.\n metric_ids: Custom metric UUIDs to attach.\n",
"inputSchema": {
"type": "object",
"title": "create_labArguments",
"required": [
"name",
"conversations",
"metric_ids"
],
"properties": {
"name": {
"type": "string",
"title": "Name"
},
"tags": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Tags",
"default": null
},
"metric_ids": {
"type": "array",
"items": {
"type": "string"
},
"title": "Metric Ids"
},
"description": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Description",
"default": null
},
"conversations": {
"type": "array",
"items": {
"type": "object",
"additionalProperties": true
},
"title": "Conversations"
}
}
},
"outputSchema": {
"type": "object",
"title": "create_labDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description66/100
Add metrics to a lab via POST /v1/metrics-lab/lab/{lab_id}/metrics.
Args:
evaluate_conversations: When true, for every conversation already in the
lab, copy existing evaluations for the added metrics where present
and queue fresh evaluation only for metrics with no result.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
lab_id
Not provided
Missing description. Explain what this value means and how to supply it.
metric_ids
Not provided
Missing description. Explain what this value means and how to supply it.
evaluate_conversations
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description82/100
Add conversations to a lab via POST /v1/metrics-lab/lab/{lab_id}/conversations.
For each added conversation, existing evaluations for the lab's metrics are
copied in where present; only pairs with no result are queued.
Args:
conversations: List of {"call_id": "<uuid>"} or {"test_result_id": <int>}.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
lab_id
Not provided
Missing description. Explain what this value means and how to supply it.
conversations
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description80/100
Create a metric revision via POST /v1/metrics-lab/lab/{lab_id}/metric-revisions.
A revision is a candidate improvement to a metric — typically a sharper
``description`` and/or ``scoring_guidance``. The revision_number is
auto-incremented. After creating it, call evaluate_conversation with
metric_type='custom_metric_revision' to score it against conversations.
Args:
eval_route: 'AUDIO', 'TEXT', or 'AUTO'.
temperature: 0-2.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 9 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
lab_id
Not provided
Missing description. Explain what this value means and how to supply it.
custom_metric_id
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
scoring_guidance
Not provided
Missing description. Explain what this value means and how to supply it.
eval_route
Not provided
Missing description. Explain what this value means and how to supply it.
model
Not provided
Missing description. Explain what this value means and how to supply it.
audio_model
Not provided
Missing description. Explain what this value means and how to supply it.
temperature
Not provided
Missing description. Explain what this value means and how to supply it.
allow_not_applicable
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description78/100
Queue evaluation of one conversation via POST /v1/metrics-lab/evaluate-conversation.
Evaluation is asynchronous — poll get_lab_detail until the evaluation
``status`` reaches COMPLETED.
Args:
conversation_type: 'obs_conversation' or 'sim_conversation'.
conversation_id: The obs_conversation_id (uuid) or sim_conversation_id (as a string).
metric_type: 'custom_metric' (score base metrics; pass custom_metric_ids)
or 'custom_metric_revision' (score a revision; pass custom_metric_revision_id).
custom_metric_ids: Required when metric_type='custom_metric'.
custom_metric_revision_id: Required when metric_type='custom_metric_revision'.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 6 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
lab_id
Not provided
Missing description. Explain what this value means and how to supply it.
conversation_type
Not provided
Missing description. Explain what this value means and how to supply it.
conversation_id
Not provided
Missing description. Explain what this value means and how to supply it.
metric_type
Not provided
Missing description. Explain what this value means and how to supply it.
custom_metric_ids
Not provided
Missing description. Explain what this value means and how to supply it.
custom_metric_revision_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description74/100
Create a workflow via POST /v1/scenario.
``definition`` is required (omit or null fails): a React Flow graph object with
``nodes`` and ``edges`` arrays. Use ``{"nodes": [], "edges": []}`` for an empty draft.
Each node: string ``id``, ``type``, ``position`` (x/y), ``data``; each edge: string
``id``, ``source``, ``target`` (node ids). Use ``validate_workflow_definition`` to check
a graph before persisting.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 4 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
name
Not provided
Missing description. Explain what this value means and how to supply it.
definition
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
agent_ids
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description71/100
Validate a React Flow graph without persisting via POST /v1/scenario/validate-definition.
Provide exactly one of ``definition`` (object) or ``json_text`` (stringified JSON).
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
definition
Not provided
Missing description. Explain what this value means and how to supply it.
json_text
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema12/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description86/100
Add a node to a scenario-builder workflow (writes /v1/scenario/{workflow_id}).
`node_type` decides which leg of the phone tree you are adding, and which of the
fields below apply. Fields belonging to another type are rejected, not ignored.
node_type="ivr_menu" — the automated menu. `options` is required: a list of
{"id", "phrase", "label"?} dicts. The prompt the IVR plays is every option's
`phrase` joined with ". ", and each option becomes a source handle `opt-<id>` you
wire up with add_scenario_edge. `barge_in_allowed` lets the caller talk over the
prompt; `interdigit_timeout_ms` is how long it waits between keypresses.
node_type="hold" — hold music. `duration_ms` is required and 0 means skip the
wait. `message_before_hold` / `message_after_hold` are the "please hold" and
"thanks for waiting" lines spoken around it.
node_type="human_agent" — the Bluejay-emulated live representative. `intent`
(what the rep should accomplish) and `success_criteria` (how the eval grades the
leg) are both required. `pickup_delay_ms` is the wait before the rep answers,
`min_talk_duration_ms` / `max_talk_duration_ms` bound the leg, and `speaks_first`
decides whether the rep or the caller opens.
Shared: `position` places the node on the canvas, `label` names it, `node_id`
pins the id instead of generating one. `voice_accent` (a key from
utils.consts.VALID_ACCENTS) and `voice_speed` override the TTS voice on the
ivr_menu prompt or the human_agent rep; omit to inherit the test case's voice.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 19 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
workflow_id
Not provided
Missing description. Explain what this value means and how to supply it.
node_type
Not provided
Missing description. Explain what this value means and how to supply it.
options
Not provided
Missing description. Explain what this value means and how to supply it.
duration_ms
Not provided
Missing description. Explain what this value means and how to supply it.
intent
Not provided
Missing description. Explain what this value means and how to supply it.
success_criteria
Not provided
Missing description. Explain what this value means and how to supply it.
position
Not provided
Missing description. Explain what this value means and how to supply it.
label
Not provided
Missing description. Explain what this value means and how to supply it.
node_id
Not provided
Missing description. Explain what this value means and how to supply it.
barge_in_allowed
Not provided
Missing description. Explain what this value means and how to supply it.
interdigit_timeout_ms
Not provided
Missing description. Explain what this value means and how to supply it.
message_before_hold
Not provided
Missing description. Explain what this value means and how to supply it.
message_after_hold
Not provided
Missing description. Explain what this value means and how to supply it.
pickup_delay_ms
Not provided
Missing description. Explain what this value means and how to supply it.
max_talk_duration_ms
Not provided
Missing description. Explain what this value means and how to supply it.
min_talk_duration_ms
Not provided
Missing description. Explain what this value means and how to supply it.
speaks_first
Not provided
Missing description. Explain what this value means and how to supply it.
voice_accent
Not provided
Missing description. Explain what this value means and how to supply it.
voice_speed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description84/100
Partial update of one scenario-builder node's data fields.
`node_id` picks the node and `node_type` must match that node's actual type —
it selects which fields are writable, and fields belonging to another type are
rejected. Only the fields you pass change; at least one must be provided.
The fields carry the same meaning as in create_scenario_node: `options` for
ivr_menu (editing it drops the `opt-<id>` handle of any removed option, so
re-wire those edges), `duration_ms` and the hold messages for hold, `intent` /
`success_criteria` and the timing bounds for human_agent. Pass voice_accent=""
or voice_speed="" to clear an override and go back to inheriting the test
case's voice.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 18 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
workflow_id
Not provided
Missing description. Explain what this value means and how to supply it.
node_id
Not provided
Missing description. Explain what this value means and how to supply it.
node_type
Not provided
Missing description. Explain what this value means and how to supply it.
options
Not provided
Missing description. Explain what this value means and how to supply it.
duration_ms
Not provided
Missing description. Explain what this value means and how to supply it.
intent
Not provided
Missing description. Explain what this value means and how to supply it.
success_criteria
Not provided
Missing description. Explain what this value means and how to supply it.
label
Not provided
Missing description. Explain what this value means and how to supply it.
barge_in_allowed
Not provided
Missing description. Explain what this value means and how to supply it.
interdigit_timeout_ms
Not provided
Missing description. Explain what this value means and how to supply it.
message_before_hold
Not provided
Missing description. Explain what this value means and how to supply it.
message_after_hold
Not provided
Missing description. Explain what this value means and how to supply it.
pickup_delay_ms
Not provided
Missing description. Explain what this value means and how to supply it.
max_talk_duration_ms
Not provided
Missing description. Explain what this value means and how to supply it.
min_talk_duration_ms
Not provided
Missing description. Explain what this value means and how to supply it.
speaks_first
Not provided
Missing description. Explain what this value means and how to supply it.
voice_accent
Not provided
Missing description. Explain what this value means and how to supply it.
voice_speed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description100/100
Remove a node from a scenario-builder workflow. Cascades every edge
that touches the node (incoming OR outgoing).
**Requires explicit user confirmation.** Calling pattern:
1. First call with ``confirmed=False`` (the default) — returns
``{needs_confirmation: True, preview: "...", ...}`` describing what
would happen.
2. Relay the preview to the user and ask "Do you want me to proceed?".
3. ONLY after the user explicitly approves, call again with
``confirmed=True`` and the same arguments.
Works on any node type (ivr_menu, hold, human_agent, single, options, start).
The ``start`` node is structurally required by the validator — deleting it
will fail validation and the change will be rejected before persistence.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
workflow_id
Not provided
Missing description. Explain what this value means and how to supply it.
node_id
Not provided
Missing description. Explain what this value means and how to supply it.
confirmed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "delete_scenario_node",
"title": "Delete scenario node",
"description": "Remove a node from a scenario-builder workflow. Cascades every edge\nthat touches the node (incoming OR outgoing).\n\n**Requires explicit user confirmation.** Calling pattern:\n 1. First call with ``confirmed=False`` (the default) — returns\n ``{needs_confirmation: True, preview: \"...\", ...}`` describing what\n would happen.\n 2. Relay the preview to the user and ask \"Do you want me to proceed?\".\n 3. ONLY after the user explicitly approves, call again with\n ``confirmed=True`` and the same arguments.\n\nWorks on any node type (ivr_menu, hold, human_agent, single, options, start).\nThe ``start`` node is structurally required by the validator — deleting it\nwill fail validation and the change will be rejected before persistence.\n",
"inputSchema": {
"type": "object",
"title": "delete_scenario_nodeArguments",
"required": [
"workflow_id",
"node_id"
],
"properties": {
"node_id": {
"type": "string",
"title": "Node Id"
},
"confirmed": {
"type": "boolean",
"title": "Confirmed",
"default": false
},
"workflow_id": {
"type": "string",
"title": "Workflow Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "delete_scenario_nodeDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description93/100
Add an edge between two nodes in a scenario-builder workflow.
For edges originating at an ``ivr_menu`` node, ``source_handle`` is REQUIRED
and must be ``"opt-<option_id>"`` matching a real option on the source node
— that's the routing key the runtime keys DTMF branches on. For ``hold`` and
``human_agent`` sources, ``source_handle`` is ignored (single source handle
on the canvas).
``hold`` and ``human_agent`` nodes accept at most ONE outbound edge — the
backend validator will reject the workflow if you add a second.
Writes to the scenario-builder workflow via ``/v1/scenario/{workflow_id}``.
Returns ``{workflow_id, edge_id, edge, error}``.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 5 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
workflow_id
Not provided
Missing description. Explain what this value means and how to supply it.
source_node_id
Not provided
Missing description. Explain what this value means and how to supply it.
target_node_id
Not provided
Missing description. Explain what this value means and how to supply it.
source_handle
Not provided
Missing description. Explain what this value means and how to supply it.
edge_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description96/100
Remove an edge by id from a scenario-builder workflow.
**Requires explicit user confirmation.** Same two-call pattern as
``delete_scenario_node``: first call with ``confirmed=False`` returns a
``needs_confirmation`` payload; only call with ``confirmed=True`` after the
user approves. Both endpoints survive — only the connection is dropped.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
workflow_id
Not provided
Missing description. Explain what this value means and how to supply it.
edge_id
Not provided
Missing description. Explain what this value means and how to supply it.
confirmed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description98/100
Return a compact view of the workflow's nodes and edges — enough to orient
follow-up edits without paying for the full ``definition`` blob.
Shape: ``{"workflow_id", "nodes": [{id, type, label, ...type-specific fields}],
"edges": [{id, source, target, sourceHandle?}], "error"}``. Use this before
``update_*_node`` / ``add_scenario_edge`` so you know which ids exist.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
workflow_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema4/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description98/100
Start an autonomous self-improve loop for a single VAPI, ElevenLabs, Retell, or Google CES agent.
The loop iterates ``agent_id``'s prompt in place - pushing each candidate to the agent's
provider and re-running ``simulation_id`` to measure it - and, when finished, writes
the single winning prompt as ONE new 'latest' version on the agent. The prior version is
left intact so the user can revert; the 'production' label is never moved. For Google CES
the prompt covers every agent in the app, and each candidate is published as a CES version
that the agent's deployment is repointed to; the draft must match the deployment to start.
**Confirm-gated.** Call first with ``confirmed=False`` (default) - the response will be
``{needs_confirmation: true, preview: "..."}``. Relay the preview verbatim and ask the
user to approve. ONLY after they approve, call again with ``confirmed=True`` and the same
arguments.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 8 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
target_pass_rate
Not provided
Missing description. Explain what this value means and how to supply it.
max_iterations
Not provided
Missing description. Explain what this value means and how to supply it.
min_improvement
Not provided
Missing description. Explain what this value means and how to supply it.
metric_count
Not provided
Missing description. Explain what this value means and how to supply it.
success_metric_ids
Not provided
Missing description. Explain what this value means and how to supply it.
confirmed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "start_self_improve_run",
"title": "Start self improve run",
"description": "Start an autonomous self-improve loop for a single VAPI, ElevenLabs, Retell, or Google CES agent.\n\nThe loop iterates ``agent_id``'s prompt in place - pushing each candidate to the agent's\nprovider and re-running ``simulation_id`` to measure it - and, when finished, writes\nthe single winning prompt as ONE new 'latest' version on the agent. The prior version is\nleft intact so the user can revert; the 'production' label is never moved. For Google CES\nthe prompt covers every agent in the app, and each candidate is published as a CES version\nthat the agent's deployment is repointed to; the draft must match the deployment to start.\n\n**Confirm-gated.** Call first with ``confirmed=False`` (default) - the response will be\n``{needs_confirmation: true, preview: \"...\"}``. Relay the preview verbatim and ask the\nuser to approve. ONLY after they approve, call again with ``confirmed=True`` and the same\narguments.\n",
"inputSchema": {
"type": "object",
"title": "start_self_improve_runArguments",
"required": [
"agent_id",
"simulation_id"
],
"properties": {
"agent_id": {
"type": "integer",
"title": "Agent Id"
},
"confirmed": {
"type": "boolean",
"title": "Confirmed",
"default": false
},
"metric_count": {
"type": "integer",
"title": "Metric Count",
"default": 5
},
"simulation_id": {
"type": "integer",
"title": "Simulation Id"
},
"max_iterations": {
"type": "integer",
"title": "Max Iterations",
"default": 5
},
"min_improvement": {
"type": "number",
"title": "Min Improvement",
"default": 0.02
},
"target_pass_rate": {
"type": "number",
"title": "Target Pass Rate",
"default": 0.9
},
"success_metric_ids": {
"anyOf": [
{
"type": "array",
"items": {
"type": "string"
}
},
{
"type": "null"
}
],
"title": "Success Metric Ids",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "start_self_improve_runDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description97/100
Start a generational-tree red-team simulation against a single target agent.
The simulation runs benign recon call(s) that seed an agent-level knowledge base (the
citadel), then attacker calls that branch per the oracle's triage — up to max_levels deep,
bounded by max_branches_per_node and a max_total_dhs budget. Every call is one voice call
hard-capped at max_call_duration_minutes. ``config`` overrides those caps (clamped to the
mandatory ceilings). ``attack_quotas`` (optional) is ``{social_engineering, prompt_injection,
audio_native, content_harm}`` → attempt counts; 0 (default) keeps the adaptive mix, N runs that
family N times (clamped to 20 per family); each attack level is sized from those counts
(largest family, at least one slot per active family). Custom per-family counts require a
Growth, Scale, Enterprise, or custom Growth+ contract. Content-safety probes (harm_categories)
run by default alongside the OWASP attacks; pass ``harm_categories: []`` for an OWASP-only test.
**Confirm-gated.** Call first with ``confirmed=False`` (default) — the response will be
``{needs_confirmation: true, preview: "..."}``. Relay the preview verbatim and ask the user
to approve. ONLY after they approve, call again with ``confirmed=True`` and the same arguments.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
config
Not provided
Missing description. Explain what this value means and how to supply it.
confirmed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "start_red_team_simulation",
"title": "Start red team simulation",
"description": "Start a generational-tree red-team simulation against a single target agent.\n\nThe simulation runs benign recon call(s) that seed an agent-level knowledge base (the\ncitadel), then attacker calls that branch per the oracle's triage — up to max_levels deep,\nbounded by max_branches_per_node and a max_total_dhs budget. Every call is one voice call\nhard-capped at max_call_duration_minutes. ``config`` overrides those caps (clamped to the\nmandatory ceilings). ``attack_quotas`` (optional) is ``{social_engineering, prompt_injection,\naudio_native, content_harm}`` → attempt counts; 0 (default) keeps the adaptive mix, N runs that\nfamily N times (clamped to 20 per family); each attack level is sized from those counts\n(largest family, at least one slot per active family). Custom per-family counts require a\nGrowth, Scale, Enterprise, or custom Growth+ contract. Content-safety probes (harm_categories)\nrun by default alongside the OWASP attacks; pass ``harm_categories: []`` for an OWASP-only test.\n\n**Confirm-gated.** Call first with ``confirmed=False`` (default) — the response will be\n``{needs_confirmation: true, preview: \"...\"}``. Relay the preview verbatim and ask the user\nto approve. ONLY after they approve, call again with ``confirmed=True`` and the same arguments.\n",
"inputSchema": {
"type": "object",
"title": "start_red_team_simulationArguments",
"required": [
"agent_id"
],
"properties": {
"config": {
"anyOf": [
{
"type": "object",
"additionalProperties": true
},
{
"type": "null"
}
],
"title": "Config",
"default": null
},
"agent_id": {
"type": "integer",
"title": "Agent Id"
},
"confirmed": {
"type": "boolean",
"title": "Confirmed",
"default": false
}
}
},
"outputSchema": {
"type": "object",
"title": "start_red_team_simulationDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description96/100
Get a red-team simulation's status, overall verdict, OWASP + MITRE ATLAS scorecard,
confirmed vulnerabilities, and Bluejay analysis. ``simulation_id`` is the id in the app's
/red-teaming/{id} URL and the ``simulation_id`` field of list_red_team_simulations.
For per-attack rows (scenario, intended action, Pass/Fail, transcript link) use
get_red_team_attacks with this simulation_id where it is available (Bluejay AI). Otherwise each
attack is one conversation in the simulation's runs (level 1 = recon): call
get_simulation_runs with this simulation_id, then get_simulation_results /
get_simulation_transcript.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema4/100
Declare the result fields and their types in the output schema.
{
"name": "get_red_team_simulation",
"title": "Get red team simulation",
"description": "Get a red-team simulation's status, overall verdict, OWASP + MITRE ATLAS scorecard,\nconfirmed vulnerabilities, and Bluejay analysis. ``simulation_id`` is the id in the app's\n/red-teaming/{id} URL and the ``simulation_id`` field of list_red_team_simulations.\n\nFor per-attack rows (scenario, intended action, Pass/Fail, transcript link) use\nget_red_team_attacks with this simulation_id where it is available (Bluejay AI). Otherwise each\nattack is one conversation in the simulation's runs (level 1 = recon): call\nget_simulation_runs with this simulation_id, then get_simulation_results /\nget_simulation_transcript.",
"inputSchema": {
"type": "object",
"title": "get_red_team_simulationArguments",
"required": [
"simulation_id"
],
"properties": {
"simulation_id": {
"type": "integer",
"title": "Simulation Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "get_red_team_simulationDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description97/100
Return a compact view of the agent's multi-agent workflow.
Shape: ``{"nodes": [{node_id, name, prompt_excerpt, type}], "edges": [{edge_id, source_node_id,
target_node_id, condition}]}``. Use this before ``update_workflow_node`` so you know which
``node_id`` to target without paying for the full workflow blob.
Works for any workflow-adapter provider — **ElevenLabs, Google Dialogflow CX**
(``GOOGLE_DFCX_VOICE`` / ``GOOGLE_DFCX_CHAT``), **VAPI**, **Retell**, **Amelia**, and
**Bland**. For DFCX, nodes are flows/pages/playbooks and edges are transition routes/event
handlers; for Amelia they come from the synced flow revision; for Bland they are the pathway's
nodes and routes; for Google CES nodes are the app's agents and edges are their handoffs.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
{
"name": "get_workflow_summary",
"title": "Get workflow summary",
"description": "Return a compact view of the agent's multi-agent workflow.\n\nShape: ``{\"nodes\": [{node_id, name, prompt_excerpt, type}], \"edges\": [{edge_id, source_node_id,\ntarget_node_id, condition}]}``. Use this before ``update_workflow_node`` so you know which\n``node_id`` to target without paying for the full workflow blob.\n\nWorks for any workflow-adapter provider — **ElevenLabs, Google Dialogflow CX**\n(``GOOGLE_DFCX_VOICE`` / ``GOOGLE_DFCX_CHAT``), **VAPI**, **Retell**, **Amelia**, and\n**Bland**. For DFCX, nodes are flows/pages/playbooks and edges are transition routes/event\nhandlers; for Amelia they come from the synced flow revision; for Bland they are the pathway's\nnodes and routes; for Google CES nodes are the app's agents and edges are their handoffs.\n",
"inputSchema": {
"type": "object",
"title": "get_workflow_summaryArguments",
"required": [
"agent_id"
],
"properties": {
"agent_id": {
"type": "string",
"title": "Agent Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "get_workflow_summaryDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description95/100
Update a single node inside the agent's stored multi-agent workflow.
Pass only the fields you want to change. ``None`` leaves a field unchanged. At least one
of ``prompt``, ``name``, or ``description`` must be supplied.
This writes to the Bluejay-stored workflow only. To push the change back to the source
provider, call ``push_agent_workflow`` afterwards.
Works for any workflow-adapter provider — ElevenLabs, Google Dialogflow CX
(``GOOGLE_DFCX_VOICE`` / ``GOOGLE_DFCX_CHAT``), VAPI, Retell, and Bland. For DFCX this edits
the prompt/fulfillment of a page or playbook node; for Bland the prompt of a pathway node.
Amelia rejects node edits: edit the flow in Amelia and sync again. Provider-specific fields
(ElevenLabs voice/llm/eagerness, etc.) are not supported here; use the provider-named tool
when one exists.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 5 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
node_id
Not provided
Missing description. Explain what this value means and how to supply it.
prompt
Not provided
Missing description. Explain what this value means and how to supply it.
name
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description100/100
Add a new node to the agent's multi-agent workflow (Bluejay-side only).
The new node has no incoming/outgoing edges — it's unreachable until you connect it with
``add_workflow_edge``. Returns ``{node_id}`` so you can wire it up in a follow-up call.
Works for ElevenLabs, Google Dialogflow CX, VAPI, Retell, and Bland (not Amelia). For DFCX the
node is added as a new page on the agent's first flow (it gets a real Dialogflow resource name
on push).
This writes to the Bluejay-stored workflow only. Call ``push_agent_workflow`` afterwards to
make the change live upstream.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 4 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
name
Not provided
Missing description. Explain what this value means and how to supply it.
prompt
Not provided
Missing description. Explain what this value means and how to supply it.
description
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "add_workflow_node",
"title": "Add workflow node",
"description": "Add a new node to the agent's multi-agent workflow (Bluejay-side only).\n\nThe new node has no incoming/outgoing edges — it's unreachable until you connect it with\n``add_workflow_edge``. Returns ``{node_id}`` so you can wire it up in a follow-up call.\n\nWorks for ElevenLabs, Google Dialogflow CX, VAPI, Retell, and Bland (not Amelia). For DFCX the\nnode is added as a new page on the agent's first flow (it gets a real Dialogflow resource name\non push).\n\nThis writes to the Bluejay-stored workflow only. Call ``push_agent_workflow`` afterwards to\nmake the change live upstream.\n",
"inputSchema": {
"type": "object",
"title": "add_workflow_nodeArguments",
"required": [
"agent_id",
"name"
],
"properties": {
"name": {
"type": "string",
"title": "Name"
},
"prompt": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Prompt",
"default": null
},
"agent_id": {
"type": "string",
"title": "Agent Id"
},
"description": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Description",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "add_workflow_nodeDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description90/100
Remove a node from the workflow. Every edge touching the node is cascade-deleted.
The Start node is protected — every workflow needs an entry point. Writes to Bluejay only;
push afterwards to ship the change upstream.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
node_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description93/100
Add a directed edge between two existing nodes in the agent's workflow.
``condition`` is the user-facing transition trigger (e.g. "caller asks about returns"). It's
optional but strongly recommended — without one the agent can't tell when to follow the edge.
Works for ElevenLabs, Google Dialogflow CX, VAPI, Retell, and Bland (not Amelia). For DFCX this
adds a transition route on the source page targeting the destination page/flow — e.g. to
re-route a billing intent into the Billing Disputes Flow, or reattach a response to the correct
intent. ``condition`` becomes the route's condition/intent label. Bland edge changes ship via a
pathway version on push (``create_version``), never the live draft.
Writes to Bluejay only; push afterwards to ship the change upstream.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 4 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
source_node_id
Not provided
Missing description. Explain what this value means and how to supply it.
target_node_id
Not provided
Missing description. Explain what this value means and how to supply it.
condition
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "add_workflow_edge",
"title": "Add workflow edge",
"description": "Add a directed edge between two existing nodes in the agent's workflow.\n\n``condition`` is the user-facing transition trigger (e.g. \"caller asks about returns\"). It's\noptional but strongly recommended — without one the agent can't tell when to follow the edge.\n\nWorks for ElevenLabs, Google Dialogflow CX, VAPI, Retell, and Bland (not Amelia). For DFCX this\nadds a transition route on the source page targeting the destination page/flow — e.g. to\nre-route a billing intent into the Billing Disputes Flow, or reattach a response to the correct\nintent. ``condition`` becomes the route's condition/intent label. Bland edge changes ship via a\npathway version on push (``create_version``), never the live draft.\n\nWrites to Bluejay only; push afterwards to ship the change upstream.\n",
"inputSchema": {
"type": "object",
"title": "add_workflow_edgeArguments",
"required": [
"agent_id",
"source_node_id",
"target_node_id"
],
"properties": {
"agent_id": {
"type": "string",
"title": "Agent Id"
},
"condition": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Condition",
"default": null
},
"source_node_id": {
"type": "string",
"title": "Source Node Id"
},
"target_node_id": {
"type": "string",
"title": "Target Node Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "add_workflow_edgeDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": false
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description99/100
Pull the latest workflow from the agent's source provider into Bluejay.
Supported for **ElevenLabs**, **Google Dialogflow CX** (``GOOGLE_DFCX_VOICE`` /
``GOOGLE_DFCX_CHAT``), **VAPI**, **Retell**, **Amelia**, and **Bland**. For DFCX this pulls the
agent's flows, pages, intents, playbooks, and transition routes so you can inspect and edit
them before pushing. For Amelia it pulls the latest revision of the agent's
``amelia_flow_name`` flow (inspect only, edits happen in Amelia). For Bland it pulls the
pathway named by ``bland_pathway_id`` (draft, or the version pinned by ``branch_id``).
For Google CES (``GOOGLE_CES_VOICE`` / ``GOOGLE_CES_CHAT``) it pulls the version the agent's
deployment serves (``branch_id="draft"`` for the editable draft, or a version id): every agent,
its tools and handoffs.
**Requires explicit user confirmation.** This call REPLACES Bluejay's stored workflow
with whatever the upstream provider currently has; any unsaved Bluejay edits are lost.
Calling pattern:
1. First call with ``confirmed=False`` (the default) — returns ``{needs_confirmation: true,
preview: "...", ...}`` describing what would happen.
2. Relay the preview to the user verbatim and ask "Do you want me to proceed?" (or similar).
3. ONLY after the user explicitly approves, call again with ``confirmed=True``.
``branch_id`` is opaque metadata — providers without branching (Retell, VAPI) ignore it; for
Bland it selects a pathway version number.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
branch_id
Not provided
Missing description. Explain what this value means and how to supply it.
confirmed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "sync_agent_workflow",
"title": "Sync agent workflow",
"description": "Pull the latest workflow from the agent's source provider into Bluejay.\n\nSupported for **ElevenLabs**, **Google Dialogflow CX** (``GOOGLE_DFCX_VOICE`` /\n``GOOGLE_DFCX_CHAT``), **VAPI**, **Retell**, **Amelia**, and **Bland**. For DFCX this pulls the\nagent's flows, pages, intents, playbooks, and transition routes so you can inspect and edit\nthem before pushing. For Amelia it pulls the latest revision of the agent's\n``amelia_flow_name`` flow (inspect only, edits happen in Amelia). For Bland it pulls the\npathway named by ``bland_pathway_id`` (draft, or the version pinned by ``branch_id``).\nFor Google CES (``GOOGLE_CES_VOICE`` / ``GOOGLE_CES_CHAT``) it pulls the version the agent's\ndeployment serves (``branch_id=\"draft\"`` for the editable draft, or a version id): every agent,\nits tools and handoffs.\n\n**Requires explicit user confirmation.** This call REPLACES Bluejay's stored workflow\nwith whatever the upstream provider currently has; any unsaved Bluejay edits are lost.\n\nCalling pattern:\n 1. First call with ``confirmed=False`` (the default) — returns ``{needs_confirmation: true,\n preview: \"...\", ...}`` describing what would happen.\n 2. Relay the preview to the user verbatim and ask \"Do you want me to proceed?\" (or similar).\n 3. ONLY after the user explicitly approves, call again with ``confirmed=True``.\n\n``branch_id`` is opaque metadata — providers without branching (Retell, VAPI) ignore it; for\nBland it selects a pathway version number.\n",
"inputSchema": {
"type": "object",
"title": "sync_agent_workflowArguments",
"required": [
"agent_id"
],
"properties": {
"agent_id": {
"type": "string",
"title": "Agent Id"
},
"branch_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Branch Id",
"default": null
},
"confirmed": {
"type": "boolean",
"title": "Confirmed",
"default": false
}
}
},
"outputSchema": {
"type": "object",
"title": "sync_agent_workflowDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description100/100
Push Bluejay's stored workflow back to the agent's source provider (makes the change live).
Supported for **ElevenLabs**, **Google Dialogflow CX** (``GOOGLE_DFCX_VOICE`` /
``GOOGLE_DFCX_CHAT``), **VAPI**, **Retell**, **Amelia**, and **Bland**. For DFCX this writes
your page/playbook prompt edits and added/removed transition routes back into the live
Dialogflow CX agent (creating a version when configured). For Amelia it publishes the stored
revision back to the flow; it requires a prior sync. For Bland, prompt edits land on the live
pathway draft; edge/routing changes cannot (Bland's update endpoint drops them), so they ship
by creating a pathway version.
**Requires explicit user confirmation.** Anything pushed becomes immediately visible to live
callers of the agent. Bluejay-side ``update_workflow_node`` edits stay local until pushed.
Calling pattern:
1. First call with ``confirmed=False`` (the default) — returns ``{needs_confirmation: true,
preview: "...", ...}`` describing what would happen.
2. Relay the preview to the user verbatim and ask "Do you want me to push these changes
live to the agent's source provider?".
3. ONLY after the user explicitly approves, call again with ``confirmed=True``.
``branch_id`` is opaque metadata — providers without branching ignore it.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 3 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
branch_id
Not provided
Missing description. Explain what this value means and how to supply it.
confirmed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "push_agent_workflow",
"title": "Push agent workflow",
"description": "Push Bluejay's stored workflow back to the agent's source provider (makes the change live).\n\nSupported for **ElevenLabs**, **Google Dialogflow CX** (``GOOGLE_DFCX_VOICE`` /\n``GOOGLE_DFCX_CHAT``), **VAPI**, **Retell**, **Amelia**, and **Bland**. For DFCX this writes\nyour page/playbook prompt edits and added/removed transition routes back into the live\nDialogflow CX agent (creating a version when configured). For Amelia it publishes the stored\nrevision back to the flow; it requires a prior sync. For Bland, prompt edits land on the live\npathway draft; edge/routing changes cannot (Bland's update endpoint drops them), so they ship\nby creating a pathway version.\n\n**Requires explicit user confirmation.** Anything pushed becomes immediately visible to live\ncallers of the agent. Bluejay-side ``update_workflow_node`` edits stay local until pushed.\n\nCalling pattern:\n 1. First call with ``confirmed=False`` (the default) — returns ``{needs_confirmation: true,\n preview: \"...\", ...}`` describing what would happen.\n 2. Relay the preview to the user verbatim and ask \"Do you want me to push these changes\n live to the agent's source provider?\".\n 3. ONLY after the user explicitly approves, call again with ``confirmed=True``.\n\n``branch_id`` is opaque metadata — providers without branching ignore it.\n",
"inputSchema": {
"type": "object",
"title": "push_agent_workflowArguments",
"required": [
"agent_id"
],
"properties": {
"agent_id": {
"type": "string",
"title": "Agent Id"
},
"branch_id": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Branch Id",
"default": null
},
"confirmed": {
"type": "boolean",
"title": "Confirmed",
"default": false
}
}
},
"outputSchema": {
"type": "object",
"title": "push_agent_workflowDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description64/100
List Convai agents for the org's stored ElevenLabs API key.
Returns ``{"agents": [{agent_id, name}], "error": null}``. Use this during Add-Agent flows
to let the user pick which Convai agent to attach to Bluejay.
Resolve contradictions between the description, input schema, and annotations.
Inputs100/100
This tool declares no inputs, so argument descriptions are not needed.
No input fields.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema6/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description99/100
List a Convai agent's branches (Main + drafts + custom).
Returns ``{"branches": [{id, name, is_main, ...}], "main_branch_id": str | null}``.
Use the returned ``id`` as the ``branch_id`` parameter for ``sync_agent_workflow`` /
``push_agent_workflow`` when you want to read/write a non-default branch.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema5/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description98/100
Merge an Experiment branch into Main (or any source → target) on the Convai agent.
**Requires explicit user confirmation.** Merging into Main typically makes a draft go live
for callers — same blast radius as a push.
Calling pattern:
1. First call with ``confirmed=False`` (the default) — returns ``{needs_confirmation: true,
preview: "..."}`` describing what would happen.
2. Relay the preview to the user and ask "Do you want me to merge?".
3. ONLY after the user explicitly approves, call again with ``confirmed=True``.
``archive_source=True`` archives the source branch on success. ``force=True`` overrides
conflict detection on the ElevenLabs side.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 6 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
agent_id
Not provided
Missing description. Explain what this value means and how to supply it.
source_branch_id
Not provided
Missing description. Explain what this value means and how to supply it.
target_branch_id
Not provided
Missing description. Explain what this value means and how to supply it.
archive_source
Not provided
Missing description. Explain what this value means and how to supply it.
force
Not provided
Missing description. Explain what this value means and how to supply it.
confirmed
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "merge_elevenlabs_branches",
"title": "Merge elevenlabs branches",
"description": "Merge an Experiment branch into Main (or any source → target) on the Convai agent.\n\n**Requires explicit user confirmation.** Merging into Main typically makes a draft go live\nfor callers — same blast radius as a push.\n\nCalling pattern:\n 1. First call with ``confirmed=False`` (the default) — returns ``{needs_confirmation: true,\n preview: \"...\"}`` describing what would happen.\n 2. Relay the preview to the user and ask \"Do you want me to merge?\".\n 3. ONLY after the user explicitly approves, call again with ``confirmed=True``.\n\n``archive_source=True`` archives the source branch on success. ``force=True`` overrides\nconflict detection on the ElevenLabs side.\n",
"inputSchema": {
"type": "object",
"title": "merge_elevenlabs_branchesArguments",
"required": [
"agent_id",
"source_branch_id",
"target_branch_id"
],
"properties": {
"force": {
"type": "boolean",
"title": "Force",
"default": false
},
"agent_id": {
"type": "string",
"title": "Agent Id"
},
"confirmed": {
"type": "boolean",
"title": "Confirmed",
"default": false
},
"archive_source": {
"type": "boolean",
"title": "Archive Source",
"default": false
},
"source_branch_id": {
"type": "string",
"title": "Source Branch Id"
},
"target_branch_id": {
"type": "string",
"title": "Target Branch Id"
}
}
},
"outputSchema": {
"type": "object",
"title": "merge_elevenlabs_branchesDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description95/100
List Bland pathways for the org's stored Bland API key.
Returns ``{"pathways": [{pathway_id, name, description, production_version_number}],
"error": null}``. Use during Add-Agent flows to pick which pathway to attach; the chosen
``pathway_id`` goes on the agent as ``bland_pathway_id``.
The description explains the capability, when to use it, and what to expect.
Inputs100/100
This tool declares no inputs, so argument descriptions are not needed.
No input fields.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
{
"name": "list_bland_pathways",
"title": "List bland pathways",
"description": "List Bland pathways for the org's stored Bland API key.\n\nReturns ``{\"pathways\": [{pathway_id, name, description, production_version_number}],\n\"error\": null}``. Use during Add-Agent flows to pick which pathway to attach; the chosen\n``pathway_id`` goes on the agent as ``bland_pathway_id``.\n",
"inputSchema": {
"type": "object",
"title": "list_bland_pathwaysArguments",
"properties": {}
},
"outputSchema": {
"type": "object",
"title": "list_bland_pathwaysDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description98/100
Start a re-pull of the org's knowledge bases from Bland (agents are left alone).
Returns {status, started_at, error} straight away; the resync runs in the background and can
take a few minutes for a large library. Next, call get_bland_knowledge_base_changes with
wait_for_sync_after=started_at (and since=<start of the last knowledge test run>): each call
waits on the server for this resync to finish, so do not add your own delays. Limited to one
call a minute per org.
The description explains the capability, when to use it, and what to expect.
Inputs100/100
This tool declares no inputs, so argument descriptions are not needed.
No input fields.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"name": "sync_bland_knowledge_bases",
"title": "Sync bland knowledge bases",
"description": "Start a re-pull of the org's knowledge bases from Bland (agents are left alone).\n\nReturns {status, started_at, error} straight away; the resync runs in the background and can\ntake a few minutes for a large library. Next, call get_bland_knowledge_base_changes with\nwait_for_sync_after=started_at (and since=<start of the last knowledge test run>): each call\nwaits on the server for this resync to finish, so do not add your own delays. Limited to one\ncall a minute per org.\n",
"inputSchema": {
"type": "object",
"title": "sync_bland_knowledge_basesArguments",
"properties": {}
},
"outputSchema": {
"type": "object",
"title": "sync_bland_knowledge_basesDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": false,
"destructiveHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description99/100
List the org's Bland knowledge bases whose text changed on a resync, newest first.
After sync_bland_knowledge_bases, call this with wait_for_sync_after set to the
started_at it returned: the server holds the answer until that resync finishes (up to about
36 seconds). Pass since (ISO 8601), e.g. the start of the last knowledge test run, so
already-tested changes drop out. If sync_complete comes back false the resync is still running:
call this again with the same arguments, up to 5 calls in total (about 3 minutes), then continue
with what came back and say the resync was still running. Without wait_for_sync_after it answers
at once.
Returns {sync_complete, last_synced_at, sync_error, changes, error}. Each change is
{knowledge_base_id, name, changed_at, added, diff, truncated}: diff is a unified diff of the
document text, before -> after, and added is true for a knowledge base that is new since the
previous sync. sync_error is set when the last resync failed for some or all knowledge bases.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
since
Not provided
Missing description. Explain what this value means and how to supply it.
wait_for_sync_after
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
{
"name": "get_bland_knowledge_base_changes",
"title": "Get bland knowledge base changes",
"description": "List the org's Bland knowledge bases whose text changed on a resync, newest first.\n\nAfter sync_bland_knowledge_bases, call this with wait_for_sync_after set to the\nstarted_at it returned: the server holds the answer until that resync finishes (up to about\n36 seconds). Pass since (ISO 8601), e.g. the start of the last knowledge test run, so\nalready-tested changes drop out. If sync_complete comes back false the resync is still running:\ncall this again with the same arguments, up to 5 calls in total (about 3 minutes), then continue\nwith what came back and say the resync was still running. Without wait_for_sync_after it answers\nat once.\n\nReturns {sync_complete, last_synced_at, sync_error, changes, error}. Each change is\n{knowledge_base_id, name, changed_at, added, diff, truncated}: diff is a unified diff of the\ndocument text, before -> after, and added is true for a knowledge base that is new since the\nprevious sync. sync_error is set when the last resync failed for some or all knowledge bases.\n",
"inputSchema": {
"type": "object",
"title": "get_bland_knowledge_base_changesArguments",
"properties": {
"since": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Since",
"default": null
},
"wait_for_sync_after": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Wait For Sync After",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "get_bland_knowledge_base_changesDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description94/100
List the organization's connected GitHub accounts via GET /v1/ci/connections.
An empty list means GitHub is not connected: call get_github_install_url and
return that link to the user.
Describe the returned information so the agent knows whether it will answer the request.
Inputs100/100
This tool declares no inputs, so argument descriptions are not needed.
No input fields.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema4/100
Declare the result fields and their types in the output schema.
{
"name": "list_ci_connections",
"title": "List ci connections",
"description": "List the organization's connected GitHub accounts via GET /v1/ci/connections.\n\nAn empty list means GitHub is not connected: call get_github_install_url and\nreturn that link to the user.\n",
"inputSchema": {
"type": "object",
"title": "list_ci_connectionsArguments",
"properties": {}
},
"outputSchema": {
"type": "object",
"title": "list_ci_connectionsDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
Align the title with the capability actually described by this tool.
Description87/100
Get the link that connects GitHub or GitLab.
GitHub uses GET /v1/ci/github/install-url and GitLab uses GET /v1/ci/gitlab/authorize-url.
Connecting needs one browser click by the user, so return the link to them; it
cannot be completed from here.
Args:
return_path: App path to send the user back to afterwards, such as the
simulation page they started from. Omit to use the default.
provider: "github" (default) or "gitlab".
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
return_path
Not provided
Missing description. Explain what this value means and how to supply it.
provider
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema6/100
Declare the result fields and their types in the output schema.
{
"name": "get_github_install_url",
"title": "Get github install url",
"description": "Get the link that connects GitHub or GitLab.\n\nGitHub uses GET /v1/ci/github/install-url and GitLab uses GET /v1/ci/gitlab/authorize-url.\nConnecting needs one browser click by the user, so return the link to them; it\ncannot be completed from here.\n\nArgs:\n return_path: App path to send the user back to afterwards, such as the\n simulation page they started from. Omit to use the default.\n provider: \"github\" (default) or \"gitlab\".\n",
"inputSchema": {
"type": "object",
"title": "get_github_install_urlArguments",
"properties": {
"provider": {
"type": "string",
"title": "Provider",
"default": "github"
},
"return_path": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Return Path",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "get_github_install_urlDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description93/100
List CI triggers via GET /v1/ci/triggers.
Each trigger carries connection id, simulation_id, repository (owner/name),
environment, min_score, endpoint_template, enabled, last result, and
has_bypass_header (the header value is never returned). If the user has no
GitHub connection, call get_github_install_url and return that link.
Args:
simulation_id: Only triggers for this simulation. Omit for all.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 1 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description80/100
Run a simulation on every successful GitHub deployment via POST /v1/ci/triggers.
Needs a GitHub connection: if list_ci_connections is empty, call
get_github_install_url and return that link instead.
Args:
simulation_id: Simulation to run.
connection_id: Id from list_ci_connections.
repository: GitHub repository as "owner/name".
environment: Exact deployment environment name, such as "Production" or "Preview".
min_score: Pass mark from 0 to 100. Defaults to 100.
endpoint_template: Where the agent is under test for preview deployments. Omit to
run the saved agent as-is. Placeholders: {environment_url}, {environment_url_host},
{sha}, {short_sha}, {pr_number}, {environment}.
preview_host_suffix: Domain the rendered preview host must end with, such as "vercel.app".
Required when endpoint_template uses {environment_url} or {environment_url_host}.
bypass_header_name: Header name to pass a protected preview, such as
"x-vercel-protection-bypass".
bypass_header_value: Header value. Stored encrypted, never returned.
enabled: Whether the trigger fires. Defaults to true.
Describe the returned information so the agent knows whether it will answer the request.
Inputs0/100
0 of 10 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
simulation_id
Not provided
Missing description. Explain what this value means and how to supply it.
connection_id
Not provided
Missing description. Explain what this value means and how to supply it.
repository
Not provided
Missing description. Explain what this value means and how to supply it.
environment
Not provided
Missing description. Explain what this value means and how to supply it.
min_score
Not provided
Missing description. Explain what this value means and how to supply it.
endpoint_template
Not provided
Missing description. Explain what this value means and how to supply it.
preview_host_suffix
Not provided
Missing description. Explain what this value means and how to supply it.
bypass_header_name
Not provided
Missing description. Explain what this value means and how to supply it.
bypass_header_value
Not provided
Missing description. Explain what this value means and how to supply it.
enabled
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description78/100
Change a CI trigger via PATCH /v1/ci/triggers/{trigger_id}. Only given fields change.
Args:
trigger_id: Trigger to change.
repository: New GitHub repository, such as "owner/name".
environment: New deployment environment name.
min_score: New pass mark from 0 to 100.
endpoint_template: New preview endpoint template. Empty string clears it.
preview_host_suffix: New preview domain, such as "vercel.app". Required for URL placeholders. Empty string clears it.
bypass_header_name: New bypass header name. Empty string for both header fields clears the header.
bypass_header_value: New bypass header value. Stored encrypted, never returned.
enabled: Turn the trigger on or off.
Explain mutations, irreversible effects, or prerequisites that matter before calling this tool.
Inputs0/100
0 of 9 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
trigger_id
Not provided
Missing description. Explain what this value means and how to supply it.
repository
Not provided
Missing description. Explain what this value means and how to supply it.
environment
Not provided
Missing description. Explain what this value means and how to supply it.
min_score
Not provided
Missing description. Explain what this value means and how to supply it.
endpoint_template
Not provided
Missing description. Explain what this value means and how to supply it.
preview_host_suffix
Not provided
Missing description. Explain what this value means and how to supply it.
bypass_header_name
Not provided
Missing description. Explain what this value means and how to supply it.
bypass_header_value
Not provided
Missing description. Explain what this value means and how to supply it.
enabled
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations50/100
Declare idempotentHint, openWorldHint based on the tool’s actual behavior.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description97/100
Query this organization's production conversations (calls).
Takes the same filters as the in-app conversation query: status, agent_ids,
label_ids, initiation_direction, caller_number, duration_min and duration_max
in milliseconds, tags, conversation_ids, interface. `label` is a convenience
that resolves a label's text (a store, location or branch name) to its id.
`issue_ids` keeps calls linked to any listed issue; get IDs from GET /v1/issues.
Leave group_by unset to get conversation rows in `data`, each with
`metric_results` (how every metric scored that call), and `total` for
everything matching the filters. Set group_by for counts per group instead,
which is what a "how many" question needs:
- 'metric_value' with metric_name: how a metric came out, e.g. how many calls
were scored Readback Frustration. Find exact names with list_custom_metrics.
Returns not_applicable separately and an average for numeric metrics.
- 'label': per store, location or branch.
- 'metadata' with metadata_path: per store when the code is in call metadata
rather than a label, e.g. metadata_path='restaurant_code'.
- 'day': a trend over time.
- 'status', 'agent', 'interface', 'direction', 'ended_by': as named.
Filters combine with any grouping, so narrow first and then choose the
resolution. To count one metric for one store over a day: label='<store>',
metric_name='<metric>', group_by='metric_value', last='1day'.
To see the conversations where a metric came out a particular way, filter with
metric_name plus metric_value (or metric_min/metric_max for numeric metrics)
and leave group_by unset. That is the filter; group_by='metric_value' is the
count. Both take the same metric_name.
`last` accepts only 1day, 3days, 7days, 30days, 90days or all. Counts use the
human-corrected outcome wherever someone edited one, so they match the app.
Check groups_truncated: when true, more groups matched than were returned.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 24 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
status
Not provided
Missing description. Explain what this value means and how to supply it.
agent_ids
Not provided
Missing description. Explain what this value means and how to supply it.
label_ids
Not provided
Missing description. Explain what this value means and how to supply it.
label
Not provided
Missing description. Explain what this value means and how to supply it.
initiation_direction
Not provided
Missing description. Explain what this value means and how to supply it.
caller_number
Not provided
Missing description. Explain what this value means and how to supply it.
duration_min
Not provided
Missing description. Explain what this value means and how to supply it.
duration_max
Not provided
Missing description. Explain what this value means and how to supply it.
tags
Not provided
Missing description. Explain what this value means and how to supply it.
conversation_ids
Not provided
Missing description. Explain what this value means and how to supply it.
issue_ids
Not provided
Missing description. Explain what this value means and how to supply it.
interface
Not provided
Missing description. Explain what this value means and how to supply it.
metadata_path
Not provided
Missing description. Explain what this value means and how to supply it.
metadata_value
Not provided
Missing description. Explain what this value means and how to supply it.
metric_name
Not provided
Missing description. Explain what this value means and how to supply it.
metric_id
Not provided
Missing description. Explain what this value means and how to supply it.
metric_value
Not provided
Missing description. Explain what this value means and how to supply it.
metric_min
Not provided
Missing description. Explain what this value means and how to supply it.
metric_max
Not provided
Missing description. Explain what this value means and how to supply it.
group_by
Not provided
Missing description. Explain what this value means and how to supply it.
last
Not provided
Missing description. Explain what this value means and how to supply it.
sort_order
Not provided
Missing description. Explain what this value means and how to supply it.
page_size
Not provided
Missing description. Explain what this value means and how to supply it.
page
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
The title clearly communicates the tool’s action and subject. Keep it concise.
Description92/100
Open one production conversation: its transcript, tool calls, any error, and
how every metric scored it.
Use this once list_conversations points at a specific conversation, to see
what actually happened on it. Set include_transcript to false when only the
metric results and outcome are needed, which makes the read cheaper.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
conversation_id
Not provided
Missing description. Explain what this value means and how to supply it.
include_transcript
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema7/100
Declare the result fields and their types in the output schema.
{
"name": "get_conversation",
"title": "Get conversation",
"description": "\nOpen one production conversation: its transcript, tool calls, any error, and\nhow every metric scored it.\n\nUse this once list_conversations points at a specific conversation, to see\nwhat actually happened on it. Set include_transcript to false when only the\nmetric results and outcome are needed, which makes the read cheaper.\n",
"inputSchema": {
"type": "object",
"title": "get_conversationArguments",
"required": [
"conversation_id"
],
"properties": {
"conversation_id": {
"type": "string",
"title": "Conversation Id"
},
"include_transcript": {
"type": "boolean",
"title": "Include Transcript",
"default": true
}
}
},
"outputSchema": {
"type": "object",
"title": "get_conversationDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
The title clearly communicates the tool’s action and subject. Keep it concise.
Description99/100
Find this organization's traces, or count them, via Bluejay GET /v1/traces/search.
Every read covers one time window: `since` and `until` are ISO timestamps
(e.g. '2026-10-20T00:00:00Z'), at most 7 days apart. With neither set the
window is the last 7 days; with only since it is the 7 days after it. To look
further back (traces are kept 90 days), step since back a week at a time.
The response echoes the window it used. Filters:
- has_error: true for traces with at least one errored span, false for clean ones.
- service_name: the service of the trace's root span.
- root_span_name: the name of the trace's root span.
- error_span_name: traces where a span with this exact name errored,
e.g. 'execute_tool verify_identity'.
Leave group_by unset to get `traces`, newest first, each with trace_id,
service_name, root_span_name, start_time, duration_ms, span_count and
error_span_count, plus `total`: every trace matching the filters, not just
this page. For a single count ("how many traces errored this week"), read
`total` with limit=1.
Set group_by for counts per group instead, which is what a breakdown needs.
Each group has traces, errored_traces, spans, error_spans, avg_duration_ms
and p95_duration_ms, largest first:
- 'service_name' or 'root_span_name': as named, e.g. error rate per service.
- 'error_span_name': which spans fail most. A trace with several different
failing spans counts once in each.
- 'day' or 'hour' (UTC): a trend over time.
Filters combine with any grouping. To find what to analyze: group_by=
'error_span_name' with has_error=true, then list traces with that
error_span_name and open them with get_trace. `limit` caps traces, or groups
when group_by is set (default 20, max 100); groups_truncated is true when
more groups matched than were returned.
The description explains the capability, when to use it, and what to expect.
Inputs0/100
0 of 8 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values.
has_error
Not provided
Missing description. Explain what this value means and how to supply it.
service_name
Not provided
Missing description. Explain what this value means and how to supply it.
root_span_name
Not provided
Missing description. Explain what this value means and how to supply it.
error_span_name
Not provided
Missing description. Explain what this value means and how to supply it.
since
Not provided
Missing description. Explain what this value means and how to supply it.
until
Not provided
Missing description. Explain what this value means and how to supply it.
group_by
Not provided
Missing description. Explain what this value means and how to supply it.
limit
Not provided
Missing description. Explain what this value means and how to supply it.
Annotations25/100
Declare destructiveHint, idempotentHint, openWorldHint based on the tool’s actual behavior.
{
"readOnlyHint": true
}
Output schema3/100
Declare the result fields and their types in the output schema.
{
"name": "list_traces",
"title": "List traces",
"description": "\nFind this organization's traces, or count them, via Bluejay GET /v1/traces/search.\n\nEvery read covers one time window: `since` and `until` are ISO timestamps\n(e.g. '2026-10-20T00:00:00Z'), at most 7 days apart. With neither set the\nwindow is the last 7 days; with only since it is the 7 days after it. To look\nfurther back (traces are kept 90 days), step since back a week at a time.\nThe response echoes the window it used. Filters:\n\n- has_error: true for traces with at least one errored span, false for clean ones.\n- service_name: the service of the trace's root span.\n- root_span_name: the name of the trace's root span.\n- error_span_name: traces where a span with this exact name errored,\n e.g. 'execute_tool verify_identity'.\n\nLeave group_by unset to get `traces`, newest first, each with trace_id,\nservice_name, root_span_name, start_time, duration_ms, span_count and\nerror_span_count, plus `total`: every trace matching the filters, not just\nthis page. For a single count (\"how many traces errored this week\"), read\n`total` with limit=1.\n\nSet group_by for counts per group instead, which is what a breakdown needs.\nEach group has traces, errored_traces, spans, error_spans, avg_duration_ms\nand p95_duration_ms, largest first:\n\n- 'service_name' or 'root_span_name': as named, e.g. error rate per service.\n- 'error_span_name': which spans fail most. A trace with several different\n failing spans counts once in each.\n- 'day' or 'hour' (UTC): a trend over time.\n\nFilters combine with any grouping. To find what to analyze: group_by=\n'error_span_name' with has_error=true, then list traces with that\nerror_span_name and open them with get_trace. `limit` caps traces, or groups\nwhen group_by is set (default 20, max 100); groups_truncated is true when\nmore groups matched than were returned.\n",
"inputSchema": {
"type": "object",
"title": "list_tracesArguments",
"properties": {
"limit": {
"type": "integer",
"title": "Limit",
"default": 20
},
"since": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Since",
"default": null
},
"until": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Until",
"default": null
},
"group_by": {
"anyOf": [
{
"enum": [
"service_name",
"root_span_name",
"error_span_name",
"day",
"hour"
],
"type": "string"
},
{
"type": "null"
}
],
"title": "Group By",
"default": null
},
"has_error": {
"anyOf": [
{
"type": "boolean"
},
{
"type": "null"
}
],
"title": "Has Error",
"default": null
},
"service_name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Service Name",
"default": null
},
"root_span_name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Root Span Name",
"default": null
},
"error_span_name": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"title": "Error Span Name",
"default": null
}
}
},
"outputSchema": {
"type": "object",
"title": "list_tracesDictOutput",
"additionalProperties": true
},
"annotations": {
"readOnlyHint": true
}
}
Loading score analytics…
Put your MCP to the test
A few tasks worth trying with this server, chosen from its reviewed tools. These have not been run.
01List dashboardsList all dashboards in the organization, each with the 'url' that opens it in the app.
02List tracesFind this organization's traces, or count them, via Bluejay GET /v1/traces/search.
03List alertsList the organization's alerts via GET /v1/alerts.
04List digital humansList digital humans in your organization via Bluejay GET /v1/digital-humans (paginated).
05List widgetsList all widgets in the organization with their metrics.
Want to run these tasks against your MCP server with us?
bluejay setup, tools, quality score, publishing readiness, and alternatives.
How do I add bluejay to Claude, ChatGPT, or Cursor?
Add bluejay to Claude, ChatGPT, or Cursor by connecting its remote MCP URL in each client's MCP settings. In Claude, add a custom connector. In ChatGPT, add an MCP app. In Cursor, add an MCP server under Settings. The MCP URL is https://api.getbluejay.ai/mcp.
Is bluejay MCP ready for ChatGPT and Claude?
As of November 4, 2026, bluejay scores 90/100 on Manufact's MCP publishing checklist. The scan does not yet meet ChatGPT publishing checks and meets Claude publishing checks. Passing these checks does not guarantee marketplace approval.
How clear is bluejay's MCP tool documentation?
As of November 4, 2026, bluejay scores 53/100 in Manufact's review of tool titles, descriptions, input and output schemas, and behavior annotations. The review covers 161 of 161 discovered tools. The quality score measures documentation clarity; runtime behavior and marketplace readiness require separate checks.
What are the best alternatives to bluejay?
As of November 4, 2026, alternatives to bluejay in developer-tools on the Manufact MCP leaderboard include Speko, Manufact, AgentMail, Context, and DNS Inspector.
How can bluejay improve its MCP documentation?
list_prompts is the lowest-scoring reviewed tool at 25/100. 0 of 2 inputs have descriptions. Add descriptions to the missing inputs, including where to obtain IDs and how to supply values. Open its review for feedback and a copyable fix prompt, then rerun the documentation review after updating your tool metadata.
Not your MCP?
Review any public or OAuth MCP server for protocol compatibility, tool documentation, and ChatGPT and Claude publishing readiness. No account required.