Skip to main content

Slack integration for interviews

Fabro can now conduct human-in-the-loop interviews directly in Slack. The new Slack Socket Mode integration supports all five question types — yes/no, confirmation, multiple choice, multi-select, and freeform (via threaded replies). Because it uses Socket Mode, no public URL or webhook endpoint is required. Previously, interviews required the CLI or web UI. Now teams can answer Fabro’s questions without leaving Slack.

Hooks

Workflows can now trigger actions at key moments — before a stage starts, after it completes, or when a run fails. Use hooks to notify external systems, enforce policies, or gate execution on custom conditions. Three executor types are available: http for calling external endpoints (with TLS mode configurable per-hook), prompt for natural-language conditions evaluated by an LLM, and agent for autonomous decision-making.
run.toml
[[hooks]]
event = "stage.before"
executor = "http"
url = "https://api.example.com/webhook"
tls_mode = "strict"

Model failover

If your primary model is unavailable or rate-limited, runs now automatically switch to a backup. Configure fallback models at the provider level in your server config:
server.toml
[providers.anthropic]
failover = ["openai", "gemini"]
Previously, a provider outage would fail the entire run. Now it retries with the next provider in the list.

GPT-5.4 and GPT-5.4 Pro

OpenAI’s GPT-5.4 and GPT-5.4 Pro are now available in the model catalog. Use the aliases gpt54 and gpt54-pro in your workflow stylesheets. Neither replaces GPT-5.2 as the default OpenAI model.
stage_a [model="gpt54-pro"];

More

  • Added fabro parse command for printing the raw AST of a DOT workflow as JSON
  • Persistent CLI defaults in ~/.fabro/cli.toml — set output format, default workflow, or any flag once
  • Richer condition expressions: ||, !, numeric comparisons, contains, and matches (regex)
  • Per-node max_visits attribute overrides the graph-level max_node_visits setting
  • $$ escapes literal dollar signs in prompts, fixing a bug where $goal could match as a substring
  • Simplified handler type names: agent_loop is now agent, one_shot is now prompt (old names still work)
  • Fixed a server-side error message that could leak to the browser in production
  • Fixed a crash in the web UI when loading run stages (apiStages.map on non-array response)
  • Fixed Docker demo build and verifications API response parsing
  • MODEL column in CLI tables widened from 24 to 30 characters to avoid truncating longer model names
  • Unknown $variable placeholders in DOT prompts now produce clear error messages instead of being silently passed through
script.output and script.stderr context keys renamed to command.output and command.stderr. The old names were inconsistent with the handler name (command).To migrate: Update any DOT workflow prompts referencing {{script.output}} or {{script.stderr}} to use {{command.output}} and {{command.stderr}}.
GET /runs/{id}/compare renamed to GET /runs/{id}/files. The endpoint now returns a standard paginated list of FileDiff items instead of the RunCompare envelope.To migrate: Update API integrations using /compare to use /files, and adjust response parsing from { checkpoints, files, stats } to { data, meta }.