Chat API
Interact with your minds through chat completions and multi-turn conversations.
Chat API
Send messages to your minds and receive AI-generated responses. The Chat API supports both stateless completions and stateful multi-turn conversations with automatic history management.
Stateful Chats (Recommended)
Create persistent conversations where the server manages history, context compression, and rolling summaries automatically. No need to send the full message history with each request.
Create a Chat
Create a new stateful conversation linked to a mind.
Endpoint: POST /api/v1/chats
Headers:
Authorization: Bearer minds_your_api_key
Content-Type: application/json
Request Body:
{
"name": "My Conversation",
"sparkId": "your-spark-id"
}
| Parameter | Type | Required | Description |
|---|---|---|---|
name | string | No | Display name for the chat (default: "API Chat") |
sparkId | string | No | The mind to chat with. If omitted, assign a mind later. |
description | string | No | Optional description |
Response (201):
{
"data": {
"id": "601af953-3837-49c1-a31e-4fdbfa82ac04",
"name": "My Conversation",
"description": null,
"createdAt": "2026-04-04T12:45:24.078Z",
"sparks": [
{
"id": "4774888e-0a03-40d7-979b-39b47c4c049c",
"name": "Ada Lovelace",
"discipline": "mathematician and computer scientist"
}
]
}
}
Send a Message
Send a message to an existing chat. The server automatically handles conversation history, context window compression, and rolling summaries.
Endpoint: POST /api/v1/chats/{chatId}/messages
Headers:
Authorization: Bearer minds_your_api_key
Content-Type: application/json
Request Body:
{
"content": "What are the latest advancements in solar panel technology?"
}
| Parameter | Type | Required | Description |
|---|---|---|---|
content | string | Yes | The message text (alternatively use message) |
Response:
{
"content": "Recent advancements in solar panel technology include perovskite cells with 30%+ efficiency...",
"messageId": "cmnkbsddh00033v01ptk9t4et"
}
| Field | Type | Description |
|---|---|---|
content | string | The mind's response |
messageId | string | Unique ID of the saved message |
Multi-Turn Example
With stateful chats, you just send the new message each time. The server remembers everything:
# Step 1: Create a chat
CHAT=$(curl -s -X POST "https://getminds.ai/api/v1/chats" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{ "name": "Research Session", "sparkId": "your-spark-id" }')
CHAT_ID=$(echo $CHAT | jq -r '.data.id')
# Step 2: Send messages (server manages history automatically)
curl -X POST "https://getminds.ai/api/v1/chats/$CHAT_ID/messages" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{ "content": "What are the top marketing trends?" }'
# Step 3: Follow up (the mind remembers the previous exchange)
curl -X POST "https://getminds.ai/api/v1/chats/$CHAT_ID/messages" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{ "content": "Which of those would work best on a small budget?" }'
How it works under the hood:
- Every message is persisted to the database
- The last 8 messages are sent in full context
- Older messages are compressed into a rolling LLM summary
- Conversations can run for weeks/months without hitting context limits
Stateless Completions
For single requests or when you want to manage conversation history yourself.
Send Message
Send messages to a mind and receive responses.
Endpoint: POST /api/v1/sparks/{sparkId}/completion
Headers:
Authorization: Bearer minds_your_api_key
Content-Type: application/json
Request Body
{
"messages": [
{
"role": "user",
"content": "What are the latest advancements in solar panel technology?"
}
]
}
Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
messages | array | No | Array of message objects (user, assistant, or tool). Omit the field entirely or send an empty array to trigger the greeting bootstrap (see Initial Message below). |
messages[].role | string | Yes | Either "user", "assistant", or "tool" |
messages[].content | string | Yes | The message text. Must be a non-empty string for user messages (whitespace is rejected with 400). Omit for tool role and use tool_call_id + content instead. |
model | string | No | Override the AI model used for this request. See model override below. |
provider | string | No | AI provider for the model override: openai, anthropic, or google. Auto-detected from model name when possible. |
language | string | No | Hint for response language. Supported: en, de, es, fr, zh, tr, ar. Strong personas (e.g. clones of public figures with a fixed native language) may continue to respond in their persona's language. |
generateImage | boolean | No | When true, enables AI image generation in the response if contextually appropriate |
response_format | object | No | Request structured output. See structured output below. |
tools | array | No | Array of user-defined tool definitions. See tool calling below. |
tool_choice | string|object | No | Control tool calling behavior. See tool choice modes. |
parallel_tool_calls | boolean | No | Allow multiple tool calls per turn (default: true). |
Response
{
"messageId": "msg_550e840029b141d4a716446655440000",
"content": "Recent advancements in solar panel technology include perovskite cells with 30%+ efficiency, bifacial panels that capture light from both sides, and integrated storage systems...",
"metadata": {
"ragCitations": [
{
"id": "abc123",
"displaySource": "Spark knowledge",
"similarity": 0.89
}
]
}
}
| Field | Type | Description |
|---|---|---|
messageId | string | Unique message identifier for tracking |
content | string | The mind's response text (JSON string when using structured output) |
parsed | object | Parsed JSON object (only present when using response_format) |
tool_calls | array | Array of tool call requests (only present when user-defined tools are called). Each has: id, name, arguments |
metadata | object | Optional metadata (citations, images, ideas) |
metadata.ragCitations | array | Knowledge sources and web search results used in the response |
Single Message Example
Ask a single question:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "What are the top 3 marketing trends for 2025?"
}
]
}'
Multi-Turn Conversation
Maintain conversation context by including previous messages:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "What are the top marketing trends?"
},
{
"role": "assistant",
"content": "The top trends are AI personalization, short-form video, and community building..."
},
{
"role": "user",
"content": "How can I implement AI personalization on a budget?"
}
]
}'
Tips for Multi-Turn Conversations:
- Include the full conversation history in each request
- Order matters: messages should be in chronological order
- Alternate between
userandassistantroles - The last message should always be from
user
File Attachments
Attach files, documents, images, and links to provide context for your minds. Minds receive the processed content as part of the conversation.
Attaching Files
Add files via the metadata.attachedFiles array in your user message:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "Please review this document and summarize the key points",
"metadata": {
"attachedFiles": [
{
"url": "https://example.com/quarterly-report.pdf",
"name": "Q4 2025 Report",
"type": "application/pdf"
},
{
"path": "uploads/meeting-notes.docx",
"name": "Strategy Meeting Notes"
}
]
}
}
]
}'
Attachment Format
Each attachment object supports:
| Field | Type | Required | Description |
|---|---|---|---|
url | string | No* | External URL to file (HTTP/HTTPS) |
path | string | No* | Supabase storage path (auto-signed) |
name | string | No | Display name for the file |
type | string | No | MIME type (e.g., application/pdf, image/png) |
description | string | No | Optional description |
transcription | string | No | Pre-transcribed audio/video content |
Note: Provide either url OR path, not both.
Supported File Types
Documents:
- PDF (
.pdf) - Text extraction + OCR for scanned pages - Word (
.docx) - Full text extraction - Text (
.txt,.md) - Direct text content - CSV/Excel (
.csv,.xlsx) - Table extraction
Images:
- PNG, JPG, WEBP - OCR + visual analysis
- Vision capabilities for image understanding
External URLs:
- Web pages fetched with Firecrawl (JS rendering + screenshots)
- Automatic markdown conversion
Processing
Files are automatically processed before being sent to the mind:
- Download - Files fetched from URL or Supabase storage
- Extract - Content extracted (text from PDFs, OCR from images, etc.)
- Inject - Processed content added to conversation context
- Response - Mind sees both your message and the file content
Processing limits:
- Timeout: 30 seconds per file
- Files processed in parallel
- Failed files show graceful fallback messages
Multiple File Example
{
"messages": [
{
"role": "user",
"content": "Compare these two proposals and recommend which one to pursue",
"metadata": {
"attachedFiles": [
{
"url": "https://example.com/proposal-a.pdf",
"name": "Proposal A - Cloud Migration",
"type": "application/pdf"
},
{
"url": "https://example.com/proposal-b.pdf",
"name": "Proposal B - On-Prem Upgrade",
"type": "application/pdf"
},
{
"path": "uploads/budget-analysis.xlsx",
"name": "Budget Comparison"
}
]
}
}
]
}
File Attachments in Conversation History
When continuing a conversation with file attachments, include the original message with attachments in the history:
{
"messages": [
{
"role": "user",
"content": "Analyze this sales data",
"metadata": {
"attachedFiles": [
{
"url": "https://example.com/sales-q4.csv",
"name": "Q4 Sales Data"
}
]
}
},
{
"role": "assistant",
"content": "Based on the Q4 sales data, I can see that revenue increased by 23% compared to Q3..."
},
{
"role": "user",
"content": "What were the top 3 performing products?"
}
]
}
Note: Files are only processed once when first attached. Subsequent messages in the same conversation reference the already-processed content.
Web Links
For web pages and external content, use the url field:
{
"messages": [
{
"role": "user",
"content": "Summarize the key findings from this research paper",
"metadata": {
"attachedFiles": [
{
"url": "https://arxiv.org/pdf/2103.12345.pdf",
"name": "AI Research Paper",
"type": "application/pdf"
}
]
}
}
]
}
For web pages specifically:
- JavaScript-heavy sites are rendered with Firecrawl
- Screenshots captured for visual context
- Content converted to clean markdown
Error Handling
If file processing fails:
- Mind receives a fallback message indicating the file was attached but processing failed
- Conversation continues normally
- Timeout errors show
[Processing timeout - file may be too large] - Other errors show
[Processing failed - file uploaded but analysis unavailable]
This ensures minds are aware of attempted attachments even if processing fails.
Initial Message (Greeting)
If you send an empty messages array or no messages, the mind will introduce itself:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": []
}'
Response:
{
"content": "Hi! I'm Sarah, a marketing director with 15 years of experience in B2B SaaS. I specialize in growth marketing and data-driven strategies. What can I help you with today?"
}
Model Override
You can optionally override the AI model used for a completion request by passing the model parameter. This is useful for benchmarking, cost optimization, or testing different model behaviors.
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "What are your thoughts on sustainable packaging?"
}
],
"model": "gpt-4o-mini"
}'
When no model is specified, the server default is used.
Providers
| Provider | Value | Example Models |
|---|---|---|
| OpenAI | openai | gpt-5.4, gpt-5.3, gpt-5-mini, gpt-4o, gpt-4o-mini, o3, o3-pro, o3-mini, o4-mini |
| Anthropic | anthropic | claude-opus-4-6, claude-sonnet-4-6, claude-haiku-4-5 |
google | gemini-3.1-pro-preview, gemini-3-flash-preview, gemini-2.5-pro, gemini-2.5-flash, gemini-2.5-flash-lite |
You can pass any model string supported by the provider. The provider is auto-detected from common model name prefixes (claude- → Anthropic, gemini- → Google, gpt-/o1/o3/o4 → OpenAI).
For models with ambiguous names, specify the provider explicitly:
{
"messages": [...],
"model": "my-custom-fine-tune",
"provider": "openai"
}
If the provider cannot be determined, the API returns a 400 Bad Request error asking you to specify it.
Structured Output
Request guaranteed JSON responses that match a specific schema using the response_format parameter. This follows the OpenAI-style structured output pattern and is useful for extracting structured data from conversations.
JSON Schema Mode
Force the model to output valid JSON matching your schema:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "Analyze the sentiment of this text: I love this product, it exceeded all my expectations!"
}
],
"response_format": {
"type": "json_schema",
"json_schema": {
"name": "sentiment_analysis",
"description": "Sentiment analysis result",
"schema": {
"type": "object",
"properties": {
"sentiment": {
"type": "string",
"enum": ["positive", "negative", "neutral"]
},
"confidence": {
"type": "number",
"minimum": 0,
"maximum": 1
},
"keywords": {
"type": "array",
"items": { "type": "string" }
}
},
"required": ["sentiment", "confidence", "keywords"]
}
}
}
}'
Response:
{
"content": "{\"sentiment\": \"positive\", \"confidence\": 0.95, \"keywords\": [\"love\", \"exceeded\", \"expectations\"]}",
"parsed": {
"sentiment": "positive",
"confidence": 0.95,
"keywords": ["love", "exceeded", "expectations"]
}
}
JSON Object Mode
Force JSON output without schema validation:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "List 3 marketing ideas as JSON"
}
],
"response_format": {
"type": "json_object"
}
}'
Response Format Types
| Type | Description |
|---|---|
text | Default text output (current behavior) |
json_object | Forces valid JSON output without schema validation |
json_schema | Forces JSON output matching the provided schema |
JSON Schema Fields
| Field | Type | Required | Description |
|---|---|---|---|
name | string | Yes | Identifier for the schema |
description | string | No | Description of what the schema represents |
schema | object | Yes | JSON Schema definition |
strict | boolean | No | Enforce strict schema adherence (default: true) |
Supported Schema Features
The following JSON Schema features are supported:
- Types:
string,number,integer,boolean,array,object,null - Constraints:
enum,minimum,maximum,minLength,maxLength,minItems,maxItems - Structure:
properties,required,items,additionalProperties - Metadata:
description(used to guide the model)
Notes
- Tools (RAG, web search, etc.) work with structured output — the mind can still search its knowledge base before generating the structured response
- The
parsedfield contains the parsed JSON object for convenience;contentcontains the raw JSON string - All major providers (OpenAI, Anthropic, Google) support structured output
- For complex schemas, consider adding
descriptionfields to guide the model's output
Tool Calling
Enable minds to call your custom functions during conversations. This follows the OpenAI-compatible function calling pattern and lets you extend minds' capabilities with external tools and APIs.
How It Works
- Define tools: Pass tool definitions with names, descriptions, and JSON Schema parameters
- Mind decides: The mind determines when to call your tools based on the conversation (or you force it with
tool_choice) - API returns tool calls: The response includes
tool_callswith the tool name and generated arguments - Execute tools: You run the tools in your application and get the results
- Send results back: Include tool results in the next message with
role: "tool" - Mind responds: The mind incorporates the tool results into its final response
Basic Example
Request with tools:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "What is the weather in Berlin?"
}
],
"tools": [
{
"name": "get_weather",
"description": "Get current weather for a city",
"parameters": {
"type": "object",
"properties": {
"city": {
"type": "string",
"description": "City name"
},
"units": {
"type": "string",
"enum": ["celsius", "fahrenheit"],
"description": "Temperature units"
}
},
"required": ["city"]
}
}
]
}'
Response:
{
"content": "",
"tool_calls": [
{
"id": "call_abc123",
"name": "get_weather",
"arguments": {
"city": "Berlin",
"units": "celsius"
}
}
]
}
Execute the tool and send results back:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "What is the weather in Berlin?"
},
{
"role": "assistant",
"content": "",
"tool_calls": [
{
"id": "call_abc123",
"name": "get_weather",
"arguments": {
"city": "Berlin",
"units": "celsius"
}
}
]
},
{
"role": "tool",
"tool_call_id": "call_abc123",
"content": "{\"temperature\": 18, \"condition\": \"partly cloudy\", \"humidity\": 65}"
}
],
"tools": [
{
"name": "get_weather",
"description": "Get current weather for a city",
"parameters": {
"type": "object",
"properties": {
"city": { "type": "string" },
"units": { "type": "string", "enum": ["celsius", "fahrenheit"] }
},
"required": ["city"]
}
}
]
}'
Final response:
{
"content": "The current weather in Berlin is 18°C and partly cloudy, with 65% humidity."
}
Tool Definition Schema
Each tool must follow this structure:
{
"name": "tool_name",
"description": "Clear description of when and how to use this tool",
"parameters": {
"type": "object",
"properties": {
"param1": {
"type": "string",
"description": "What this parameter does"
}
},
"required": ["param1"]
},
"strict": true
}
Required fields:
| Field | Type | Description |
|---|---|---|
name | string | Function name. Must be unique and cannot conflict with internal tools. |
description | string | Clear description of what the tool does and when to use it. This guides the mind's tool selection. |
parameters | object | JSON Schema defining the function arguments. |
Optional fields:
| Field | Type | Default | Description |
|---|---|---|---|
strict | boolean | true | Enforce strict schema validation for arguments. |
Tool Choice Modes
Control when and how the mind calls tools using the tool_choice parameter:
| Value | Behavior |
|---|---|
"auto" | Mind decides whether to call tools (default) |
"required" | Mind must call at least one tool before responding |
"none" | Disable tool calling for this turn |
{"name": "tool_name"} | Force the mind to call a specific tool |
Examples:
// Let the mind decide
{
"messages": [...],
"tools": [...],
"tool_choice": "auto"
}
// Force a specific tool
{
"messages": [...],
"tools": [...],
"tool_choice": {
"name": "search_database"
}
}
// Require at least one tool call
{
"messages": [...],
"tools": [...],
"tool_choice": "required"
}
Parallel Tool Calls
By default, minds can call multiple tools in a single turn for efficiency:
{
"content": "",
"tool_calls": [
{
"id": "call_1",
"name": "get_customer",
"arguments": { "id": "CUST-001" }
},
{
"id": "call_2",
"name": "get_customer",
"arguments": { "id": "CUST-002" }
}
]
}
To disable parallel calls and force sequential execution:
{
"messages": [...],
"tools": [...],
"parallel_tool_calls": false
}
Tool Message Format
When sending tool results back, use the tool role:
{
"role": "tool",
"tool_call_id": "call_abc123",
"content": "{\"result\": \"success\", \"data\": {...}}"
}
| Field | Type | Required | Description |
|---|---|---|---|
role | string | Yes | Must be "tool" |
tool_call_id | string | Yes | The id from the tool call in the assistant's response |
content | string | Yes | Tool execution result (typically JSON string) |
Internal vs User Tools
Minds has built-in server-side tools that execute automatically:
| Internal Tool | Purpose |
|---|---|
GET_SPARK_RAG | Search the mind's knowledge base |
WEB_SEARCH | Search the web |
GENERATE_IMAGE | Generate images with AI |
DISPLAY_IMAGE | Display images from the mind's memory |
DOCUMENT_PROCESSING | Analyze uploaded files |
ANALYZE_LINK | Fetch and analyze web URLs |
Key differences:
- Internal tools: Execute server-side, results included in
contentandmetadata. Never returned intool_calls. - User tools: Returned in
tool_callsfor you to execute. Results must be sent back astoolmessages.
You cannot override or disable internal tools. User tools are additive — they extend the mind's capabilities.
Complete Multi-Tool Example
A legal assistant mind with multiple custom tools:
curl -X POST "https://getminds.ai/api/v1/sparks/spark-id/completion" \
-H "Authorization: Bearer minds_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"messages": [
{
"role": "user",
"content": "Create a new case for Schmidt vs. Mueller and search for similar precedents"
}
],
"tools": [
{
"name": "create_case",
"description": "Create a new legal case in the system",
"parameters": {
"type": "object",
"properties": {
"title": {
"type": "string",
"description": "Case title (parties involved)"
},
"practice_area": {
"type": "string",
"enum": ["corporate", "litigation", "employment", "ip"],
"description": "Legal practice area"
},
"client_id": {
"type": "string",
"description": "Client identifier"
}
},
"required": ["title", "practice_area"]
}
},
{
"name": "search_precedents",
"description": "Search legal database for similar cases",
"parameters": {
"type": "object",
"properties": {
"keywords": {
"type": "array",
"items": { "type": "string" },
"description": "Search keywords"
},
"practice_area": {
"type": "string",
"description": "Filter by practice area"
},
"max_results": {
"type": "integer",
"minimum": 1,
"maximum": 50,
"description": "Maximum number of results"
}
},
"required": ["keywords"]
}
}
],
"parallel_tool_calls": true
}'
Response with parallel tool calls:
{
"content": "",
"tool_calls": [
{
"id": "call_1",
"name": "create_case",
"arguments": {
"title": "Schmidt vs. Mueller",
"practice_area": "litigation"
}
},
{
"id": "call_2",
"name": "search_precedents",
"arguments": {
"keywords": ["Schmidt", "Mueller"],
"practice_area": "litigation",
"max_results": 10
}
}
]
}
Best Practices
- Write clear descriptions: The
descriptionfield is critical. Be specific about when and why to use each tool.❌ "description": "Search database" ✅ "description": "Search the legal precedents database for similar cases based on keywords and practice area" - Use parameter descriptions: Help the mind understand what each parameter does.
"case_id": { "type": "string", "description": "Unique case identifier in format CASE-YYYY-NNNN" } - Leverage enums for constrained values:
"status": { "type": "string", "enum": ["pending", "active", "closed", "archived"] } - Set validation constraints:
"priority": { "type": "integer", "minimum": 1, "maximum": 5, "description": "Priority level (1=lowest, 5=highest)" } - Enable strict mode: Keep
strict: true(default) to ensure the mind generates valid arguments. - Return structured tool results: Use JSON for tool results to make them easy to parse:
{ "role": "tool", "tool_call_id": "call_123", "content": "{\"success\": true, \"case_id\": \"CASE-2026-001\", \"created_at\": \"2026-03-30T23:00:00Z\"}" } - Handle errors gracefully: Return error details in the tool result:
{ "role": "tool", "tool_call_id": "call_123", "content": "{\"success\": false, \"error\": \"Case already exists\", \"error_code\": \"DUPLICATE_CASE\"}" }
Limitations
- Maximum 128 tools per request
- Tool names must be unique and cannot conflict with internal tool names
- Tool execution happens client-side — you are responsible for running and securing your tools
- Tool results must be sent back in the conversation history for the mind to respond
JSON Schema Support
The parameters field supports standard JSON Schema features:
Types:
string,number,integer,boolean,array,object,null
Validation:
enum— Restrict to specific valuesminimum,maximum— Numeric boundsminLength,maxLength— String lengthminItems,maxItems— Array sizepattern— Regex validationformat— String formats (e.g.,"date-time","email","uri")
Structure:
properties— Object propertiesrequired— Required fieldsitems— Array item schemaadditionalProperties— Allow/disallow extra properties
Example with advanced validation:
{
"name": "schedule_meeting",
"description": "Schedule a meeting with a client",
"parameters": {
"type": "object",
"properties": {
"title": {
"type": "string",
"minLength": 1,
"maxLength": 200
},
"date": {
"type": "string",
"format": "date-time",
"description": "Meeting date and time in ISO 8601 format"
},
"attendees": {
"type": "array",
"items": {
"type": "string",
"format": "email"
},
"minItems": 1,
"maxItems": 20
},
"duration_minutes": {
"type": "integer",
"minimum": 15,
"maximum": 480,
"description": "Meeting duration (15-480 minutes)"
}
},
"required": ["title", "date", "attendees"]
}
}
How It Works
1. Context Loading
When you send a message, the mind:
- Loads its system prompt and configuration
- Automatically searches its knowledge base for relevant information
- Considers the conversation history
2. Processing
The mind:
- Analyzes your message in context
- Grounds responses in retrieved knowledge with citations
- Accesses additional tools (web search, image generation, etc.) if needed
- Formulates a response aligned with its personality
3. Response Generation
The mind:
- Generates a response that reflects its expertise
- Includes citations when using knowledge base or web sources
- Returns the message with optional metadata (citations, images, etc.)
Metadata
Responses can include additional metadata:
Images
When a mind generates or displays images:
{
"content": "Here are some logo concepts...",
"metadata": {
"images": [
{
"id": "img_123",
"url": "https://...",
"filename": "Logo Concept 1",
"description": "Modern minimalist logo with blue gradient",
"source": "generated"
}
]
}
}
Ideas
When a mind creates flow ideas:
{
"content": "I've created a campaign concept...",
"metadata": {
"ideas": [
{
"id": "idea_123",
"title": "Summer Campaign 2025",
"description": "Eco-friendly summer campaign targeting millennials",
"status": "draft"
}
]
}
}
Knowledge Citations
When a mind retrieves information from its knowledge base or web search:
{
"content": "Based on recent research, solar panel efficiency has improved significantly...",
"metadata": {
"ragCitations": [
{
"id": "9bf44ab0-9d83-42ec-b941-c0ab7610e949",
"displaySource": "Spark knowledge",
"similarity": 0.85
},
{
"id": "external-web-123",
"displaySource": "https://example.com/solar-research",
"similarity": 0.92
}
]
}
}
Citation Fields:
id- Unique identifier for the sourcedisplaySource- Human-readable source name or URLsimilarity- Relevance score (0-1) indicating how well the source matches the query
Minds automatically search their knowledge base before responding and include citations when grounding their answers in specific sources.
Access Control
You can chat with minds you:
- Own - Minds you created
- Have access to - Minds shared with you by team members
- Are a member of - Minds in team workspaces you belong to
- Public minds - Publicly accessible minds
Attempting to access unauthorized minds returns:
{
"statusCode": 403,
"statusMessage": "Access denied"
}
Response Formats
Text Response
Most responses are plain text:
{
"content": "Based on current trends, I recommend focusing on..."
}
Structured Response
Some minds may return structured content:
{
"content": "Here's my analysis:\n\n1. Trend: AI Personalization\n - Impact: High\n - Timeline: 6-12 months\n\n2. Trend: Short-form Video\n - Impact: Very High\n - Timeline: Immediate"
}
Empty Response with Metadata
Sometimes only metadata is returned (e.g., for image generation):
{
"content": "",
"metadata": {
"images": [...]
}
}
Best Practices
Be Specific
❌ "Tell me about marketing"
✅ "What are the most cost-effective digital marketing channels for a B2B SaaS startup with a $5K monthly budget?"
Provide Context
✅ "We're launching a sustainable fashion brand targeting Gen Z. What social media strategy would you recommend?"
Use Follow-ups
Take advantage of conversation memory:
User: "What are the top trends?"
Assistant: "The top trends are..."
User: "Which of these would work best for a small budget?"
Assistant: "For a small budget, I'd focus on..."
Reference Knowledge
If you've uploaded knowledge, reference it:
✅ "Based on our brand guidelines, what tone should we use for this campaign?"
Error Responses
400 Bad Request
Missing or invalid spark ID:
{
"statusCode": 400,
"statusMessage": "Spark ID is required"
}
Unsupported provider:
{
"statusCode": 400,
"statusMessage": "Unsupported provider: 'invalid'. Supported providers: openai, anthropic, google."
}
Ambiguous model name without provider:
{
"statusCode": 400,
"statusMessage": "Cannot auto-detect provider for model 'my-model'. Please specify a 'provider' parameter (openai, anthropic, or google)."
}
401 Unauthorized
Invalid API key.
403 Forbidden
Access denied to spark:
{
"statusCode": 403,
"statusMessage": "Access denied"
}
404 Not Found
Spark doesn't exist:
{
"statusCode": 404,
"statusMessage": "Spark not found"
}
Usage Notes
- The API does not currently enforce rate limits
- However, please be respectful of server resources
- Excessive usage may result in throttling or account suspension
Next Steps
- Understand latency and performance
- Learn about errors and rate limits
- Create your first mind
- Upload knowledge to enhance responses
- Read the API overview