Skip to content

Agent Configuration

An agent in Alquimia is fully described by an AssistantConfig JSON document. This document is stored in the registry and loaded at inference time.

{
"assistant_id": "my-agent",
"nickname": "Helper",
"description": "A helpful assistant.",
"tags": ["support", "v2"],
"channels": [...],
"shields": {...},
"empathy": {...},
"response": {
"provider_id": "alquimia",
"config": {...},
"profile": {...}
}
}
FieldTypeRequiredDescription
assistant_idstringYesUnique identifier
nicknamestringNoDisplay name (max 64 chars)
descriptionstringNoHuman-readable description (max 3000 chars)
tagsstring[]NoLabels for filtering and discovery
channelsChannel[]NoMessaging channel integrations (WhatsApp, Slack, Email)
shieldsdict[str, Shield]NoPre-inference guard models
empathyEmpathyEngineNoContext-aware profile switching
responseResponseProfileYesThe main LLM configuration and behavior profile

The response field is the core of the agent configuration:

{
"response": {
"provider_id": "alquimia",
"config": {
"provider_id": "generative",
"connector": {
"provider_id": "openai",
"model": "gpt-4o",
"api_key": { "$secretRef": "OPENAI_API_KEY" }
}
},
"profile": {
"system_prompt": "You are a helpful assistant.",
"evaluation_strategy": { "evaluation_strategy_id": "one-shoot" },
"short_term_memory_strategy": [...],
"long_term_memory_strategy": [...],
"knowledge_base": [...],
"tools": [...],
"persistence_strategy": "INCREMENTAL"
}
}
}
FieldTypeDefaultDescription
system_promptstringnullJinja2 template for the system message
prompt_clausesdict[str, str]nullAdditional named sections injected into the system prompt
evaluation_strategyEvaluationStrategyone-shootHow to interpret LLM responses
short_term_memory_strategyShortTermMemoryStrategy[]nullToken windowing for conversation history
long_term_memory_strategyLongTermMemoryStrategy[]nullSummarization or erasure of old context
knowledge_baseKnowledgeBase[]nullRAG sources (Qdrant vector stores)
toolsToolConfig[]nullMCP, Llama Stack, or A2A tool sources
persistence_strategystringINCREMENTALHow to persist conversation state
ValueBehavior
INCREMENTALAppend new messages to the existing session
FLUSHReplace the session with the current conversation
EPHEMERALDo not persist — session is lost after inference

System prompts are Jinja2 templates. Alquimia automatically injects:

  • {{ rag_context }} — retrieved knowledge base chunks
  • {{ attachment_context }} — uploaded file content
  • {{ evaluation_strategy.prompt_clauses }} — strategy-specific instructions
  • {{ prompt_clauses }} — custom named sections
  • {{ runtime_context.prompt_clauses }} — dynamic runtime state (plan, condensed context)

Example:

You are a support agent for Acme Corp.
{% if rag_context %}
# Knowledge base
<context>{{ '\n'.join(rag_context) }}</context>
{% endif %}
Always respond in {{ language }}.

Sensitive values are referenced with $secretRef markers:

{
"api_key": { "$secretRef": "OPENAI_API_KEY" }
}

At runtime, the secret resolver substitutes the actual value. The resolver is selected via ALQUIMIA_REGISTRY_SECRET_RESOLVER:

ResolverBackendKey format
envEnvironment variablesOPENAI_API_KEY
vaultHashiCorp Vault KV v2OPENAI_API_KEY

Secrets are scoped:

ScopeResolution pattern
global{KEY}
shared{realm}_{KEY}
local{realm}_{assistant_id}_{KEY}

Shields are pre-inference classifiers that run before the main LLM call. Their output is available to the Empathy Engine for profile switching.

{
"shields": {
"language_detector": {
"provider_id": "huggingface/text-classification",
"model": "papluca/xlm-roberta-base-language-detection",
"endpoint": "https://api-inference.huggingface.co/models/..."
}
}
}

The Empathy Engine evaluates rules against shield outputs and runtime context to dynamically switch the response profile:

{
"empathy": {
"rules": [
{
"rule_id": "spanish-override",
"strategy": "merge",
"conditions": ["shields['language_detector'].label == 'es'"],
"requirements": ["shields"],
"response": {
"provider_id": "alquimia",
"profile": {
"system_prompt": "Eres un asistente útil. Responde siempre en español."
}
}
}
]
}
}
StrategyBehavior
noneMatch but do not change the profile
overrideReplace the entire response profile
mergeDeep-merge the rule’s profile into the main profile