AgentKit
DocsKitsCLI ReferenceDesktop App
BetaYou are reading docs for the beta channel (3.0.0-beta.15). Features may change before the next stable release.Switch to stable →

prefs

ak config prefs set

Set one bounded Hook boolean, the journal.auto preference, the worktree.root default, one runtime capability-tier agent model, or one semantic_decision setting with exact scope, schema, backup, atomic-write, output, and manual-recovery behavior.

Use ak config prefs set to pin one Hook soft-preference, the journal.auto preference, the worktree.root default location, one runtime capability-tier agent model, or one semantic_decision setting in the user config or the current project's config. The command changes the selected file immediately; it does not unregister or install a Hook and does not stop explicit /ak:journal.

Usage

ak config prefs set <key> <value>

Supply exactly two positional arguments.

Command flag

FlagDefaultDescription
--scope <scope>userSelect user under AgentKit home or project under the current working directory.

Shared flags are described in CLI conventions. The write does not prompt, so --yes and --no-interactive do not change it. There is no --dry-run, --force, or preview mode.

Key and value validation

Five key shapes are accepted:

  • hooks.<name> — <name> must be a lowercase kebab-case Hook script basename matching ^[a-z0-9]+(?:-[a-z0-9]+)*$ and cannot contain another dot.
  • journal.auto — the exact literal, no nested keys under journal.
  • worktree.root — the exact literal, no nested keys under worktree.
  • agent_models.<runtime>.<tier> — <runtime> is the closed set cursor, and <tier> is one of inherit, sonnet, opus, fable, or haiku.
  • semantic_decision.<leaf> — <leaf> is enabled, provider, model, timeout_ms, or consumers.<consumer>, where <consumer> is domain-routing, fix-complexity, orchestration-risk, skill-routing-eval, review-triage, workflow-controller, ui-regression, test-impact, or e2e-classification.

For hooks.<name> and journal.auto the value must be the exact lowercase literal true or false. For worktree.root the value is a filesystem path; project scope only accepts a relative path (resolved against the project root), while user scope accepts either a relative path (also resolved against the project root) or an absolute path. For agent_models.<runtime>.<tier> the value is the model ID to emit for that tier: a single non-empty token whose shape is checked, never whether a catalog entry with that ID exists. A runtime or tier you leave unauthored keeps that adapter's built-in catalog default.

ak config prefs set hooks.simplify-gate false
ak config prefs set hooks.simplify-gate true --scope project
ak config prefs set journal.auto false
ak config prefs set worktree.root /Volumes/Portable/agentkit-worktrees
ak config prefs set worktree.root ../my-app-worktrees --scope project
ak config prefs set agent_models.cursor.sonnet claude-sonnet-4-6
ak config prefs set semantic_decision.provider typesafe --scope user
ak config prefs set semantic_decision.enabled true --scope user

Keys such as keys.anthropic, api.token, telemetry.enabled, hooks.Bad-Name, hooks.a.b, any journal.<other>, any worktree.<other>, any agent_models.<runtime> other than cursor, any unrecognized agent_models.<runtime>.<tier>, and any semantic_decision leaf not listed above (such as semantic_decision.api_key) are rejected before a preference write. This allowlist prevents the command from being used as a general secret or config editor.

For a Hook toggle, false lets a Hook that honors this preference exit early on its next run; true records the opposite preference. Harness registration is unchanged, and setting a name does not prove that Hook is installed.

For journal.auto, false suppresses the automatic /ak:journal step at the end of plan, cook, fix, ship, and bootstrap workflows without unregistering hooks or blocking an explicit /ak:journal. true records the opposite preference. The built-in default is true.

For worktree.root, the value picks the default location that ak:worktree uses when --worktree-root is not passed. Project scope refuses an absolute value with a warning and falls through to the next scope, because a committed project config can arrive from an untrusted clone. User scope accepts an absolute path, which is the right choice for a portable-drive or external-volume worktree layout. The built-in default is unset, so ak:worktree continues to fall back to the WORKTREE_ROOT environment variable and its built-in location chain.

Semantic decision settings

These keys control opt-in semantic evaluation by ak eval decision, ak eval triage, ak eval ui, ak eval workflow, ak test optimize, and ak test classify-e2e.

KeyAccepted valueDefault
semantic_decision.enabledtrue or falsefalse
semantic_decision.providertypesafe or cloudflareunset
semantic_decision.modelModel ID matching ^[A-Za-z0-9][A-Za-z0-9._:/-]{0,127}$; only clef or clef-flash with cloudflareunset
semantic_decision.timeout_msInteger from 100 to 300005000
semantic_decision.consumers.<consumer>true or falseunset

Provider consent is user-scoped. At --scope project, only semantic_decision.enabled false and semantic_decision.consumers.<consumer> false are accepted; they restrict the user grant for that project. Any other semantic key or value at project scope exits 1 before a project config is scaffolded or written. Set semantic_decision.provider before enabling, because an enabled user policy without a provider is invalid when evaluated.

Without a user consumers map, only domain-routing, fix-complexity, and orchestration-risk are permitted. The other six consumers (skill-routing-eval, review-triage, workflow-controller, ui-regression, test-impact, and e2e-classification) each need an explicit semantic_decision.consumers.<consumer> true at user scope:

ak config prefs set semantic_decision.consumers.test-impact true --scope user

Setting semantic_decision.enabled true at user scope is consent to send normalized request facts to an external provider, and each evaluation may incur provider charges. Provider credentials never belong in config; they come from the process environment or $AGENTKIT_HOME/.env. See providers and credentials.

Scope and filesystem effects

ScopeTargetAdditional effect
user$AGENTKIT_HOME/config.yaml, normally ~/.agentkit/config.yamlA missing file is created.
project<cwd>/.agentkit/config.yamlIf absent, AgentKit scaffolds the project template and .agentkit/.gitignore first. The project config is intended to be committed, so do not place credentials in it.

The writer changes only the selected hooks.<name>, journal.auto, worktree.root, agent_models.<runtime>.<tier>, or semantic_decision.* leaf. It preserves other sections, unmodelled YAML, comments, key order, and the schema editor directive. If hooks, journal, or worktree already exists but is not a mapping, the write is refused.

Before writing, AgentKit validates the whole candidate against the schema embedded in this binary. Existing legacy spellings can produce warnings but do not by themselves fail validation; schema errors leave an existing target untouched.

Backup, atomicity, and recovery

When the target exists, AgentKit copies its current bytes to a mode-0600 file under $AGENTKIT_HOME/backups/config/. User backups begin with config-; project backups begin with project-config-. Backup failure aborts the config rewrite.

The new document is written to a sibling temporary file, changed to mode 0600, then renamed over the target. This prevents readers from seeing a half-written document.

Atomic replacement is not a cross-process transaction lock. Do not run this command alongside another config writer or a manual save; both can read the same old document and the later rename can lose the earlier change. A symlinked config path is also replaced by the new regular file rather than preserved as a symlink.

To recover, stop other writers, inspect the backup_path reported by the successful command, manually replace config_path with that backup, and run ak config prefs validate. These config copies are not full AgentKit snapshots and have no automatic rollback command.

Human and JSON output

Human success writes the change and target path to stdout, followed by the backup path when one was created:

set hooks.simplify-gate = false (user scope) in /home/user/.agentkit/config.yaml
backed up prior config to /home/user/.agentkit/backups/config/config-<timestamp>.yaml

--json writes the shared success envelope with kind config.prefs.set:

{
  "schema_version": 1,
  "kind": "config.prefs.set",
  "data": {
    "action": "set",
    "key": "hooks.simplify-gate",
    "value": false,
    "scope": "user",
    "config_path": "/home/user/.agentkit/config.yaml",
    "backup_path": "/home/user/.agentkit/backups/config/config-<timestamp>.yaml",
    "found": true
  }
}

Inside data, a boolean is reported in value. A string value, such as worktree.root, an agent model ID, semantic_decision.provider, or semantic_decision.model, is reported in value_string instead, and semantic_decision.timeout_ms in value_int.

backup_path is omitted when no backup was created. found is always true for a successful set. --quiet does not suppress this command-specific stdout.

JSON-mode failures, including flag-parse errors (exit 2), write the shared error envelope to stderr. A wrong positional-argument count follows the generic runtime error path instead.

Exit behavior

ExitMeaningSafe next step
0The selected leaf was written and any reported backup completed first.Run resolve and validate.
1The positional-argument count, key, value, scope (including a disallowed project-scope semantic_decision write), path, YAML shape, schema, backup, or write failed.Correct the invocation or read the human error without exposing config secrets; do not force the write.
2Flag parsing failed.Correct the flags.

Verify the result

ak config prefs resolve --json
ak config prefs validate

For project scope, run resolve from that same project directory so the intended project file participates in precedence.