Skip to main content

Configuration

How do you configure an agentic workflow without repeating yourself across dozens of actions? Agent Actions uses a three-level configuration hierarchy that lets you set defaults once and override them where needed. Higher specificity wins—action settings override agentic workflow defaults, which override project defaults.

Think of it like CSS specificity: project settings are the base styles, agentic workflow defaults are class-level overrides, and action-specific settings are inline styles that take precedence.

The diagram below shows how configuration cascades from project-level down to individual actions:

Notice that the most specific level (action inline fields) has final say. This means you can establish sensible defaults project-wide but still customize individual actions when needed.

Project Configuration​

The agent_actions.yml file in your project root defines global settings:

yaml
YAML
# agent_actions.yml
default_agent_config:
api_key: OPENAI_API_KEY
model_name: gpt-4o-mini
model_vendor: openai
chunk_config:
chunk_size: 4000
chunk_overlap: 500

schema_path: schema
tool_path: ["tools"]
seed_data_path: seed_data
required_by_default: false
FieldDescription
default_agent_configDefault settings inherited by all actions, including chunk_config — see Chunking. Only keys nested here reach an action; a chunk_config: at the file's top level is read by nothing
schema_pathDirectory containing output schemas (default: schema)
tool_pathDirectories to scan for custom tools
seed_data_pathDirectory for static reference data (default: seed_data)
required_by_defaultWhen true, flat schema fields (fields: list) are required unless marked optional: true; when false (default) they are optional unless marked required: true. Applies project-wide; a schema declaring its own required_by_default overrides it.

Agentic Workflow Configuration​

Each agentic workflow YAML file defines defaults and actions. Let's explore how an agentic workflow brings together model settings, execution modes, and action definitions:

yaml
YAML
# agent_config/my_workflow.yml
name: my_workflow
description: "Extract and validate facts"
# version: "1.0.0" # Optional — for your own bookkeeping

defaults:
model_vendor: openai
model_name: gpt-4o-mini
json_mode: true
granularity: Record
run_mode: batch

actions:
- name: extract_facts
prompt: $prompts.extract_facts
schema: facts_schema

The top level takes exactly these keys, and refuses any other — a misspelled defaults: would otherwise be dropped in silence, taking every setting in the block with it:

KeyMeaning
nameWorkflow name (required)
descriptionWorkflow description (required)
versionOptional, for your own bookkeeping
defaultsSettings inherited by every action
actionsThe actions themselves (required)
tool_pathWhere this workflow's UDFs live. Takes precedence over the default config and over tool_path in agent_actions.yml
storageMaintenance knobs: prompt_trace_retention_runs and source_data_ttl_days. Despite the first one's name its unit is calendar days, not runs. 0 means never prune; omitting a key takes the framework default, which for traces is 10 days and does prune

Model settings such as model_vendor belong under defaults:, not at the top level.

See Defaults for the complete inheritance system.

Action Configuration​

Each action can override any default. Consider what happens when you need one action to use a different model or run in a different mode—you simply specify those fields on the action itself:

yaml
YAML
actions:
- name: extract_facts
intent: "Extract key facts from content"
dependencies: [prior_action] # Input source

# Model
model_vendor: openai
model_name: gpt-4o-mini

# Prompt & Schema
prompt: $prompts.extract_facts
schema: facts_schema
json_mode: true

# Execution
run_mode: batch
granularity: Record

# Conditional
guard:
condition: "source.content != ''"
on_false: filter

Core Action Fields​

FieldTypeDescription
namestringUnique action identifier
intentstringHuman-readable description
kindstringllm (default) or tool
dependencieslistUpstream actions to wait for
promptstringInline prompt or $store.template reference
schemastringOutput validation schema
context_scopeobjectControl data visibility: observe, drop, passthrough, seed — see Context Scope

Model Fields​

FieldTypeDescription
model_vendorstringProvider: openai, anthropic, google, groq, cohere, ollama_local, ollama_cloud
model_namestringModel identifier (e.g., gpt-4o-mini)
api_keystringEnvironment variable name for API key
temperaturefloatLLM temperature (0.0-2.0)
max_tokensintegerMaximum response tokens
top_pfloatTop-p (nucleus) sampling (0.0-1.0)
stopstring/listStop sequence(s) to end generation

:::note Vendor-Specific Parameter Mapping Generation parameters (temperature, max_tokens, top_p, stop) are mapped to vendor-specific API keys automatically:

  • OpenAI / Groq: Parameters passed through as-is. OpenAI and Groq also support frequency_penalty and presence_penalty.
  • Anthropic: stop → stop_sequences (string values are wrapped in a list)
  • Gemini: max_tokens → max_output_tokens, stop → stop_sequences
  • Cohere: top_p → p, stop → stop_sequences
  • Ollama: max_tokens → num_predict, parameters placed in options dict. stop strings are wrapped in a list. :::

Execution Fields​

FieldTypeDescription
run_modestringonline or batch — see Run Modes
granularitystringrecord or file — see Granularity
guardobjectConditional execution — see Guards
is_operationalbooleanEnable/disable action (default: true)
on_emptystringWhat an empty answer does: warn (default) fails the record and the run goes on, error fails the action, skip passes the record through as a tombstone
retryobjectRetry configuration for transport-layer failures

:::note Granularity Constraints

  • File granularity is supported for tool and HITL actions (kind: tool, kind: hitl)
  • Guards are supported with File granularity; the guard is evaluated per record before the action receives the file, against the record as stored rather than the context_scope-shaped view — so a field the action drops still answers a clause. See Guards. :::

Input Source​

A workflow can replace the default staging/ input with a local folder and optional file-type filter. data_source is set under defaults:, where the workflow's first actions read it; the loader refuses it on an action:

yaml
YAML
defaults:
data_source:
type: local
folder: ./data
file_type: [json]

Validation Fields​

FieldTypeDescription
json_modebooleanEnable structured JSON output
expectobjectOutput rules and repair policy (see Expectations)
expectobjectOutput expectations and their enforcement policy (see AI Expectations)

Tool Action Fields​

FieldTypeDescription
implstringPython function name (required for kind: tool)

Tool actions support both Record and File granularity. File granularity allows the tool to process all records at once, enabling operations like deduplication, aggregation, and batch exports.

Vendor Support​

Vendormodel_vendorBatch APIExample Models
OpenAIopenai✅gpt-4o, gpt-4o-mini
Anthropicanthropic✅claude-sonnet-4-20250514
Googlegoogle✅gemini-2.0-flash
Groqgroq✅llama-3.3-70b-versatile
Coherecohere❌command-r-plus
Ollama (local)ollama_local✅llama3, mistral
Ollama (cloud)ollama_cloud✅gpt-oss:120b-cloud

Environment Variables​

You might wonder why API keys are specified as variable names rather than values. Agent Actions references environment variables by name, keeping secrets out of your configuration files:

yaml
YAML
api_key: OPENAI_API_KEY # Uses $OPENAI_API_KEY from environment

API Keys​

VariableProvider
OPENAI_API_KEYOpenAI
ANTHROPIC_API_KEYAnthropic
GOOGLE_API_KEYGoogle Gemini
GROQ_API_KEYGroq
OLLAMA_HOSTOllama (default: http://localhost:11434)

Runtime Variables​

VariableDefaultDescription
AGENT_ACTIONS_LOG_LEVELINFOLog level (DEBUG, INFO, WARNING, ERROR)
AGENT_ACTIONS_DEBUG0Enable debug mode
AGAC_RECORD_LIMITunsetCap each action at this many records per input file, overriding a larger record_limit and applying to actions that set none. --record-limit takes precedence when both are set, and can raise this value as well as lower it. For running a project cheaply from outside it — a smoke check, a quick sanity pass. On a workflow you have already run it is not read-only: a limit smaller than what a completed action already processed differs from the one it stored, so it re-executes under this one and its output is rewritten to the smaller set. A value at or above what an untruncated run processed cannot cut anything and leaves the action alone. That needs a run able to say what it processed: one that completed before these counts existed, or one that lost an input file to an error, keeps the coarse rule and re-executes on any change. Unset it, or use a scratch project, when the stored output matters. An action that actually drops records logs a warning naming this variable, since a truncated run otherwise looks complete; an action that had nothing to drop stays quiet. A value below 1, or one that is not an integer, fails rather than being ignored — checked while the workflow is assembled, so it stops any command that loads one, read-only ones like agac inspect included. An empty or blank value reads as unset, since that is what a shell means by AGAC_RECORD_LIMIT=. Never excludes a record that agac retry is re-running, since retry selects by id.
AGAC_FILE_LIMITunsetStop each action after this many input files, overriding a larger file_limit and applying to actions that set none. It counts files the action got through, so one that fails does not spend the budget. --file-limit takes precedence when both are set, and can raise this value as well as lower it. The other axis of the same job: AGAC_RECORD_LIMIT shrinks each file, this shrinks how many are read, and a run is proportional to both. On a workflow you have already run it is not read-only, for the same reason: the limit it applies differs from the one the completed actions stored, so they re-execute under it. Files the shorter walk does not reach keep the output the earlier run wrote there, so what you end up with is the old output with the walked files replaced rather than a smaller fresh copy. An action whose walk actually stops short logs a warning naming this variable; one that reached every file stays quiet. A value below 1, or one that is not an integer, fails rather than being ignored, and fails before any action starts — the walk does not consult a file limit until a file has been processed, so it is checked while the workflow is assembled, which also stops read-only commands like agac inspect. An empty or blank value reads as unset. Never holds back agac retry, which walks every file holding a record it named.

Directory Structure​

Here's where it gets interesting: Agent Actions uses a two-level structure—project-level assets shared across workflows, and workflow-level assets specific to each domain:

text
TXT
project/
├── agent_actions.yml # Project config
│
├── # ════════════════════════════════════════════════════════
├── # PROJECT-LEVEL (shared across all workflows)
├── # ════════════════════════════════════════════════════════
├── schema/ # Output schemas (project-level only)
├── tools/ # Custom tools (shared)
├── prompt_store/ # Shared prompt templates (optional)
│
├── # ════════════════════════════════════════════════════════
├── # WORKFLOW-LEVEL (domain-specific)
├── # ════════════════════════════════════════════════════════
└── agent_workflow/
└── my_workflow/
├── agent_config/
│ └── my_workflow.yml # Agentic workflow definition
├── agent_io/
│ ├── staging/ # Input data (starting point)
│ └── target/ # Output data
├── seed_data/ # Static reference data (workflow-level)
└── prompt_store/ # Domain-specific prompts (optional)

Asset Location Summary​

AssetProject LevelWorkflow LevelNotes
Schemasschema/—Always project-level; shared across workflows
Toolstools/—Always project-level; shared across workflows
Promptsprompt_store/workflow/prompt_store/Either or both; searched recursively
Seed Data—workflow/seed_data/Always workflow-level; domain-specific
Input/Output—workflow/agent_io/Always workflow-level

This structure keeps your agentic workflows organized while enabling reuse. Shared schemas ensure consistent data contracts; workflow-level seed data enables domain customization without touching shared assets.

See Also​