@agentuiai/cli
v0.16.0
Published
AgentUI CLI — build, sync, and manage AgentUI projects from the terminal
Maintainers
Readme
@agentuiai/cli
Command-line tool for the AgentUI platform. Sync projects to your laptop, edit components in your editor, push changes back, manage secrets, run validations — without leaving the terminal.
Built for two audiences:
- Developers who want a real code-editor workflow (git, VS Code, Cursor) on top of AgentUI projects.
- AI coding assistants (Claude Code, Codex, Aider) — every command supports
--jsonand returns machine-parseable output, matching the approach of the AWS CLI and GitHub CLI.
0.2.0 breaking change. A "project" is now a workflow, not its enclosing App.
project synctakes a workflow id. Existing.agent.jsonfiles will need a one-time re-sync. See CHANGELOG.md for the migration.
Table of contents
- Install
- Quick start
- Authentication
- The sync → edit → push workflow
- Command reference
- auth
- workspace
- project
- The app's icon and index.html
- Are the AI instruction files current?
- env
- secrets
- validate
- build
- deploy
- skills
- packages
- blueprints
- prompts
- functions
- automation
- data
- files
- logs
- guide
- feedback
- integrations
- report — something is broken or missing
- agent-skill — teach your coding assistant
- integration — build one for the community
- Editor and agent plugins
- Global flags
- JSON output mode
- Config files
- Project structure on disk
- Safety and multi-tenant guarantees
- Exit codes
- Troubleshooting
Install
Windows
Download and run AgentUI-Setup.exe — Install, Finish. No Node, no admin, and agentui works in any terminal opened afterwards.
Or from PowerShell (this is what an AI assistant runs; agentui works on the next line, no restart):
irm https://cdn.agentui.ai/cli/install.ps1 | iexBoth install agentui.exe to %LOCALAPPDATA%\Programs\AgentUI and add it to your user PATH. Update with agentui update.
macOS / Linux
No Node needed — this installs the standalone agentui (sha256-checked):
curl -fsSL https://cdn.agentui.ai/cli/install.sh | sudo sh # /usr/local/bin, all users (servers, the connector)
curl -fsSL https://cdn.agentui.ai/cli/install.sh | sh # ~/.agentui/bin, just youUpdate with agentui update (with sudo for the system-wide install).
Or with npm (Node 22+): npm install -g @agentuiai/cli, updated with npm install -g @agentuiai/cli@latest. Verify install:
agentui --versionRun without installing:
npx @agentuiai/cli project listQuick start
Brand-new app — two commands
project create creates the project and the local folder. You don't need
mkdir, and you don't need a separate project sync.
agentui auth login
agentui project create --name "My App" # → ./my-app with AGENTS.md + skeleton
cd my-app && cat AGENTS.md # read the build guide before writing codeWhere it scaffolds:
| Situation | Scaffolds into |
| ---------------------------------------- | ------------------- |
| current directory is empty | the current directory |
| current directory has files | ./<project-name> |
| --dir <path> passed | exactly <path> (created if missing, at any depth) |
Add --no-sync to create the project server-side only (no local files), and
--force to scaffold into a directory that isn't empty.
Working with an existing project
# 1. Log in. You'll get an email with a 6-digit verification code.
agentui auth login
# 2. Pick a workspace (your company).
agentui workspace list
agentui workspace select <workspaceId>
# 3. List projects (workflows) in the active workspace.
agentui project list
# 4. Sync a project into the current directory. The id is the "Project ID"
# column from `project list` — that's the workflow id.
mkdir my-project && cd my-project
agentui project sync <workflowId>
# 4b. (Or, if you cloned the project from git and only need to bootstrap
# .agent.json + the manifest without overwriting your local files:)
agentui project init <workflowId>
# 5. Open in your editor. Edit existing components, create new ones,
# delete ones you don't need.
code .
# 6. Preview what will be pushed.
agentui project push --dry-run
# 7. Push. Use --delete to also remove components whose local files were deleted.
agentui project push --delete
# 8. Make the pushed code live and smoke-test it.
agentui build # or: agentui project push --build
agentui functions invoke sendEmail --data '{}' # calls the app's live /api routeAuthentication
The CLI uses the same OTP email login as the AgentUI web app.
Log in
agentui auth loginYou'll be prompted for your email. AgentUI sends a 6-digit code; paste it to complete the login. The access token is stored at ~/.agentui/credentials.json with 0600 permissions.
Non-interactive email login (for AI agents)
The OTP lives in your inbox, so a fully unattended login isn't possible — but the flow splits into two scriptable steps so an AI assistant can drive it and only ask you for the code:
# Step 1 — agent runs this; it emails the code and exits (no prompt).
agentui auth login --email [email protected]
# → { "status": "code_sent", "email": "[email protected]" }
# Step 2 — agent asks you for the code, then runs:
agentui auth login --email [email protected] --code 481920
# → { "status": "logged_in", "email": "[email protected]",
# "agentSkill": { "installed": false, "install": "agentui agent-skill install" } }An interactive login also offers, once, to install the agent skill. A non-interactive login never installs it; it only reports the command.
When stdin isn't a terminal (an agent or CI pipe), --email without --code stops after sending the code instead of hanging on a prompt. To keep the code out of shell history, pipe it via --code -:
echo "$OTP" | agentui auth login --email [email protected] --code -Who am I?
agentui auth whoami Email: [email protected]
Role: admin
Company: Acme Inc (cmp_abc123)For a fuller report that adds env, token type, and expiry:
agentui auth status Email: [email protected]
Role: admin
Company: Acme Inc (cmp_abc123)
Env: production
Token: jwt
Login at: 2026-06-02T14:21:08.412Z
Expires: 2026-07-02T14:21:08.000Z (in 30d)--json works on both commands.
Log out
agentui auth logoutRevokes the server session and deletes local credentials.
CI / automated environments
For CI, skip the OTP entirely with an API key issued from the AgentUI dashboard:
agentui auth login --api-key "$AGENTUI_API_KEY"This writes the key to ~/.agentui/credentials.json (type api-key) and every subsequent command uses it. You can also write that file directly if you prefer not to shell out:
{ "token": "sk_live_...", "type": "api-key" }The sync → edit → push workflow
A "project" in the CLI is a single workflow on the platform (an APP_V2 SaaS app, an AUTOMATION, a TOOL, or an APP). Its components, pages, functions, entity schemas, and integrations are all server-side records. sync pulls them down as plain files you can edit with any tool; push sends changes back. A workflow's enclosing App container is informational only — it's shown in project status but all CLI operations scope to the workflow.
What sync writes
From the current directory:
.agent.json # projectId (= workflow id), projectName, projectType,
# appId, projectEnvironment, syncedAt (gitignored)
.agent-manifest.json # component ids, versions, workflow ids,
# codeHash per component (gitignored)
.gitignore # created/updated to hide the two config files
Layout.jsx # if the workflow has a Layout component
components/ # one .jsx per COMPONENT
pages/ # one .jsx per PAGE
functions/ # one .jsx per FUNCTION
entities/ # one .json per ENTITYWhat push sends
push compares the current working tree against the manifest and sends the difference:
| Local state | Manifest state | Operation |
|--------------------------------|----------------|-----------|
| File present, content changed | Has entry | update |
| File present | No entry | create |
| File missing | Has entry | delete (opt-in with --delete) |
Each push is atomic per-operation with a server-side version bump. Concurrent pushes from multiple CLIs never collide on the same version.
What's protected
- Values of secrets are never returned, even to admins, even in JSON mode.
- Database records are never returned by
sync— only schemas. - Integration configs / tokens / auth state are never returned — only the type + whether it's authenticated.
Command reference
auth
| Command | Description |
|-----------------------------------------------|--------------------------------------------------|
| agentui auth login | Interactive email + OTP login |
| agentui auth login --email <e> [--code <c>] | Non-interactive two-step email login (--code - reads from stdin) |
| agentui auth login --api-key <key> | Headless login with a dashboard API key (CI) |
| agentui auth logout | Revoke session and clear credentials |
| agentui auth whoami | Show current user, role, and company |
| agentui auth status | whoami + env, token type, and token expiry |
workspace
Alias: ws.
| Command | Description |
|----------------------------------|-------------------------------------------------|
| agentui workspace list | Show all workspaces you have access to |
| agentui workspace select <id> | Switch the active workspace |
| agentui workspace current | Print the active workspace |
project
All project commands are scoped to the active workspace. <projectId> is a workflow id — the "Project ID" column from project list.
| Command | Description |
|-------------------------------------------|-------------------------------------------------------------|
| agentui project create --name "<name>" | Create a workflow and scaffold it locally (--no-sync = server-only, --dir = where, --force = allow non-empty) |
| agentui project list | Workflows in the active workspace (paginated) |
| agentui project init <workflowId> | Bootstrap manifest for an existing local checkout (no file writes) |
| agentui project sync <workflowId> | Pull the workflow into the current directory |
| agentui project push | Send local changes back (auto-detects create/update) |
| agentui project rename <componentId> <newName> | Rename a component server-side |
| agentui project status | Project / workflow / component / entity counts vs last sync |
| agentui project instructions | Are AGENTS.md / CLAUDE.md / Cursor / Windsurf / Copilot the version the platform generates today? |
| agentui project instructions --check | Same, but exits non-zero when any is stale (CI, or a pre-flight before trusting them) |
| agentui project diff | Local file changes since last sync |
| agentui project settings | Workflow runtime toggles (requiresLogin, mfaEnabled, isFunctionAPIEnabled, customDomain, …) |
| agentui project settings set <key> <value> | Change one of those toggles |
| agentui project open [--preview] [--print] | Open the editor (or --preview for the live app) in the browser; --print emits the URL instead |
| agentui project link [--scope newTab\|iframe] [--open] | Mint a short-lived pre-authed deep link to the live preview — for sharing across devices |
create flags
--name <name>— required, project name--sync— also sync the new (empty) project into--dirafter creating--dir <path>— sync target (default: current dir)
Only APP_V2 workflows are created. Legacy
APP/AUTOMATION/TOOLtypes existed in earlier schema versions but the runtime can't execute them end-to-end, so the CLI no longer lets you mint them.
list flags
--limit <n>— results per page (default 20, max 50)--offset <n>— pagination offset--all— fetch every page (100 ms throttle between pages)--type <t>— filter by workflow type:APP,APP_V2,AUTOMATION,TOOL--status <s>— filter by status:ACTIVE,PAUSED,ARCHIVED--search <q>— case-insensitive match on workflow name--app <appId>— narrow to workflows inside one App container
init flags
--dir <path>— target directory (default: current dir)--environment <name>— project environment this folder follows (default: the active one,agentui env current); recorded asprojectEnvironment--force— overwrite an existing.agent.json/.agent-manifest.json
init is for the case where you've cloned a project from git but .agent.json is gitignored. It hits /cli/projects/:id/sync for metadata only — it never writes any component files. Existing local files become the new baseline (their SHA-256 is recorded in the manifest so the next diff is clean). Files missing locally are surfaced in the summary with a sync hint.
sync flags
--dir <path>— target directory (default: current dir)--incremental— only re-fetch components changed since last sync--environment <name>— project environment to pull, and switch this folder to (default: the active one). Pushes from the folder then go to that environment--theirs/--ours/--merge— conflict resolution (mutually exclusive)
sync is 3-way merge aware. Before overwriting any local file, it compares the file's SHA-256 against the codeHash recorded in .agent-manifest.json from the last sync. If a file is locally modified AND the server has a new version (or has deleted/renamed it), sync aborts with an itemized list of conflicts:
Sync aborted: 2 local edit(s) would be overwritten.
Re-run with one of:
--theirs overwrite local edits with the server version
--ours keep local edits (skip the server version)
--merge write server version to <path>.theirs and leave local untouched
Modified locally + new version on server (1):
~ components/Button.jsx (local @ 1.2.0 → server @ 1.3.0)
Modified locally + deleted on server (1):
- pages/OldPage.jsx--merge writes a <path>.theirs sidecar file containing the server's version so you can diff and merge by hand. Sidecars are gitignored (*.theirs is added to the managed .gitignore automatically) so server code can't leak into commits.
A TOCTOU recheck runs immediately before each overwrite — if the live file changed during sync (you saved between pre-flight and write), that file is skipped with a warning instead of being silently destroyed. Pass --theirs to force.
push flags
--dry-run— print the planned operations without sending them--delete— include deletions for manifest entries whose local files are gone (off by default for safety; matchesgit's conservative posture)--no-create— skip auto-creating components for new local files--yes— bypass the production guardrail (see below). Required in CI/scripts that legitimately push to prod.--no-write-back— don't update.agent-manifest.jsonwith the new component IDs / versions returned by the server (default behaviour writes back)--build— after a successful push, trigger the app rebuild and wait for it (see build). The pushed code is live when the command returns.--build-timeout <seconds>— max wait for the--buildrebuild (default 300)
Push ≠ live. A push only flags the app for a rebuild; the platform rebuilds lazily on the app's next page load, so the live app (pages and /api functions) serves the previous build until then. The push output includes requiresRebuild and a nextSteps array; run agentui build (or push with --build) to close the gap deterministically.
Production guardrail. push refuses to ship to production by default. Re-run with --yes to confirm you intend to publish to the live app (CI/scripts). Dry-runs are exempt — they don't change server state. This closes the "stray agentui project push shipped to prod silently" footgun.
After a successful push, the local manifest is auto-updated with what the server returned — new component IDs for creates, bumped versions for updates, removed entries for deletes. Without this write-back, a push that creates a brand-new file would leave the new component as "untracked" locally, and the next push would create a duplicate on the server. --no-write-back opts out for tooling that wants the legacy "push doesn't touch local files" contract.
Each operation is reported individually in the output:
Would push 3 operation(s):
update MyButton components/MyButton.jsx (2.1KB)
create NewThing components/NewThing.jsx (1.3KB)
delete OldThing pages/OldThing.jsx (—)Naming new files
When you create a new local file, push infers:
- type from the directory:
components/→COMPONENT,pages/→PAGE,functions/→FUNCTION,entities/→ENTITY,Layout.jsxat the root →COMPONENT - name from the filename (without extension):
components/UserCard.jsx→UserCard
To control where a new component lives when the project has multiple workflow steps, read the step IDs from .agent-manifest.json and pass --step <id> (coming soon); today, creates go to the project's first active workflow step.
Settings
agentui project settingsPrints every workflow toggle the platform exposes — requiresLogin, requiresPartialLogin, allowSelfSignup, ssoEnabled, mfaEnabled, isFunctionAPIEnabled, isProductionLocked, isInstallableWebApp, isOfflineEnabled, isDeepLinkEnabled, isCustomIndexHtmlEnabled, isCustomAuditLogsEnabled, customDomain. The key list is the same WORKFLOW_SETTING_KEYS source the in-app QA prompt reads (apps/api/src/modules/langchain/resolvers/getQAQuestionsForAI.js), so the CLI and the chat agree by construction — add a key there and project settings surfaces it automatically.
agentui project settings set requiresLogin false # booleans: true/false, on/off, yes/no, 1/0
agentui project settings set customDomain app.acme.com
agentui project settings set customDomain none # "", "null", "none" clear itOne key per invocation — these flags change who can reach the app, so a mistyped batch write is worse than a second command. The server owns validation: an unknown key or an unparseable value is rejected with the list of writable keys / accepted values and nothing is written. Writes are delegated to the same mutations the dashboard uses, so the environment rebuild cascade, custom-domain validation, and function-credential minting are identical on both surfaces. When a change is baked into the build, the output says so — run agentui deploy for it to take effect in a running environment.
Settings live on the project's own workspace: if your active workspace differs, the command tells you to agentui workspace use <workspaceId> first rather than failing opaquely.
homePagePath — which page the app serves at / — is the one setting whose valid values depend on the project's contents, so the server resolves it against your real pages:
agentui project settings set homePagePath Reports # by name...
agentui project settings set homePagePath pages/Reports.jsx # ...or by file
agentui project settings set homePagePath none # back to the automatic choiceWithout a pin the build picks / by name (Home, Homepage, HomePage, Dashboard, DashboardPage, Main, Index, Landing, Welcome, Overview, App — else the first page that isn't Login or ResetPassword), which can move as you add or rename pages. Pinning stores the page's file path, so two pages named Dashboard in different folders stay distinguishable — pass the full path to disambiguate. A page that doesn't exist is rejected with the list of the ones that do (no silent no-op), and a pin whose page is later deleted degrades back to the automatic choice rather than leaving the app with no /. Login and ResetPassword can never be pinned. Takes effect on the next agentui deploy.
Open / share
agentui project open # editor (apps/app /chat/:id/chat)
agentui project open --preview # live preview (component-server URL)
agentui project open --preview --print # print the URL (CI / AI agent friendly)
agentui project link # mint a pre-authed deep link (7d, scope=newTab)
agentui project link --scope iframe # short-lived (1h) — for embedding
agentui project link --open # also launch a browserThe base URL (Blue.settings.public.appUrl) is fetched from the server on every sync/create and cached in ~/.agentui/settings.json + .agent.json — the CLI never hardcodes hosts, so self-hosted deployments work without flags.
project link mints a short-lived workflow-scoped JWT (x_deep_link_token=…) and prints the URL. Anyone with the link can act as you in this workflow until the token expires — share over a trusted channel only.
The app's icon and index.html
agentui project icon logo.png --yesUploads the image, publishes it (the platform FETCHES it to render the sizes,
so it has to be publicly readable — the command says so and asks for --yes)
and generates the 16, 32, 180 (apple-touch), 192 and 512 variants, then queues
a rebuild. It reports which sizes actually rendered, so an image the renderer
could not read shows up here instead of as a generic square on a home screen.
If Custom index.html is on for the project, the app's own index.html at the
project root is pushed with everything else. It is the ONLY .html the CLI
ships — other .html files stay out of the app, because the platform matches
this one by exact path.
Are the AI instruction files current?
sync writes AGENTS.md, .claude/CLAUDE.md, .github/copilot-instructions.md,
.cursor/rules/agentui.md and .windsurf/rules/agentui.md — then deliberately
never overwrites one you have edited, and a repo cloned from GitHub is never
synced at all. So a file here can describe the platform as it was months ago,
and nothing about it looks wrong.
Every generated file ends with a version stamp:
<!-- agentui-instructions v=<12-hex fingerprint> — verify with: agentui project instructions --check -->The version is a fingerprint of the instruction text itself, so it is the same in every project and changes only when the instructions change. It carries no timestamp, which is why an unchanged sync rewrites nothing.
agentui project instructions # current / stale / unstamped / missing, per file
agentui project instructions --check # exit 1 if any is out of dateA file with no stamp predates stamping and counts as out of date. If a file was
edited locally, sync parks the platform's copy at <file>.theirs rather than
overwriting your rules — the check says so, and tells you to merge rather than
re-sync.
env
The PROJECT's environments — the production/staging/custom deploy environments of your app on the platform (domains, versions, rebuild state). Server-touching subcommands require being inside a synced project and logged in; they degrade to actionable hints otherwise.
| Command | Description |
|--------------------------------------|-----------------------------------------------------------------------------------------------|
| agentui env list | This project's environments, fetched live. JSON: { project, environments, activeEnvironment } |
| agentui env use <name> | Set the active project environment — validated against the project's REAL envs (+ production, always valid); persists .agent.json.projectEnvironment |
| agentui env current | The active project environment + source (offline — reads .agent.json) |
| agentui env status [name] | One environment's details (type, URL, pinned version) plus live build freshness — built / up-to-date / stale / building-now, last-built time, served artifact version. Read-only: it never triggers a build. Defaults to the active selection |
| agentui env create <name> | Create a new environment (--type, --domain optional) — lets an agent bootstrap a sandbox |
| agentui env promote <from> <to> | Promote one environment's version to another by name; promoting into production requires --yes |
Each environment is an independent deploy of the app with its own separate database/data. A project can have as many as you like — development, testing, staging, production, or any custom name — promote a version from one to another with agentui env promote <from> <to>.
project sync, project push and deploy follow the active environment: a push from a folder on staging writes only staging's code (a new version of it) and never production's; production needs --yes. Every push saves a version you can restore from the editor's version history.
secrets
Secret names and their descriptions are visible; values are never returned by any CLI command, ever.
| Command | Description |
|---------------------------------------------------|----------------------------------------------------------------|
| agentui secrets list | Secrets available to the current project |
| agentui secrets request <NAME> | Associate an existing secret with the project, or create it |
secrets list flags
--project <id>— project ID (auto-detected from.agent.json)--accessible-only— only show secrets the project's workflows can currently use
secrets request flags
--description "..."— description for a new secret--value <v>— provide the value inline (shows in shell history; prefer--stdinor the interactive prompt)--stdin— read the value as a single line from stdin--project <id>— project ID
Behavior:
- Scope is this one workflow (the CLI's current project). Sibling workflows inside the same App container are not touched.
- If
<NAME>already exists in your company, it's associated with this workflow (if not already). Idempotent — re-running is safe. - If it doesn't exist and you provide a value, it's created (encrypted via AWS KMS / Azure Key Vault / local AES-256-GCM depending on server config) and associated with this workflow.
- If it doesn't exist and no value is provided, the command returns
404telling you to pass a value.
Naming rules: UPPER_SNAKE_CASE, must start with a letter, 1–64 chars (e.g. STRIPE_API_KEY). Values are capped at 8 KB.
validate
Runs the platform's canonical codeValidator server-side (same rules the AppCodeGenerator worker enforces). Only code files are scanned — .md, .json, and any non-jsx/js/tsx/ts path is skipped silently. The CLI doesn't keep its own rule copy, so rule coverage always matches what the runtime actually enforces.
agentui validate components/MyComponent.jsx
agentui validate --all # validate every component in the manifest
agentui --json validate --all # machine-parseable findings + skipped countFindings come back with {severity, file, line, message}. Exit code 1 iff any finding is severity: "error". Run agentui skills info code-validator for the current full rule list — it stays in sync with the backend.
build
Push ships code to the platform; build makes it live. The platform rebuilds an app lazily on its next page load — agentui build triggers that same rebuild deterministically and waits for it, using the exact component-server endpoints the in-app loading page uses (its status poll + Force Refresh). No new build machinery; the CLI behaves like the loading page.
agentui build # trigger + wait (default timeout 300s)
agentui build --no-wait # trigger and return immediately
agentui build --environment staging # build a specific project environment
agentui build --force # delete the existing build and rebuild from scratch
agentui --json build # { built, environmentName, stepId, durationMs, previewUrl, nextSteps }Flags: --environment <name> (defaults to the active agentui env use selection), --no-wait, --force, --timeout <seconds>.
If the build is already current, the command exits successfully with upToDate: true without rebuilding. Credentials are minted per-run by the platform (POST /cli/projects/:id/runtime-context) — short-lived and step-scoped.
deploy
Runs validation, then pushes updates for components already tracked in .agent-manifest.json. Does not create new components — use agentui project push for that.
agentui deploy --dry-run # validate + show the planned updates, ship nothing
agentui deploy --yes # validate, then publish updates to the live appFlags: --validate (default on), --dry-run, --yes (confirm a production deploy).
Untracked-file redirect. If deploy is run with local source files that aren't in the manifest yet (the common APP_V2 case right after init), it errors out explicitly:
Error: Found 3 untracked local file(s) (components/Foo.jsx, components/Bar.jsx, components/Baz.jsx).
`agentui deploy` only updates components already in .agent-manifest.json — it does not create new ones.
Use `agentui project push` to create + update in one step.Earlier this surfaced as "Nothing to deploy — no local files found" — a false-empty that read like user error. The redirect is the safer agent-facing contract.
skills
Platform skill documentation — the same docs the AppCodeGenerator LLM reads.
| Command | Description |
|--------------------------------------|-----------------------------------------------------|
| agentui skills list | All available skills |
| agentui skills info <name> | Full markdown content of a skill |
| agentui skills search <query> | Keyword search across skill names and content |
Skill docs are fetched from the server on every invocation — no local cache — so you always see the latest.
packages
Alias: pkg.
| Command | Description |
|-----------------------------------------|---------------------------------------------------------------|
| agentui packages list | Packages available to components at runtime |
| agentui packages list --category <c> | Filter: core, ui, charts, forms, export, etc. |
| agentui packages info <name> | Package version and docs (uses the matching skill, if any) |
| agentui packages categories | List all categories |
blueprints
Alias: bp.
| Command | Description |
|--------------------------------------|----------------------------------------------------------|
| agentui blueprints list | Starter templates you can fork from |
| agentui blueprints info <id> | Blueprint details |
| agentui blueprints create <id> | Create a new project from a blueprint |
prompts
Server-side prompt templates that can be reused in workflows.
| Command | Description |
|------------------------------------------|------------------------------------------------|
| agentui prompts list | All prompt templates |
| agentui prompts list --integration <x> | Filter to an integration |
| agentui prompts list --search <q> | Keyword search |
| agentui prompts info <id> | Template details |
Entity schemas
Every entity is a file: entities/<Name>.json (name + properties), written by sync and sent by push. For the live data tables and their fields in the active environment, run agentui data entities.
Older CLIs also wrote a table dump to entities/<Name>.schema.json. It is not an entity: push ignores it and sync deletes it.
functions
Alias: fn.
| Command | Description |
|---------------------------------------|-----------------------------------------------------|
| agentui functions list | Serverless functions in the project |
| agentui functions invoke [id] | Invoke a function through the app's live /api route |
| agentui functions logs <stepId> | Recent execution logs |
| agentui functions stats [stepId] | Invocation count, success rate, latency percentiles |
invoke calls the deployed function exactly the way browsers and webhooks do — POST https://<app-domain>/api/<name> with the workflow's public key. The [id] is a function name, component id, or file path; it's auto-resolved when the project has exactly one function.
agentui functions invoke # single-function project
agentui functions invoke sendEmail --data '{"to":"[email protected]"}'
agentui functions invoke seed --environment staging
agentui --json functions invoke sendEmail # { statusCode, durationMs, ok, response, … }Flags: --data <json> (default {}), --method <verb> (default POST), --environment <name>, --timeout <seconds> (default 60), --allow-stale.
Invoke refuses to run when the app has un-built changes — the function would execute stale code. Run agentui build first (or push with --build), or pass --allow-stale deliberately. Non-2xx responses exit 1 and include nextSteps (check functions logs, rebuild if stale).
integrations
Alias: int.
| Command | Description |
|-------------------------------------------------|------------------------------------------------------|
| agentui integrations list | Workspace integrations |
| agentui integrations list --authenticated | Only show connected integrations |
| agentui integrations list --not-authenticated | Only show disconnected |
| agentui integrations list --platform <p> | Filter by platform (stripe, slack, google, …) |
| agentui integrations list --type <t> | Filter by type |
| agentui integrations info <id> | Details for one integration |
| agentui integrations docs <platform> | Pull integration docs (from skills + prompts) |
| agentui integrations alerts | Recent alerts (auth expired, rate-limit, etc.) |
integration — build one for the community
Alias: ci. Turns an HTTP API into something every AgentUI builder can install
in one click. You describe the API once, in one JSON file; the platform handles
credentials, encryption, token refresh, retries and the proxy. No request code.
agentui integration guide # the whole playbook, offline
agentui integration new "Polygon.io" # a working starter spec
agentui integration check # offline, ~40ms — run it constantly
agentui integration check --fix # apply every machine-applicable fix
agentui integration test # real calls, through the real proxy
agentui integration publish # public and free| Command | Description |
|--------------------------------------------|------------------------------------------------------------------------|
| agentui integration guide | How to build one people actually install (no auth, no network) |
| agentui integration new <name> | Scaffold <slug>.integration.json and gitignore the credentials file |
| agentui integration check [file] | Validate offline; names the field, the consequence and the fix |
| agentui integration check --fix | Apply every fix the CLI can make safely, then report what is left |
| agentui integration test [file] | Run each endpoint's own test through POST /integrations/test-endpoint |
| agentui integration publish [file] | Publish using the spec's own visibility; --public / --private override |
| agentui integration list | Browse yours plus everything the community has shared |
| agentui integration pull <id> [file] | Download a published integration to edit; --fork makes your own copy, --force overwrites a local file |
Each step refuses to run until the one before it is green, so you cannot publish
an endpoint nobody has ever called. Every command supports --json.
The spec file. One object, committed to git:
{
"name": "Polygon.io",
"description": "Stock, option and crypto market data.",
"apiType": "rest", // or "graphql"
"baseUrl": "https://api.polygon.io", // no trailing slash
"visibility": "public",
"auth": {
"type": "api_key", // none | api_key | bearer | basic | oauth2
// custom | hmac | oauth1 | digest | session
"credentialFields": [
{ "name": "apiKey", // read BY NAME at call time — not "key"
"label": "API Key",
"help": "Dashboard → Keys", // where the installer finds it
"location": "query", // "header" | "query" | "url"
"headerName": "apiKey" } // what it is CALLED on the wire
]
},
"endpoints": [
{ "id": "listTickers",
"method": "GET",
"path": "/v3/reference/tickers",
"description": "Lists tradable tickers. Call it before any per-ticker lookup.",
"parameters": [{ "name": "limit", "in": "query", "type": "number",
"description": "How many to return (1-1000)." }],
"test": { "query": { "limit": 1 }, "expectStatus": 200 } }
],
"errorMap": [
{ "status": 401, "message": "The API rejected the key.",
"fix": "Regenerate it under Dashboard → Keys, then reconnect." }
]
}Visibility. publish uses the spec's own visibility field. Pass --public
or --private to override it; whichever is used is written back to the spec, so
a later plain publish cannot silently change it. Pulling another workspace's
integration always forks — you can only publish your own copy of it.
Credentials never go in the spec. The spec is published; your key is not.
Put it in .agentui-credentials.json (created gitignored by integration new)
or pass --credential apiKey=…. check refuses a spec carrying anything that
looks like a live key anywhere in it — including under auth or config — and
publish sends only the auth keys the runtime actually reads, so a leftover
value cannot ride along into a row every installer can see. Test output redacts
any credential the API quotes back at you.
Readiness score. check, test and publish print a 0-100 breakdown across
five dimensions: spec validity, endpoints proven against the real API, test
coverage, how well another builder's AI could choose between your endpoints, and
whether a failure is recoverable from your errorMap and credential help. The
headline is gated on validity, so a spec that cannot be published never reads as
nearly ready.
automation
An app's automations live in the app's own project folder. On the platform an automation is a sibling workflow sharing the app's container, so it already reaches the app's data — keeping it here means one repo, one PR, one review.
| Command | Description |
|------------------------------------------------------|--------------------------------------------------------------------|
| agentui automation list | Every automation, what fires it, next run, last run's status |
| agentui automation create "<name>" | New automation + its folder, ready to work in |
| agentui automation pull [name] [--all] | Write each step to automations/<name>/steps/ |
| agentui automation show [name] [--step <s>] | What the PLATFORM holds now, and which local files differ |
| agentui automation push [name] [--dry-run] | Send your edits back |
| agentui automation run [name] [--watch] [--data] | Run it; --watch waits and prints the result |
| agentui automation logs [name] [--list] [--run] | The last run's output, step by step, or the run history |
| agentui automation trigger list\|set\|rm\|incoming | What fires it, and what your first step receives |
The filename is the structure. Its number is the execution order, renaming it renames the step, deleting it deletes the step:
automations/daily-report/
├── automation.json ← generated. Do NOT edit by hand.
└── steps/
├── 001-fetch-orders.js
└── 002-send-summary.jsSteps run on Deno, so import what you use (import axios from "npm:axios";).
agentui automation create "Daily report"
# write automations/daily-report/steps/001-fetch.js
agentui automation push
agentui automation trigger set cron "0 9 * * *" --tz America/Mexico_City
agentui automation run --watchA rename is only recognised as a rename while the file's contents are
unchanged — push the rename on its own, then edit. Deleting a step file takes
its run history with it, and push warns before it does.
data
Read your app's records from the terminal, and see who can reach them. Read-only by design: writes go through the app, an automation, or the dashboard, where your app's own rules run.
| Command | Description |
|----------------------------------------------------|------------------------------------------------------------|
| agentui data entities | The app's entities and their fields |
| agentui data list <entity> [--where ...] | List records |
| agentui data get <entity> <id> | One record |
| agentui data count <entity> [--where ...] | Count, honouring the same filter |
| agentui data security | Current per-table rules + what a rule can compare against |
| agentui data security suggest <Table> … | Propose permissions as a link the user accepts |
Every command reads the environment agentui env current reports, and prints
which one it read — rows are meaningless without that label.
Row-level security is proposed, never changed here. suggest prints a link
that opens Data Security with the proposal filled in and an Accept button:
agentui data security
agentui data security suggest Invoice \
--read authenticated --update creator --delete admin \
--reason "Financial records"A proposal that would match no records — a field or a user property that does
not exist — is refused before the link is created, because accepting one locks
every user out of their own data with no error. Run agentui guide security
for the full access vocabulary; it is generated from the platform's own
registry, so it is never out of date.
files
Workspace file storage.
| Command | Description |
|-----------------------------------------------|---------------------------------------------------------------------|
| agentui files upload <path> [--public] | Upload. Private by default; --public returns a permanent URL |
| agentui files list [--all] | List workspace files (the platform pages at 100) |
| agentui files download <fileId> [--out] | Download to disk |
| agentui files publish <fileId> --yes | Make an existing private file public |
| agentui files url <fileId> | Mint a temporary share link |
| agentui files delete <fileId> --yes | Delete |
upload prints a file id and download prints a path — a signed URL is a
bearer credential for one object, so it never leaves the process. files url
is the one explicit share verb, and it says the expiry and who it grants
access to.
logs
What actually happened at runtime.
| Command | Description |
|-------------------------------------------|-------------------------------------------------------------------------|
| agentui logs invocations [--limit ...] | Function invocations: method, path, status, duration, console output |
| agentui logs telemetry | Recurring runtime errors, sorted by how often they happen |
Failures come first and the payload is capped, so the output stays readable when something is failing in a loop.
guide
The live playbook for whoever is driving this CLI — usually an AI agent.
agentui guide # the whole thing
agentui guide security # one topic
agentui guide automationsServed from the platform, not bundled, so it can be corrected without waiting
for a release. Topics include new-project, integrations, external-api,
send-email, secrets, deploy, debug, automations, data-security,
pwa-icon, custom-index-html, external-db and open-in-app.
feedback
agentui feedback "<what you want to say>"Product feedback, straight from the terminal. For something that is broken or
missing, use report instead — it
attaches the command that failed.
report — something is broken or missing
Use it the moment you hit a wall. A workaround you keep to yourself leaves the wall standing for everyone behind you, and you are usually the only person who will ever see the exact failure.
agentui report broken "integration test times out on an API that answers in 12s"
agentui report missing "no way to list an app's cron schedules"
agentui report unclear "the deploy guide says push first, but push needs a build"| Command | Goes in as | For |
|---|---|---|
| agentui report broken <msg> | bug | a command, endpoint or behaviour that is wrong |
| agentui report missing <msg> | feature_request | a capability that does not exist |
| agentui report unclear <msg> | harness | docs or an error that pointed the wrong way |
report broken attaches the last failed command automatically — the exact
invocation, the exact error, the CLI version, the platform — so none of it has
to be remembered or retyped. Arguments are scrubbed first: --credential,
--token, --password and anything shaped like a live API key never leave the
machine.
| Flag | |
|---|---|
| --expected <text> | What should have happened. The single most useful line in a report. |
| --dry-run | Print exactly what would be sent, and send nothing. |
| --no-last / --last | Turn the failed-command attachment off, or on for a kind that does not do it by default. |
| --stdin | Read a long message from stdin. |
| --force | Send even if an identical report already went today. |
Identical reports are de-duplicated for 24 hours and capped at 5 per hour, so an agent retrying a failing command cannot spam anyone. A suppressed report exits 0 and says why — it is not an error, and retrying it is not the answer.
Set AGENTUI_HOME to relocate where the CLI keeps this state (CI wants that).
agent-skill — teach your coding assistant
Installs a global skill so Claude Code, Codex, Cursor and other assistants use agentui to host apps, upload files and create databases instead of setting that up by hand.
agentui agent-skill install # install or update
agentui agent-skill status # which assistants have it
agentui agent-skill removeIt writes skills/agentui-cli/SKILL.md only into assistants already on your machine: ~/.claude, ~/.codex, and ~/.agents (read by Cursor, Gemini CLI, OpenCode…; used when any of them is present). It never edits your CLAUDE.md, and never overwrites or deletes a skill you wrote at that path. Start a new assistant session to pick it up.
Editor and agent plugins
The commands above are the contract; agentui-tools
is how an AI assistant finds out they exist. It is one plugin with manifests for Cursor,
Claude Code and the Agent Plugins format, wrapping this CLI
in model-invoked skills — so asked for "a tool to track X", the assistant reaches for
agentui project create instead of scaffolding Next.js + Postgres + S3 by hand.
# Cursor
git clone https://github.com/agentui-ai/agentui-tools.git ~/.cursor/plugins/local/agentui-tools
# Claude Code
claude --plugin-dir ./agentui-toolsMaintainers: this README and that plugin are two copies of the same contract. A change to a command, a flag, a guardrail or a default here is a change there. The plugin's skills were written against
apps/cli/src, not against this file — the two have drifted before (deploydoes create components;validateexits 0 on findings; a productionbuildneeds--yes), and an assistant acting on the stale half does not fail loudly, it confidently does the old thing. When you change the CLI, open a PR onagentui-toolsin the same breath, the way you would update--help.
Global flags
Work on every command:
| Flag | Description |
|-----------------------|-----------------------------------------------------------------------------|
| --json | Output JSON (see JSON output mode) |
| --version | Print the CLI version and exit |
| --help | Print help for the current command |
JSON output mode
Pass --json on the root command and every subcommand will emit machine-parseable JSON on stdout:
agentui --json project list{
"total": 2,
"count": 2,
"projects": [
{
"id": "cmo8…",
"appId": "cmo7…",
"name": "Mercury Dashboard",
"type": "APP_V2",
"status": "ACTIVE",
"published": false,
"updatedAt": "2026-04-21T14:43:55.867Z"
},
{
"id": "cmo9…",
"appId": "cmo7…",
"name": "Nightly Report",
"type": "AUTOMATION",
"status": "ACTIVE"
}
]
}Errors are structured too:
agentui --json project sync does-not-exist{ "error": "Project not found", "details": null }On error, the process exits with code 1 — JSON still goes to stdout.
This is the contract AI coding assistants rely on. No ANSI color, no spinners, no tables — just JSON.
Config files
| Path | Contents |
|----------------------------------------------|----------------------------------------------------------|
| ~/.agentui/credentials.json (0600) | { token, userId, email } |
| ~/.agentui/settings.json | { activeWorkspace: { id, name } } |
| ./.agent.json (per project) | { projectId, projectName, projectType, appId, projectEnvironment, platformApi?, syncedAt } — projectId is a workflow id; projectEnvironment is the app environment this folder follows (agentui env use), platformApi the AgentUI backend (lead-only, rarely set) |
| ./.agent-manifest.json (per project) | Component map with per-component codeHash, workflow IDs, version snapshots |
Both per-project files are added to .gitignore automatically — don't commit them.
Project structure on disk
After agentui project sync <id>:
my-project/
├── .agent.json
├── .agent-manifest.json
├── .gitignore
├── Layout.jsx
├── components/
│ ├── Header.jsx
│ └── UserCard.jsx
├── pages/
│ ├── Dashboard.jsx
│ └── Settings.jsx
├── entities/
│ └── Patient.json
└── functions/
└── sendEmail.jsx- The
.agent.jsonand.agent-manifest.jsonfiles are the CLI's state. If you delete them,pushwon't know how to map your files back to the server. - File names are sanitized on sync: illegal filesystem characters are stripped, whitespace becomes
_, names are capped at 200 chars. - Duplicate component names inside the same type directory get a
_<stepSuffix>disambiguator.
Safety and multi-tenant guarantees
- Path traversal blocked.
../, absolute paths, URL-encoded traversal, and symlinks out of the project directory are all rejected for reads, writes, and deletes. - Multi-tenant isolation. Every server endpoint verifies the authenticated user's
companyIdowns the workflow, workflow step, component, and secret being touched. Cross-tenant access returns404, not403, to avoid leaking existence. A dedicated test suite (cli.tenant-isolation-smoke.test.js) exercises every /cli/* endpoint from Tenant B against Tenant A's resources with DB-level assertions. - Workflow isolation. Two workflows inside the same App container are strictly isolated. Syncing workflow A never returns workflow B's components; pushing a workflow-A-scoped op against workflow B's component id fails per-op.
- Secret values never leave the server. Not in
secrets list, not insecrets requestresponses, not insyncbundles. - Push payload limits. Max 50 operations per batch, 1 MB total UTF-8 bytes (emoji-safe byte counting, not UTF-16 code units).
- Atomic version bumps. Even with N concurrent pushes from different CLIs racing on the same component, each push gets a unique version number — no lost updates.
- Archived projects reject writes. Pushing or requesting secrets on an archived app returns
404.
Exit codes
| Code | Meaning |
|------|----------------------------------------------------------|
| 0 | Success |
| 1 | Any error — validation, auth, network, server error. Inspect stderr or --json stdout for details. |
Troubleshooting
Not authenticated. Run 'agentui auth login' first.'
You've never logged in on this machine, or your token was revoked. Run agentui auth login again.
Session expired. Run 'agentui auth login'
Your token was valid but the user/session was deleted server-side. Re-login.
No project found. Run 'agentui project sync <id>' first.
You're running a project-scoped command outside a synced project directory. Either cd into one or pass --project <id>.
Project not found when you know it exists
Three likely causes, in order:
- You passed an App id instead of a workflow id.
<projectId>is a workflow id now (the "Project ID" column ofproject list). - Your
.agent.jsonis from a pre-0.2.0 sync and still holds an App id. Re-sync once with a workflow id to migrate. - The authenticated user belongs to a different company than the workflow. Check with
agentui auth whoamiandagentui workspace current.
Push failed with 1 MB error
Your batch is too big. Split into smaller pushes, or drop large components into a separate push.
Components created in the wrong workflow step
Today, push creates new components in the project's first active workflow step. For explicit control, pass workflowStepId directly (see the API docs) — a --step flag is planned.
The server returns an error I don't understand
Run with --json to get the raw error envelope, or report an issue with the full output: https://github.com/nesbtesh/agentUI/issues.
License
MIT
