curl --request POST \
--url https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue \
--header 'Content-Type: application/json' \
--data '
{
"npc_context": "Dwarf innkeeper, gruff but kind, knows local rumors",
"npc_name": "Grognard the Innkeeper",
"player_message": "What do you know about the forest to the north?",
"situation": "Player asks about the haunted forest",
"tone": "cautious"
}
'import requests
url = "https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue"
payload = {
"npc_context": "Dwarf innkeeper, gruff but kind, knows local rumors",
"npc_name": "Grognard the Innkeeper",
"player_message": "What do you know about the forest to the north?",
"situation": "Player asks about the haunted forest",
"tone": "cautious"
}
headers = {"Content-Type": "application/json"}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({
npc_context: 'Dwarf innkeeper, gruff but kind, knows local rumors',
npc_name: 'Grognard the Innkeeper',
player_message: 'What do you know about the forest to the north?',
situation: 'Player asks about the haunted forest',
tone: 'cautious'
})
};
fetch('https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'npc_context' => 'Dwarf innkeeper, gruff but kind, knows local rumors',
'npc_name' => 'Grognard the Innkeeper',
'player_message' => 'What do you know about the forest to the north?',
'situation' => 'Player asks about the haunted forest',
'tone' => 'cautious'
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue"
payload := strings.NewReader("{\n \"npc_context\": \"Dwarf innkeeper, gruff but kind, knows local rumors\",\n \"npc_name\": \"Grognard the Innkeeper\",\n \"player_message\": \"What do you know about the forest to the north?\",\n \"situation\": \"Player asks about the haunted forest\",\n \"tone\": \"cautious\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue")
.header("Content-Type", "application/json")
.body("{\n \"npc_context\": \"Dwarf innkeeper, gruff but kind, knows local rumors\",\n \"npc_name\": \"Grognard the Innkeeper\",\n \"player_message\": \"What do you know about the forest to the north?\",\n \"situation\": \"Player asks about the haunted forest\",\n \"tone\": \"cautious\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Content-Type"] = 'application/json'
request.body = "{\n \"npc_context\": \"Dwarf innkeeper, gruff but kind, knows local rumors\",\n \"npc_name\": \"Grognard the Innkeeper\",\n \"player_message\": \"What do you know about the forest to the north?\",\n \"situation\": \"Player asks about the haunted forest\",\n \"tone\": \"cautious\"\n}"
response = http.request(request)
puts response.read_body{
"dialogue": "Aye, I wouldn't go near those woods if I were ye...",
"mood": "worried",
"stage_direction": "leans in close, lowers voice",
"suggested_actions": [
"Ask about specific dangers",
"Ask who else has been there"
]
}{
"error": "Not found",
"code": "not_found",
"request_id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
"message": "The requested resource does not exist.",
"doc_url": "https://docs.kitefrost.ai/errors/not_found"
}{
"error": "Internal server error",
"code": "internal_error",
"request_id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
"message": "An unexpected error occurred.",
"doc_url": "https://docs.kitefrost.ai/errors/internal_error"
}Generate quick NPC dialogue
Synchronous NPC dialogue generation for real-time use (e.g. Foundry VTT). Makes a single LLM call (economy tier, quick-dialogue pack) and returns within 1-3 seconds. No session creation or polling required. Requires a valid Bearer token.
The response includes the NPC’s spoken dialogue, their current mood, a stage_direction for the GM, and suggested_actions as follow-up hints.
curl --request POST \
--url https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue \
--header 'Content-Type: application/json' \
--data '
{
"npc_context": "Dwarf innkeeper, gruff but kind, knows local rumors",
"npc_name": "Grognard the Innkeeper",
"player_message": "What do you know about the forest to the north?",
"situation": "Player asks about the haunted forest",
"tone": "cautious"
}
'import requests
url = "https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue"
payload = {
"npc_context": "Dwarf innkeeper, gruff but kind, knows local rumors",
"npc_name": "Grognard the Innkeeper",
"player_message": "What do you know about the forest to the north?",
"situation": "Player asks about the haunted forest",
"tone": "cautious"
}
headers = {"Content-Type": "application/json"}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({
npc_context: 'Dwarf innkeeper, gruff but kind, knows local rumors',
npc_name: 'Grognard the Innkeeper',
player_message: 'What do you know about the forest to the north?',
situation: 'Player asks about the haunted forest',
tone: 'cautious'
})
};
fetch('https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'npc_context' => 'Dwarf innkeeper, gruff but kind, knows local rumors',
'npc_name' => 'Grognard the Innkeeper',
'player_message' => 'What do you know about the forest to the north?',
'situation' => 'Player asks about the haunted forest',
'tone' => 'cautious'
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue"
payload := strings.NewReader("{\n \"npc_context\": \"Dwarf innkeeper, gruff but kind, knows local rumors\",\n \"npc_name\": \"Grognard the Innkeeper\",\n \"player_message\": \"What do you know about the forest to the north?\",\n \"situation\": \"Player asks about the haunted forest\",\n \"tone\": \"cautious\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue")
.header("Content-Type", "application/json")
.body("{\n \"npc_context\": \"Dwarf innkeeper, gruff but kind, knows local rumors\",\n \"npc_name\": \"Grognard the Innkeeper\",\n \"player_message\": \"What do you know about the forest to the north?\",\n \"situation\": \"Player asks about the haunted forest\",\n \"tone\": \"cautious\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api-staging.kitefrost.ai/v1/projects/{project_id}/quick-dialogue")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Content-Type"] = 'application/json'
request.body = "{\n \"npc_context\": \"Dwarf innkeeper, gruff but kind, knows local rumors\",\n \"npc_name\": \"Grognard the Innkeeper\",\n \"player_message\": \"What do you know about the forest to the north?\",\n \"situation\": \"Player asks about the haunted forest\",\n \"tone\": \"cautious\"\n}"
response = http.request(request)
puts response.read_body{
"dialogue": "Aye, I wouldn't go near those woods if I were ye...",
"mood": "worried",
"stage_direction": "leans in close, lowers voice",
"suggested_actions": [
"Ask about specific dangers",
"Ask who else has been there"
]
}{
"error": "Not found",
"code": "not_found",
"request_id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
"message": "The requested resource does not exist.",
"doc_url": "https://docs.kitefrost.ai/errors/not_found"
}{
"error": "Internal server error",
"code": "internal_error",
"request_id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
"message": "An unexpected error occurred.",
"doc_url": "https://docs.kitefrost.ai/errors/internal_error"
}Body
POST /v1/projects/{project_id}/quick-dialogue
Synchronous NPC dialogue generation - single LLM call, 1-3 sec response. Bypasses CoreRuntimeGraph; no session creation, no event sourcing.
Design reference: docs/discovery/foundry-vtt-module/4-decide/concepts-extracted.md
Display name of the NPC
1 - 100What the player just said or did.
1 - 500Free-text or structured description of the NPC (race, alignment, traits, biography). Accepts either a plain string or a JSON object from Actor Context Extraction.
GM-provided situational context (location, stakes, mood of scene).
500Desired emotional tone: neutral, friendly, hostile, cautious, suspicious, etc.
50Game system identifier (dnd5e, pf2e, generic).
20Maximum tokens for the LLM response (50-500).
50 <= x <= 500Response
NPC dialogue generated successfully
200 response for POST /v1/projects/{project_id}/quick-dialogue.
The NPC's spoken words (inline stage directions stripped out).
NPC's current emotional state, e.g. 'worried'.
Behavioral/visual description for the GM, e.g. 'leans in close, lowers voice'.
GM hints for follow-up player actions.