Skip to content

feat: declaratively materialize global agent profiles #460

Description

@christso

Problem

AllAgents can synchronize plugins and agent artifacts into default user and project client locations, but it cannot declaratively create separate user-level client profiles.

For example, setting up a Compound Engineering OMP profile currently requires imperative commands:

omp --profile compound-engineering plugin marketplace add EveryInc/compound-engineering-plugin
omp --profile compound-engineering plugin install compound-engineering@compound-engineering-plugin

The user must also remember how to launch that profile. OMP can create a shell alias, but that mutates shell startup files and is not a portable launcher lifecycle.

The desired profile, launcher, native plugins, selected skills, MCP servers, and settings should be reproducible from the user-owned AllAgents workspace instead of imperative setup steps.

Goal

Allow the user-level ~/.allagents/workspace.yaml to declaratively define reusable agent profiles:

profiles:
  compound-engineering:
    clients:
      - name: omp
        install: native
        launcher: omp-compound

    plugins:
      - source: EveryInc/compound-engineering-plugin
        ref: main
        install: native

A user explicitly materializes a declared profile once:

allagents profile install compound-engineering

AllAgents creates the selected native profile, configuration root, or documented configuration override, installs its declared resources, generates its launchers, and records enough ownership state to update or remove those resources safely.

Once installed, ordinary allagents update reconciles the installed profiles declared by the user-level workspace as part of the existing user sync pass. If the command is run from a project workspace, the existing project sync pass still runs independently.

Scope model

Global profiles and project workspaces are independent:

~/.allagents/workspace.yaml
├── top-level plugins           -> existing default user client state
└── profiles                    -> explicitly installed user-level client profiles

<project>/.allagents/workspace.yaml
└── top-level clients/plugins   -> existing project-local client state

Requirements:

  • profiles is valid only in ~/.allagents/workspace.yaml.
  • A project-scoped .allagents/workspace.yaml containing profiles is a validation error.
  • Profiles always materialize user-level native profiles, configuration roots, or documented configuration overrides. An override isolates AllAgents-managed writes but may inherit other client, user, or project configuration; it does not promise strict runtime isolation.
  • A profile declaration does not accept scope.
  • Project workspaces have no profile lifecycle or profile ownership state.
  • Profile commands never search for or read a project workspace declaration.
  • Profile installation, update, status, and removal never mutate project files.
  • Project synchronization never copies project resources into a global profile.
  • Removing a profile declaration does not authorize removal of an installed profile.
  • Ordinary sync must not create an uninstalled profile or silently remove an installed profile.

Runtime composition

Profile state and project state do not need an AllAgents merge step.

A generated launcher selects only the declared user-level client profile and preserves the caller's current working directory. The client runtime continues to discover project-local files through its normal rules.

For OMP:

#!/bin/sh
exec omp --profile compound-engineering "$@"

When run inside a synchronized project, both omp and omp-compound can discover that project's .agents, .omp, and other OMP-supported project files. When run outside the project, those project resources are absent. AllAgents does not copy, adopt, track, or reconcile project resources as profile resources.

Launchers must not run allagents update, inspect project configuration, access the network, or perform installation as a side effect of launching the client.

Terminology

  • Profile declaration: a named entry under profiles in the user-level ~/.allagents/workspace.yaml.
  • Installed profile: user-level client state materialized from a profile declaration and recorded in AllAgents profile ownership state.
  • Client: a supported agent runtime configured by a profile, such as OMP, Codex CLI, or Claude Code.
  • Native runtime profile: a first-class profile mechanism provided by a client, such as OMP --profile or Codex --profile.
  • Configuration root: a client-specific user-state directory selected through an environment variable or equivalent when the client has no suitable native profile mechanism, such as COPILOT_HOME or CLAUDE_CONFIG_DIR.
  • Configuration override: a client-specific configuration layer that may inherit other user or project configuration rather than providing strict isolation, such as OpenCode's OPENCODE_CONFIG or OPENCODE_CONFIG_DIR.
  • Launcher: a generated platform-native executable that selects a declared client profile or configuration root and forwards arguments. It is not a shell alias.
  • Native installation: invoking the selected client's package or plugin lifecycle inside the selected profile or configuration root.
  • File installation: AllAgents-managed synchronization into the selected user profile or configuration root.
  • Managed resource: a resource AllAgents created and may update or remove while its recorded identity still matches.
  • Referenced resource: a matching resource that existed independently. AllAgents may use it but must preserve it on removal.

Use client in the public workspace schema. Do not introduce a separate target taxonomy.

Workspace schema

profiles is a top-level section in the user-level workspace:

profiles:
  compound-engineering:
    clients:
      - name: omp
        install: native
        launcher: omp-compound
        settings: {}

    plugins:
      - source: EveryInc/compound-engineering-plugin
        ref: main
        install: native
        skills:
          - ce-plan
          - ce-work
          - ce-code-review

    mcpServers: {}

Schema requirements:

  • profiles is keyed by profile name.
  • Profile names are 1–64 lowercase ASCII characters matching ^[a-z0-9][a-z0-9._-]{0,63}$. . and .. and Windows reserved device basenames are invalid.
  • Each profile contains one or more clients, and each client name is unique within that profile.
  • Client names use the existing public client vocabulary.
  • The profile key is the default native profile/configuration-root identity. Adapters may derive a safe client-specific path from it, but generated machine paths are never workspace input.
  • Shared client fields are name, install, launcher, and settings.
  • Client-level install is the default plugin materialization mode for that client; a plugin-level install overrides it. It never installs the client executable.
  • launcher is optional. Omitting it creates no launcher.
  • Launcher names use the profile-name grammar. Declarations and retained installed state must not contain platform-equivalent launcher collisions, including case-folded Windows names and .ps1/.cmd companions.
  • settings is an optional strict client-specific object selected by the client name and defaults to {}. Unknown or unsupported settings fail validation before mutation.
  • Profile plugins use the existing source, ref, install, clients, and skills vocabulary.
  • A plugin can restrict itself to clients in the same profile through clients. Without that selector, it applies to every client in the profile.
  • Omitting skills enables all plugin-provided skills; an array is an allowlist; { exclude: [...] } is a blocklist. Native installation with a skill selection fails when the client cannot enforce that selection.
  • Profile-specific agents and instructions come from declared plugins through the existing artifact model. Profiles do not introduce a standalone instructions field.
  • mcpServers uses the existing workspace MCP declaration vocabulary. Each server applies to every client in the profile unless its existing clients selector restricts it. A selected client that cannot materialize the server fails the complete profile plan before mutation.
  • Machine-specific paths, resolved credentials, generated launcher paths, resolved revisions, and ownership state are invalid declaration fields.
  • The profile schema is strict. Unknown fields are errors.

There is no generic public capabilities field. The declaration names concrete desired resources. The planner derives the required capabilities, and the selected client adapter reports whether it can materialize them.

Commands and synchronization

allagents profile install [name]

  • Reads only ~/.allagents/workspace.yaml.
  • Selects the named declaration; if omitted in an interactive terminal, prompts from declared profiles.
  • Validates and plans the complete profile before mutation.
  • Shows profile/configuration selection, commands, paths, launchers, plugin identities, refs, skills, MCP endpoints or command names, and secret names.
  • Requires approval before the first mutation unless an explicit non-interactive approval option is supplied.
  • Creates the profile and records ownership incrementally.
  • Is idempotent when the same profile is already installed and unchanged.

allagents profile status [name]

  • Reads declarations and user-local ownership state without mutation.
  • Reports installed, missing, drifted, partial, unsupported, and declaration-missing states per client and resource.

allagents profile remove <name>

  • Plans removal from user-local ownership state even when the declaration no longer exists.
  • Requires explicit approval.
  • Removes only unchanged managed resources whose ownership is still proven.
  • Releases referenced resources without deleting them.
  • Reports retained, modified, shared, unsupported, and failed resources.

allagents update [--profile <name>...]

Without --profile, the existing command reconciles every applicable resource:

  1. Reconcile the user-level workspace, including every installed profile that still has a declaration.
  2. When the current directory contains a project workspace, reconcile that project using the existing project behavior.

Both applicable passes are attempted independently with no cross-scope rollback. They may share fetched source caches but do not share declarations, resource plans, or ownership state. Human and JSON output report each scope separately, and the command exits nonzero if either scope fails.

--profile is a repeatable filter:

allagents update --profile compound-engineering
allagents update --profile compound-engineering --profile security-review

When one or more profile filters are present:

  • Reconcile only the selected profiles. Skip top-level user resources and the project workspace.
  • Read declarations only from ~/.allagents/workspace.yaml.
  • Require every selected name to have both a declaration and installed ownership state.
  • Validate the complete selected set before the first mutation.
  • Deduplicate repeated names while preserving their first-seen order.
  • Never treat a missing installation as an install request.
  • Support the normal --dry-run and --offline update controls.
  • Reject combinations with --scope or --client; the complete profile is the reconciliation unit.
  • Report results per profile in human and JSON output and exit nonzero if any selected profile fails or remains partial.
  • Remove resources deleted from a still-declared profile only when they remain unchanged and managed.
  • Fail on collisions or lost ownership instead of overwriting.

Update is an explicit reconciliation command and does not prompt for separate approval. Deleting an entire profile declaration leaves its installed state declaration-missing and unchanged; ordinary update does not remove it.

Declarative materialization

Before the first mutation, AllAgents must:

  1. Parse and validate the complete user workspace and selected profile.
  2. Resolve each client's documented profile or configuration-root mechanism.
  3. Resolve plugin source metadata and requested refs.
  4. Resolve authoritative client-native plugin identities where native installation is requested.
  5. Validate skill filtering, MCP, settings, launcher, and cleanup capabilities against each adapter.
  6. Inspect destination resources and classify them as creatable, managed, referenced, conflicting, drifted, or unsupported.
  7. Produce a concrete ordered plan with redacted effects.
  8. Obtain approval when required by the selected lifecycle command.

Apply must execute the approved plan without rediscovering composition interactively. Missing declaration data is a validation error.

For native marketplaces, an adapter resolves the installable plugin identity from authoritative marketplace metadata. If a source remains ambiguous, this version fails validation rather than guessing.

Client adapter seam

Shared profile orchestration owns:

  • Workspace and profile validation
  • Profile selection
  • Requested and resolved refs
  • Skill selection semantics
  • Plan construction and ordering
  • Approval and dry-run behavior
  • User-local ownership state
  • Result reporting
  • Launcher safety
  • Secret-reference redaction

Each client adapter owns:

  • Native profile, configuration-root, or override selection
  • Supported client versions
  • Exact native commands
  • File locations and precedence
  • Native plugin identity resolution
  • Client-specific settings validation and serialization
  • Skill-filter support
  • MCP serialization
  • Runtime reload behavior
  • Project-file discovery documentation
  • Safe status inspection and cleanup

Adapter capabilities are typed implementation metadata, not workspace-authored claims. At minimum they report support for native installation, file installation, launchers, skill filters, MCP, settings, status inspection, and cleanup.

An unsupported declared capability is an actionable validation error. Explicit install: native must never fall back to file copying.

Compound Engineering OMP fixture

The canonical declaration is:

  • Profile: compound-engineering
  • Client: omp
  • Launcher: omp-compound
  • Marketplace source: EveryInc/compound-engineering-plugin
  • Native plugin: compound-engineering@compound-engineering-plugin
  • Installation mode: OMP native installation

The adapter executes the equivalent of:

omp --profile compound-engineering plugin marketplace add EveryInc/compound-engineering-plugin
omp --profile compound-engineering plugin install compound-engineering@compound-engineering-plugin

The POSIX launcher behaves equivalently to:

#!/bin/sh
exec omp --profile compound-engineering "$@"

It preserves arbitrary arguments, the current working directory, signals, and the OMP exit code. OMP's built-in --alias may be an explicitly requested compatibility mode later, but it is not the default launcher implementation.

Native and file installation

install: native delegates to the selected client's installer inside the selected profile or configuration root. The native operation owns marketplace registration, installed-plugin metadata, locks, discovery, upgrade, and uninstall behavior. AllAgents records what it requested and which resources it introduced; it does not emulate native installation by copying runtime files.

install: file synchronizes files only into the selected user profile or configuration root. It never writes profile resources into a project directory.

Linking is supported only where a client exposes a documented link lifecycle. It is not a generic substitute for native installation.

Ownership state and recovery

Profile state is user-local and separate from both global and project sync state:

~/.allagents/profiles/<profile-name>/state.json

The versioned state records:

  • Installed profile and client identities
  • Normalized declaration digest
  • Requested and resolved plugin refs
  • Concrete native package, marketplace, MCP, configuration, and launcher identities
  • Managed or referenced ownership relationship
  • Last observed content or identity fingerprint where available
  • Cleanup mechanism
  • Per-operation completion and partial-failure state

State never contains secret values.

Persist successful ownership changes immediately so interrupted installation or update can resume safely. External installers and configuration writers are not one transaction; a partial operation must report partial, retain uncertain provenance, and stop before unsafe cleanup.

Repeat install or update is idempotent. Removal compares recorded ownership with live state and preserves modified, unrelated, shared, referenced, or uncorroborated resources. Policy-retained resources are preserved and this profile's ownership relationship is released. Failed or uncertain operations retain their state for retry and leave the profile partial. Profile state is deleted only after every relationship has been removed or explicitly released.

Trust and secrets

The global workspace is user-owned, but it can still request executable native installation and MCP configuration. Plans must disclose:

  • Client and profile/configuration mechanism
  • Native commands
  • Package sources and resolved revisions
  • Launcher destinations
  • Local MCP command names and arguments with secrets redacted
  • Remote MCP endpoints
  • Names, but never values, of requested secrets

Secrets are environment or credential-store references. Resolved values must not be written to workspace YAML, generated launchers, ownership state, logs, errors, or command arguments. If a client cannot consume a secret reference without persisting plaintext, the adapter reports that capability as unsupported.

The portable secret-reference syntax is ${ENV_VAR}, where the name matches [A-Za-z_][A-Za-z0-9_]*. AllAgents preserves the reference during planning and materialization. An adapter may use it only where the client resolves the environment reference at runtime without writing the value; otherwise the declaration is unsupported.

Launcher names must be safe command basenames. Creation refuses path traversal, symlink destinations, unsafe parents, or unrelated existing files.

Cross-platform launchers

  • Linux/macOS: write an executable wrapper to the configured user bin directory, defaulting to an XDG-compatible location such as ~/.local/bin.
  • Windows PowerShell: write a .ps1 launcher that selects the profile/configuration root, forwards all arguments, and returns the client exit code.
  • Windows command compatibility: write a companion .cmd shim where required for discovery from PowerShell and cmd.exe.

AllAgents checks whether the launcher directory is on PATH and prints exact remediation. It never modifies .bashrc, .zshrc, PowerShell profiles, or equivalent startup files.

Supported clients and delivery order

Profile adapters are required for:

  • Pi
  • OMP
  • OpenCode
  • GitHub Copilot CLI
  • OpenAI Codex CLI
  • Claude Code

Capability baseline:

Client Profile/configuration model
Pi PI_CODING_AGENT_DIR selects a separate agent directory. Pi core has no MCP support.
OMP --profile <name> / OMP_PROFILE; native state under ~/.omp/profiles/<name>/agent.
OpenCode OPENCODE_CONFIG and OPENCODE_CONFIG_DIR add configuration layers and do not guarantee strict isolation.
GitHub Copilot CLI COPILOT_HOME selects a user configuration root.
Codex CLI --profile <name> selects a configuration overlay. CODEX_HOME is a separate state-root mechanism and must not be conflated with it.
Claude Code CLAUDE_CONFIG_DIR selects settings, history, and plugin state.

Pi MCP through pi-mcp-adapter is deferred. Until Pi extension/package support exists, Pi profile declarations requiring MCP must fail as unsupported.

Deliver in this order:

  1. Add OMP to the ordinary supported client schema and implement its existing project/user artifact mappings and native installation adapter.
  2. Add global profile schemas, commands, planner, adapter contract, user-local state, and launcher support.
  3. Complete the Compound Engineering OMP fixture end to end.
  4. Add remaining clients one adapter at a time, with documented real-runtime verification before each is marked supported.
  5. Publish the generated workspace JSON Schema after the profile shape is implemented.

Workspace JSON Schema

Publish a versioned JSON Schema for both user and project .allagents/workspace.yaml contexts:

  • Runtime Zod validation remains authoritative.
  • Generate the external schema from the authoritative input models.
  • Commit the generated artifact and enforce a drift test.
  • The project schema rejects profiles.
  • The user schema includes strict profile/client/ref/settings definitions.
  • Document stable versioned URLs and YAML language-server setup.

Dogfood requirement

Use an isolated disposable home and two disposable project directories so real user state cannot collide.

For the Compound Engineering OMP fixture:

  1. Create ~/.allagents/workspace.yaml with the canonical profile declaration.
  2. Install compound-engineering through allagents profile install.
  3. Verify the marketplace and plugin were installed through OMP's native commands in the selected profile.
  4. Launch omp-compound from a fresh shell and outside any project.
  5. Verify argument, working-directory, signal, and exit-code pass-through.
  6. Verify the Compound Engineering plugin and selected skills load in omp-compound and not in the default OMP profile.
  7. Create project A with a unique project skill and synchronize it.
  8. Run both omp and omp-compound inside project A and verify both discover the project skill through normal OMP project discovery.
  9. Run both launchers outside project A and verify the project skill is absent.
  10. Create project B with a different project skill and verify there is no cross-project leakage.
  11. Change the global profile declaration, run allagents update --profile compound-engineering, and verify targeted reconciliation and idempotence.
  12. Verify project synchronization does not change profile ownership state and targeted profile update does not change project files.
  13. Remove the profile explicitly and verify managed plugin state, marketplace registration, disposable profile state, and launchers are removed while both projects remain unchanged.

Each additional client adapter requires a recorded real-runtime dogfood run covering its profile/configuration mechanism and normal project discovery behavior before support is advertised.

Acceptance criteria

Schema and scope

  • Only ~/.allagents/workspace.yaml accepts top-level profiles.
  • Project workspace validation rejects profiles.
  • Profile declarations use existing client, plugin, ref, skill-selection, and MCP vocabulary.
  • Client-specific settings are strict and adapter-owned.
  • Existing top-level user and project configuration remains backward compatible.
  • No implicit default profile is introduced.

Lifecycle

  • Explicit profile install, status, and remove commands are available.
  • allagents update without profile filters reconciles every installed profile that still has a declaration.
  • Repeated --profile filters reconcile only the selected installed profiles and skip top-level user and project resources.
  • Targeted update rejects missing declarations, missing installations, --scope, and --client before mutation.
  • Ordinary update does not create undeclared installations or remove declaration-missing profiles.
  • Profile operations are idempotent and recover safely from partial failure.
  • allagents profile update is not introduced as a second spelling for the same mutation.
  • Profile lifecycle is independent of project lifecycle.

Materialization

  • The declaration determines clients, launchers, plugins, refs, skill selection, MCP servers, and settings.
  • Named installation does not prompt for composition already present in the declaration.
  • Native installation never silently becomes file installation.
  • Unsupported client capabilities fail before mutation.
  • Generated machine paths and state remain outside workspace YAML.

Ownership and cleanup

  • Adapters report concrete resource identities and whether AllAgents manages or references them.
  • Removal invokes native cleanup where supported.
  • Removal preserves pre-existing, referenced, modified, unrelated, shared, and uncorroborated resources.
  • Deleting a declaration does not implicitly uninstall a profile.
  • Profile state contains no project resources or secret values.

Launchers and project independence

  • POSIX and Windows launchers preserve arbitrary arguments, working directory, and exit codes; POSIX launchers also preserve normal signal delivery through exec.
  • Launchers do not inspect, synchronize, or mutate project workspaces.
  • Launchers do not modify shell startup files.
  • The default and named client launchers discover the same synchronized project-local resources according to the client's native rules.
  • Project resources are never copied into profile state.

Verification

  • The Compound Engineering OMP profile installs, updates, reports status, and removes end to end in an isolated environment.
  • omp-compound works from a fresh shell and outside a project.
  • Default OMP state remains unchanged.
  • Project-specific skills are visible to both default and named OMP launchers only inside the corresponding project.
  • Every supported adapter has recorded real-runtime verification.
  • Generated JSON Schema is checked for drift from runtime validation.

Primary references

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions