Skip to Content
CLI ReferenceCommand Reference

Command Reference

This page documents every command group available in the Foir CLI. Commands follow a consistent foir <group> <action> pattern. All commands support the global --json, --jsonl, --quiet, and --project flags described in the CLI Overview.

Authentication & Setup

login

Authenticate the CLI via browser-based OAuth. Opens your default browser to sign in and writes a session token to ~/.foir/credentials.json once you complete the flow. Run this first on any new machine.

foir login [options]
OptionDescription
--deviceUse the device flow: approve on any device with a short code (for SSH, containers, CI). Auto-selected when no local browser is detected.
--no-browserAuthenticate without a local browser callback by pasting a one-time code back into the terminal.

The default login flow:

  1. Opens your default browser at the Foir sign-in page.
  2. You sign in (or pick an existing session).
  3. The browser hands a short-lived authorization code back to the CLI listening on a local port.
  4. The CLI exchanges the code for a session token and saves it to ~/.foir/credentials.json.

When no local browser is detected (SSH, containers, CI), foir login automatically falls back to the device flow — it prints a short code and a URL to approve on any other device, then waits for approval. Pass --device to force this, or --no-browser to paste a one-time code back into the terminal instead.

Examples

# Default: opens a local browser foir login # Headless: approve a short code on any device (SSH / containers / CI) foir login --device # Out-of-band: paste a one-time code back into the terminal foir login --no-browser

logout

Clear stored credentials. Removes ~/.foir/credentials.json and any cached session state.

foir logout

whoami

Show the current authentication status — which user is signed in, which tenant + project are active, and which credentials file is in use.

foir whoami

Useful for confirming you’re operating on the project you think you are before running a destructive command. Combine with --json to script against the output.

select-project

Pick the active project for subsequent CLI calls. Lists every project your session has access to, provisions a scoped API key, and writes the selection to .foir/project.json at your repository root so later commands don’t need a --project flag.

foir select-project [options]
OptionDescription
--project-id <id>Skip the interactive picker and select a project directly.
--save-as <name>Save the selection as a named profile (see foir profiles).

Examples

# Interactive picker foir select-project # Switch without the prompt foir select-project --project-id prj_abc123 # Save the selection as a profile so you can switch back later foir select-project --project-id prj_abc123 --save-as staging

profiles

Manage named project profiles — bookmarks for tenant/project combinations so you can switch between environments (dev, staging, prod) without re-running select-project each time. Each profile is just a saved { tenantId, projectId } pair pinned to a name.

CommandDescription
foir profiles listList all saved profiles
foir profiles show [name]Show details of a profile (or the active one if no name)
foir profiles default [name]Show or set the default profile
foir profiles delete <name>Delete a named profile
OptionApplies toDescription
--confirmdeleteSkip confirmation prompt.

Activate a saved profile with the global --project <name> flag (see CLI Overview).

Examples

# List profiles foir profiles list # Inspect the active profile foir profiles show # Set the default profile so naked CLI calls use staging foir profiles default staging # Remove a profile foir profiles delete old-tenant --confirm

workspaces create

Create a workspace from the terminal. You become its owner, it starts on the free plan, and it comes with a default project — the same atomic flow as the dashboard’s New workspace. While public sign-ups are closed, workspace creation is declined server-side (your account and any workspaces you’ve been invited to are unaffected).

foir workspaces create --name <name> [options]
OptionDescription
--name <name>Workspace name (required).
--project-name <name>Name for the default project. Defaults to "<name> Project".
--selectMake the new workspace’s default project the active CLI context (same save path as select-project).

Examples

# Create a workspace and start pushing immediately foir workspaces create --name "Acme Studio" --select foir push # Scripting-friendly output foir workspaces create --name "Acme Studio" --json

projects create

Create a project in a workspace you own. Requires the projects:write permission in that workspace (owners have it).

foir projects create --name <name> [options]
OptionDescription
--name <name>Project name (required).
--tenant <id>Workspace to create the project in. Defaults to your active session workspace; with several workspaces and no default, an interactive picker opens.
--selectMake the new project the active CLI context.

Examples

# Create in the active workspace and switch to it foir projects create --name "Marketing Site" --select # Target a specific workspace foir projects create --name "Marketing Site" --tenant ten_abc123

Content Management

records

Manage content records within a model.

CommandDescription
foir records list <modelKey>List records for a model
foir records get <modelKey> <idOrKey>Get a record by ID or natural key
foir records create <modelKey>Create a record
foir records update <modelKey> <id>Update a record’s data column directly (bypasses versioning)
foir records save <modelKey> <id>Atomic draft save (data + new version + currentVersionId bump)
foir records delete <modelKey> <id>Delete a record
foir records publish <versionId>Publish a record version
foir records unpublish <id>Unpublish a record
foir records duplicate <modelKey> <id>Duplicate a record
foir records versions <recordId>List versions for a record
foir records variants <recordId>List variants for a record
foir records create-version <parentId>Low-level: create a version row without touching the parent
foir records create-variant <recordId>Create a variant
OptionApplies toDescription
--filter <expr>listFilter expression (e.g. status=active). See Filtering.
--first <n>list, versionsPage size. Default: 20.
--after <cursor>listCursor for the next page (from prior pageInfo).
--resolvedgetInclude resolved content (published version).
--previewgetResolve the latest draft instead of the published version.
--locale <locale>getLocale for field translations.
-d, --data <json>create, update, save, create-versionData as a JSON string.
-f, --file <path>create, update, save, create-versionRead data from a file.
-m, --message <msg>save, create-versionChange description.
--variant <key>saveSave into a specific variant.
--natural-key <key>duplicateNatural key for the duplicate.
--key <variantKey>create-variantVariant key (required).
--confirmdeleteSkip confirmation prompt.

update vs save: records update writes the record’s data column directly and does not create a version or move currentVersionId — preview/storefront won’t see the change. records save is the admin “Save Draft” equivalent: it replaces data, writes an immutable version row, and advances currentVersionId in one atomic step.

Examples

# List published records, page size 10 foir records list blog-post --filter "status=published" --first 10 # Get a record by natural key (model key is positional) foir records get page hello-world # Get the resolved published content foir records get page hello-world --resolved # Create a record from a JSON file foir records create page --file page.json # Atomic draft save (data + version + currentVersionId) foir records save page clx123 --file page.json --message "Update hero copy" # Publish a version by its version ID foir records publish ver_abc123 # List all versions of a record foir records versions clx1234567890

models

Manage content models (schemas).

CommandDescription
foir models listList all models
foir models get <key>Get a model by key
foir models createCreate a model
foir models update <key>Update a model
foir models delete <key>Delete a model
foir models versions <key>List schema versions for a model
OptionApplies toDescription
--category <cat>listFilter by category.
--search <term>listSearch by name.
--first <n>list, versionsMax results. Default: 50 for list, 20 for versions.
--after <cursor>listOpaque cursor from a previous page.
-d, --data <json>create, updateModel data as a JSON string.
-f, --file <path>create, updateRead model data from a file.
--confirmdeleteSkip confirmation prompt.

Examples

# List models in a category foir models list --category content # Search models by name foir models list --search blog # Create a model from a JSON file foir models create --file blog-post-model.json # Update a model by key foir models update blog-post --file blog-post-model.json # View schema version history (by model key) foir models versions blog-post

locales

Manage locales for content localization.

CommandDescription
foir locales listList all locales
foir locales get <idOrCode>Get a locale by ID or code
foir locales defaultGet the default locale
foir locales createCreate a locale
foir locales update <id>Update a locale
foir locales delete <id>Delete a locale

Examples

# List all locales foir locales list # Get a locale by code foir locales get en-US # Get the default locale foir locales default # Create a new locale foir locales create --data '{"locale":"fr-FR","displayName":"French","nativeName":"Francais"}'

media

Upload and manage media files. The media group handles file uploads via the storage service, while file metadata commands are available through the dynamic files group.

CommandDescription
foir media upload <filepath>Upload a file
foir media listList files
foir media get <id>Get file details
foir media update <id>Update file properties
foir media update-metadata <id>Update alt text, caption, description
foir media delete <id>Delete a file
foir media restore <id>Restore a deleted file
foir media usageGet storage usage stats

Examples

# Upload a file to a specific folder foir media upload ./images/hero.jpg --folder banners # List files filtered by folder foir media list --folder banners # Search for files foir media list --search "hero" # Update file metadata foir media update-metadata clx123 --alt-text "Hero banner image" --caption "Welcome banner" # Check storage usage foir media usage # Permanently delete a file (cannot be restored) foir media delete clx123 --confirm --permanent

files

Inspect and manage files in the media library. For uploads use foir media upload; this group covers everything after upload — listing, renaming, tagging, moving between folders, editing alt text and captions, and reporting storage usage.

CommandDescription
foir files listList files
foir files get <id>Get a file by ID
foir files usageStorage usage statistics
foir files update <id>Update file properties (filename, folder, tags)
foir files update-metadata <id>Update alt text, caption, description
foir files delete <id>Delete a file
OptionApplies toDescription
--folder <folder>list, updateFilter by folder / move to folder.
--mime-type <type>listFilter by MIME type.
--search <term>listSearch by filename.
--first <n>listMax results. Default: 50.
--after <cursor>listOpaque cursor from a previous page.
--filename <name>updateNew filename.
--tags <tags>updateComma-separated tags.
--alt-text <text>update-metadataAlt text.
--caption <text>update-metadataCaption.
--description <text>update-metadataDescription.
--confirmdeleteSkip confirmation prompt.

Examples

# List images in the /banners folder foir files list --folder banners --mime-type image/jpeg # Search by filename foir files list --search hero # Move a file to a different folder foir files update clx123 --folder archive # Tag a file foir files update clx123 --tags "homepage,launch,q2" # Add alt text + caption for accessibility / SEO foir files update-metadata clx123 \ --alt-text "A woman walking through a field of barley at sunrise" \ --caption "Spring '26 campaign" # Storage usage summary foir files usage --json

Search across all records globally.

foir search <query> [options]
OptionDescription
--models <keys>Filter to specific model keys (comma-separated)
--first <n>Maximum number of results (default: 20)

Examples

# Search across all content foir search "getting started" # Search within specific models foir search "pricing" --models page,blog-post --first 5 # Output as JSON for scripting foir search "hello" --json

rollouts

Manage rollouts — bulk scheduled-publishing batches that promote a mixed set of records, models, operations, auth providers, and other publishable resources together at a chosen time. The admin equivalent is Scheduled Publishing → Rollouts; see Scheduled Publishing for the feature overview.

CommandDescription
foir rollouts listList rollouts
foir rollouts get <id>Get a rollout (with its items)
foir rollouts createCreate a rollout
foir rollouts update <id>Update name, description, or scheduledAt
foir rollouts delete <id>Delete a rollout before it runs
foir rollouts trigger <id>Trigger a rollout immediately (ignore its scheduled time)
foir rollouts pause <id>Pause an in-flight rollout
foir rollouts resume <id>Resume a paused rollout
foir rollouts retry <id>Retry failed items in a rollout
foir rollouts rollback <id>Roll back a completed rollout
foir rollouts add-items <id>Add items (records / models / operations / etc.) to a rollout
foir rollouts remove-items <id>Remove items from a rollout
OptionApplies toDescription
--status <status>listFilter by status.
--first <n>listPage size.
--after <cursor>listOpaque cursor from a previous page.
-d, --data <json>create, update, add-items, remove-itemsPayload as a JSON string.
--file <path>create, update, add-items, remove-itemsPayload from a JSON file.
--previewrollbackPreview the rollback without executing — useful for confirming scope.
--confirmdelete, rollbackSkip confirmation prompt.

Note on lifecycle: use delete for rollouts that haven’t been triggered yet, rollback for ones that have. The CLI rejects mixing these.

Examples

# Create a rollout scheduled for next Monday foir rollouts create --data '{ "name": "Weekly Release", "scheduledAt": "2026-05-19T09:00:00Z", "items": [ { "kind": "record", "versionId": "ver_abc123" }, { "kind": "record", "versionId": "ver_def456" } ] }' # Inspect the rollout, including its items foir rollouts get rollout_abc123 --json # Add more items to a draft rollout foir rollouts add-items rollout_abc123 --file ./additional-items.json # Trigger immediately, skipping the scheduled time foir rollouts trigger rollout_abc123 # Pause while it runs, then resume foir rollouts pause rollout_abc123 foir rollouts resume rollout_abc123 # Retry items that failed during the run foir rollouts retry rollout_abc123 # Preview a rollback before committing foir rollouts rollback rollout_abc123 --preview # Execute the rollback foir rollouts rollback rollout_abc123 --confirm # Delete a rollout that never ran foir rollouts delete rollout_abc123 --confirm

Customers and Targeting

customers

Manage customer accounts.

CommandDescription
foir customers listList customers
foir customers get <idOrEmail>Get a customer by ID or email
foir customers create --email <email>Create a customer
foir customers delete <id>Delete a customer (hard delete for GDPR)
OptionApplies toDescription
--status <status>listFilter by status (ACTIVE, PENDING, SUSPENDED).
--search <term>listSearch by email.
--first <n>listMax results. Default: 20.
--after <cursor>listOpaque cursor from a previous page.
--email <email>createCustomer email (required).
-d, --data <json>createAdditional customer data as a JSON string.
--confirmdeleteSkip confirmation prompt.

Examples

# List active customers foir customers list --status active # Get a customer by email foir customers get user@example.com # Create a customer foir customers create --email new@example.com # Create a customer with extra data foir customers create --email new@example.com --data '{"name":"New User"}'

Profile schemas: A customer’s profile fields are declared in foir.config.ts and reconciled with foir push — there is no standalone CLI command for editing the profile schema. Use the admin app or your config file to change profile fields.

customer-roles

Manage customer RBAC roles — the scope sets attached to customer access tokens. A customer token’s scopes are the union of the customer’s role permissions; a role marked default grants its permissions to every customer with no explicit assignment. The declarative equivalent is the customerRoles block in foir.config.ts, reconciled by foir push; this group is for one-off CRUD and assignment management.

CommandDescription
foir customer-roles listList customer roles in the current project
foir customer-roles createCreate a customer role
foir customer-roles update <id>Update a role’s name, permissions, or default flag
foir customer-roles disable <id>Disable a customer role
foir customer-roles assignAssign a role to a specific customer
foir customer-roles revoke <assignmentId>Revoke a role assignment
foir customer-roles assignmentsList role assignments for a customer or a role
OptionApplies toDescription
--first <n>listMax results. Default: 100.
--key <key>createStable role key (e.g. default). Required.
--name <name>create, updateDisplay name. Required for create.
--permissions <scopes>create, updateComma-separated scopes (e.g. self:*,operations:execute). Required for create; replaces scopes on update.
--defaultcreate, updateMake this the project default role (all customers inherit it).
--no-defaultupdateClear the project-default flag.
--customer <id>assign, assignmentsCustomer ID (required for assign).
--role <id>assign, assignmentsRole ID (required for assign).
--confirmdisable, revokeSkip confirmation prompt.

For assignments, pass at least one of --customer <id> or --role <id>. Customers must log in again to pick up newly assigned or changed scopes.

Examples

# List customer roles foir customer-roles list # Create a default role granting self-access to customer-writable records foir customer-roles create --key default --name "Default" --permissions "self:*" --default # Add operation execution to a role foir customer-roles update clx_role_123 --permissions "self:*,operations:execute" # Assign a role to a specific customer foir customer-roles assign --customer clx_cust_456 --role clx_role_123 # List a customer's role assignments foir customer-roles assignments --customer clx_cust_456 # Revoke an assignment foir customer-roles revoke clx_assign_789 --confirm

context-dimensions

Manage context dimensions — the home of segments (sourceType: 'segment', a rule evaluated into segment.<key>) and customer-context sources (sourceType: 'model'). Prefer declaring them in your config (see Defining Context Dimensions); this command is for one-off inspection and edits. Aliased as foir context-dims.

foir push auto-publishes context dimensions on create, so use foir context-dimensions publish <id> to promote a subsequent edit to the published channel.

CommandDescription
foir context-dimensions listList context dimensions
foir context-dimensions get <idOrKey>Get a dimension by ID or key
foir context-dimensions createCreate a dimension (--data <json> / --file <path>)
foir context-dimensions update <id>Update a dimension
foir context-dimensions publish <id>Promote a dimension draft to the published channel
foir context-dimensions delete <id>Delete a dimension

Examples

# List context dimensions (segments + model sources) foir context-dimensions list # Create a segment from JSON foir context-dimensions create --data '{ "key": "gold", "name": "Gold", "sourceType": "segment", "evaluationRules": { "type": "group", "logicalOperator": "AND", "conditions": [] } }'

variant-catalog

Manage the variant catalog for content personalization.

CommandDescription
foir variant-catalog listList variant catalog entries
foir variant-catalog get <idOrKey>Get an entry by ID or key
foir variant-catalog createCreate a variant catalog entry
foir variant-catalog update <id>Update a variant catalog entry
foir variant-catalog delete <id>Delete a variant catalog entry

Examples

# List all variant catalog entries foir variant-catalog list # Get a variant by key foir variant-catalog get premium-users # Create a new variant catalog entry foir variant-catalog create --data '{"key":"mobile","name":"Mobile Users","isActive":true}'

context

Inspect and switch the CLI’s session context — the tenant and project subsequent commands run against. This is session/project management, not targeting data; the active project is persisted in .foir/project.json (see the CLI Overview).

CommandDescription
foir context projectsList projects your session can access (the active one is marked)
foir context switch <projectId>Switch the active project
foir context tenantsList tenants your session can access

Examples

# See which projects you can use and which is active foir context projects # Switch to a different project foir context switch prj_abc123 # List available tenants foir context tenants

After context switch, run foir select-project to provision a scoped API key for the newly selected project.

Automation

operations

Run and inspect server-side operations. Operations themselves are declared in foir.config.ts and reconciled with foir push — this group executes them and manages their dead-letter queue.

CommandDescription
foir operations listList operations
foir operations get <key>Get an operation by key
foir operations execute <key>Execute an operation
foir operations dead-lettersList failed operations in the dead letter queue
foir operations retry-dead-letter <id>Retry a failed operation
foir operations dismiss-dead-letter <id>Dismiss a failed operation without retrying
OptionApplies toDescription
--category <cat>listFilter by category.
--activelistOnly active operations.
--first <n>list, dead-lettersMax results. Default: 50 for list, 20 for dead-letters.
-d, --data <json>executeInput data as a JSON string.
-f, --file <path>executeRead input from a file.
--asyncexecuteExecute asynchronously.
--operation <key>dead-lettersFilter the queue by operation key.

Examples

# List all operations foir operations list # Execute an operation with input data (key is positional) foir operations execute send-welcome-email --data '{"userId":"clx123"}' # Execute asynchronously foir operations execute long-running-report --data '{"month":"2026-05"}' --async # View the dead letter queue foir operations dead-letters # Retry a failed operation foir operations retry-dead-letter clx_dl_456

hooks

Manage lifecycle hooks — webhooks that fire on platform events (record.published, record.deleted, etc.). Hooks can also be declared in foir.config.ts and reconciled with foir push; this group is for one-off CRUD and for inspecting delivery history that lives outside the config file.

CommandDescription
foir hooks listList hooks
foir hooks get <keyOrId>Get a hook by key or ID
foir hooks createCreate a hook
foir hooks update <id>Update a hook
foir hooks delete <id>Delete a hook
foir hooks deliveries <hookId>List recent deliveries for a hook
foir hooks retry-delivery <deliveryId>Retry a failed delivery
foir hooks test <hookId>Send a test delivery
OptionApplies toDescription
--event <event>listFilter by event name.
--activelist, updateList only active hooks / activate a hook.
--inactivelistList only inactive hooks.
--no-activeupdateDeactivate a hook.
--first <n>list, deliveriesPage size.
--after <cursor>list, deliveriesOpaque cursor from a previous page.
--status <status>deliveriesFilter deliveries by status (success, failed, pending).
-d, --data <json>create, update, testPayload as a JSON string.
--file <path>create, update, testPayload from a JSON file.
--confirmdeleteSkip confirmation prompt.

Examples

# List active hooks for a specific event foir hooks list --event record.published --active # Create a hook from a JSON file foir hooks create --file ./hooks/on-publish.json # Inline create foir hooks create --data '{"key":"on-publish","name":"On Publish","event":"record.published","url":"https://example.com/webhook"}' # Deactivate without removing foir hooks update hook_abc123 --no-active # Recent failed deliveries for a hook foir hooks deliveries hook_abc123 --status failed --first 20 # Send a synthetic delivery to verify the receiver foir hooks test hook_abc123 --data '{"message":"test"}' # Retry one failed delivery foir hooks retry-delivery del_456

schedules

Manage scheduled tasks with cron expressions.

CommandDescription
foir schedules listList schedules
foir schedules get <key>Get a schedule by key
foir schedules createCreate a schedule
foir schedules update <key>Update a schedule
foir schedules trigger <key>Trigger a schedule immediately
foir schedules pause <key>Pause a schedule
foir schedules resume <key>Resume a paused schedule
foir schedules delete <key>Delete a schedule

Examples

# List all schedules foir schedules list # Create a scheduled task foir schedules create --file daily-sync.json # Trigger a schedule immediately (outside its cron) foir schedules trigger daily-sync # Pause a schedule foir schedules pause daily-sync

Administration

settings

Manage project settings.

CommandDescription
foir settings listList all settings
foir settings get <key>Get a setting by key
foir settings set <key> <value>Set a setting value
foir settings reset <key>Delete a setting (reset to default)
OptionApplies toDescription
--category <cat>list, setFilter by category / category for the setting (required for new settings).
--data-type <type>setData type: STRING, NUMBER, BOOLEAN, or JSON. Inferred from the value if omitted.

Examples

# List all settings foir settings list # Get a specific setting foir settings get site.name # Set a setting value (key and value are positional) foir settings set site.name "My Site" --category general # Reset a setting back to its default foir settings reset site.name

design-tokens

Manage the project’s design tokens document.

CommandDescription
foir design-tokens getPrint the current document
foir design-tokens apply <path>Apply a W3C-formatted JSON document from disk
foir design-tokens publishPromote draft → published
foir design-tokens unpublishRemove the published snapshot
foir design-tokens statusShow draft / published version status
OptionApplies toDescription
--channel <draft|published>getChannel to read. Default: draft.
--resolvedgetPrint the server-resolved view (typed arrays, references expanded) instead of the raw W3C document.
--publishapplyAlso publish after applying.

Examples

# Print the draft document as JSON foir design-tokens get # Print the resolved view (groups expanded into flat arrays) foir design-tokens get --resolved # Diff what the storefront is serving against the draft foir design-tokens get --channel published > published.json foir design-tokens get --channel draft > draft.json diff published.json draft.json # Apply a hand-authored or generated tokens document foir design-tokens apply ./tokens.json # Apply and publish in one step foir design-tokens apply ./tokens.json --publish # Promote the current draft to published foir design-tokens publish # Check whether draft and published are in sync foir design-tokens status

Tip: For projects that track tokens in foir.config.ts, use foir push --publish instead — it applies models, operations, and design tokens (and publishes them) in one step.

secrets

Manage vault secrets — opaque references your app code resolves to plaintext at runtime. Plaintext values never leave your machine; the CLI stores only encrypted blobs on the platform.

CommandDescription
foir secrets putStore a new secret and print its ref
foir secrets listList secret metadata (no plaintext)
foir secrets rotate <ref>Replace plaintext for an existing ref; returns a new ref
foir secrets delete <ref>Soft-delete a secret (recoverable until purged)
foir secrets restore <ref>Undo a soft-delete (only valid before the purge window passes)
foir secrets pushReconcile a foir.secrets.ts declaration file with the vault
foir secrets purgeDrop every soft-deleted secret past its TTL
OptionApplies toDescription
--label <label>putOptional human-readable label.
--app <name>put, listOwner: app name. Default: project-owned.
--file <path>put, rotateRead plaintext from file (binary-safe).
--value <plaintext>put, rotatePlaintext value (string only; prefer --file for binary).
--include-soft-deletedlistInclude soft-deleted entries.
--config <path>pushPath to foir.secrets.ts (default: auto-discover).
--plaintext <path>pushPath to local.foir.secrets.ts (default: auto-discover).
--rotatepushRotate plaintext for secrets that already exist.
--dry-runpushShow what would change without writing.
--confirmrotate, delete, purgeSkip confirmation prompt.

Examples

# Store a new secret from a file (binary-safe) foir secrets put --file ./stripe.key --label "Stripe API key" # Store a string value foir secrets put --value "sk_test_..." --label "Stripe (test)" # List project-owned secrets foir secrets list # Reconcile a declarative secrets file foir secrets push --config foir.secrets.ts --plaintext local.foir.secrets.ts # Rotate (returns a new ref — update your app code) foir secrets rotate vault:abc123 --file ./new-stripe.key # Soft-delete and undo foir secrets delete vault:abc123 --confirm foir secrets restore vault:abc123

api-keys

Manage API keys for programmatic access.

CommandDescription
foir api-keys listList API keys
foir api-keys createCreate an API key
foir api-keys rotate <id>Rotate an API key
foir api-keys revoke <id>Revoke an API key

Examples

# List all API keys foir api-keys list # Create a new API key foir api-keys create --data '{"name":"CI Pipeline"}' # Rotate an existing key (requires confirmation) foir api-keys rotate clx123 --confirm # Revoke a key foir api-keys revoke clx123 --confirm

auth-providers

Manage customer authentication providers (OAuth, SAML, etc.).

CommandDescription
foir auth-providers listList customer auth providers
foir auth-providers get <id>Get an auth provider
foir auth-providers createCreate an auth provider
foir auth-providers update <id>Update an auth provider
foir auth-providers delete <id>Delete an auth provider
OptionApplies toDescription
--enabled-onlylistShow only enabled providers.
--key <key>createUnique provider key. Required.
--name <name>create, updateDisplay name. Required for create.
--type <type>createProvider type: OAUTH2, TOKEN_SSO, SAML, OTP_VERIFY, OIDC, or EXTERNAL. Required.
-d, --data <json>create, updateProvider config as a JSON string.
--file <path>create, updateProvider config from a JSON file.
--enabled / --no-enabledcreate, updateEnable / disable the provider (--no-enabled on update).
--is-defaultcreate, updateSet as the default provider.
--priority <n>create, updateDisplay priority (higher = first).
--verify-external-customercreate, updateVerify the customer exists in an external system.
--capture-metadatacreate, updateCapture metadata from the provider during auth.
--confirmdeleteSkip confirmation prompt.

Examples

# List configured auth providers foir auth-providers list # Create a Google OAuth provider (key, name, and type are required) foir auth-providers create \ --key google \ --name "Google" \ --type OAUTH2 \ --enabled \ --file google-auth.json

notifications

Manage platform notifications.

CommandDescription
foir notifications listList notifications
foir notifications read <id>Mark a notification as read
foir notifications read-allMark all notifications as read

Examples

# List unread notifications foir notifications list --unread # Mark all as read foir notifications read-all

push-credentials

Manage per-project push credentials (APNs for iOS, FCM for Android) used to deliver push notifications. Alias: push-creds.

CommandDescription
foir push-credentials listList push credentials for the current project
foir push-credentials upload-iosUpload an APNs .p8 credential for iOS
foir push-credentials upload-androidUpload an FCM service-account JSON for Android
foir push-credentials delete <id>Delete a push credential by ID
OptionApplies toDescription
--p8 <path>upload-iosPath to the APNs .p8 private key. Required.
--bundle-id <id>upload-iosiOS app bundle identifier. Required.
--team-id <id>upload-iosApple Developer Team ID (10 chars). Required.
--key-id <id>upload-iosAPNs Key ID (10 chars). Required.
--productionupload-iosUse the production APNs endpoint (default: sandbox).
--service-account <path>upload-androidPath to the Firebase service-account JSON. Required.

Examples

# List configured push credentials foir push-credentials list # Upload an APNs key for iOS (sandbox by default) foir push-credentials upload-ios \ --p8 ./AuthKey_ABC123.p8 \ --bundle-id com.example.app \ --team-id A1B2C3D4E5 \ --key-id F6G7H8I9J0 # Upload the same key for production foir push-creds upload-ios --p8 ./AuthKey_ABC123.p8 --bundle-id com.example.app \ --team-id A1B2C3D4E5 --key-id F6G7H8I9J0 --production # Upload an FCM service-account for Android foir push-credentials upload-android --service-account ./firebase-service-account.json # Delete a credential foir push-credentials delete cred_abc123

notes

Manage notes attached to entities (records, models, etc.).

CommandDescription
foir notes listList notes for an entity
foir notes get <id>Get a note by ID
foir notes createCreate a note
foir notes resolve <id>Resolve a note
foir notes delete <id>Delete a note
OptionApplies toDescription
--entity-type <type>list, createEntity type (e.g. record, model). Required.
--entity-id <id>list, createEntity ID. Required.
--include-resolvedlistInclude resolved notes (default: unresolved only).
--first <n>listMax results. Default: 20.
--body <text>createNote body text. Required.
--parent-note-id <id>createReply to an existing note.
--resolution <text>resolveResolution message.
--confirmdeleteSkip confirmation prompt.

Examples

# List unresolved notes on a record foir notes list --entity-type record --entity-id clx123 # Create a note on a record foir notes create --entity-type record --entity-id clx123 --body "Needs review before publishing" # Resolve a note foir notes resolve clx_note_456 --resolution "Reviewed and approved" # Delete a note foir notes delete clx_note_456 --confirm

Apps

apps

Install and manage apps — pluggable units delivered by manifest URL.

CommandDescription
foir apps listList installed apps
foir apps get <name>Get an installed app by name
foir apps install <manifestUrl>Install an app from a manifest URL
foir apps update <name>Check for updates and apply if no rejected changes
foir apps uninstall <name>Uninstall (runs __uninstall first if declared)
foir apps trigger <appName> <operationKey>Trigger an app-owned operation
foir apps validate <manifestUrl>Dry-run validation of a manifest URL
foir apps devOpen a public tunnel to a local app dev server so foir admin can iframe it
OptionApplies toDescription
--source-map <json>installInline source mappings (ad-hoc, instead of foir.config.ts).
--dry-runupdateShow the diff without applying.
--forceuninstallSkip the middleware __uninstall call; remove platform state regardless.
-d, --data <json>triggerInput data as a JSON string.
-p, --port <port>devLocal port serving the app. Default: 8787 (wrangler default).
--host <host>devLocal host to forward to. Default: localhost.
-t, --tunnel <kind>devTunnel provider: cloudflared (default), ngrok, or none (use --url).
--url <url>devBYO tunnel URL; pairs with --tunnel none.
--pushdevRun foir push once after the tunnel comes up, with FOIR_APPS_HOST set.
--watchdevRe-run foir push on foir.config.* changes (implies --push).

Examples

# List installed apps foir apps list # Install with inline mappings (ad-hoc) foir apps install https://shopify.apps.foir.io/manifest.json \ --source-map '{"product":{"toModel":"product","naturalKey":"handle","fields":{"title":"title","handle":"handle"}}}' # Install via foir.config.ts (golden path) — declare apps.<name> and run: foir push # Check for updates with a diff foir apps update redirector --dry-run # Apply updates (only safe-auto changes apply automatically; rejected changes block) foir apps update redirector # Trigger a specific operation on an installed app foir apps trigger redirector deploy-worker --data '{"force":true}' # Force-uninstall (skip middleware __uninstall, remove platform state regardless) foir apps uninstall redirector --force # Validate a manifest before installing foir apps validate https://my-app.example.com/manifest.json # Tunnel a local app dev server (on :5173) and re-push on config changes foir apps dev --port 5173 --watch # Use a BYO tunnel URL instead of cloudflared foir apps dev --tunnel none --url https://my-tunnel.example.com --push

The CLI namespaces app-owned operation keys as <appName>/<operationKey> when storing them, but foir apps trigger accepts the bare key form too.

Scaffolding

create-config

Scaffold a new app or extension project — a Vite UI + Hono API monorepo wired up for Foir’s scoped-token verification.

npx @foir/cli create-config <name> [options]
OptionDescription
--type <type>Project type: custom-editor, workflow, or widget

Examples

# Custom editor placement (UI + middleware) npx @foir/cli create-config my-editor --type custom-editor # Pure backend operation (no UI) npx @foir/cli create-config my-summarizer --type workflow # Static iframe (no middleware) npx @foir/cli create-config color-picker --type widget

See Building an App and Building Operations for end-to-end walkthroughs.

init

Generate starter files for a project — a single model definition, or a tree of seed records for existing models. Run from inside a project that already has a foir.config.ts. To scaffold a brand-new project, use create-config.

CommandDescription
foir init model <key>Generate a starter model definition file
foir init recordsGenerate seed files for one or more existing models (interactive picker)
OptionApplies toDescription
-o, --output <dir>model, recordsOutput directory. Default: models for model, seed for records.
--tsmodel, recordsEmit TypeScript (.ts) instead of JSON.

Examples

# Create a starter model file at ./models/blog-post.ts foir init model blog-post --ts # Generate seed records into ./seed/ for models you pick interactively foir init records --ts

Config Management

configs

Manage platform configs (apps, webhooks). For the config-as-code workflow built around foir.config.ts, use push / pull / remove instead.

CommandDescription
foir configs listList configs
foir configs get <idOrKey>Get a config by ID or key
foir configs createCreate a new config
foir configs sync <id>Trigger a data sync for a config
OptionApplies toDescription
--type <type>listFilter by config type.
--enabledlistOnly enabled configs.
--first <n>listMax results. Default: 50.
-d, --data <json>createConfig data as a JSON string.
-f, --file <path>createRead config data from a file.

Examples

# List all configs foir configs list # Get a config by key foir configs get my-blog-config # Create a config foir configs create --file config.json # Trigger a sync foir configs sync clx123

pull

Export the current platform state of a config back into a local foir.config.ts file. Inverse of push — useful when an admin edited models or operations in the dashboard and you want those changes back in source control.

foir pull [options]
OptionDescription
--key <configKey>Config key to export (default: auto-discover from the current foir.config.ts)
--out <path>Output file (default: foir.config.ts next to the current one)
--forceOverwrite an existing file without prompting

Examples

# Pull the current project's config into ./foir.config.ts foir pull # Pull a named config and write to a different file foir pull --key my-blog-config --out ./configs/blog.config.ts # Overwrite without prompt (useful in CI / pre-commit hooks) foir pull --force

push

Push a local foir.config.ts file to the platform. This registers or updates a config and all its associated resources.

foir push [options]
OptionDescription
--config <path>Path to config file (default: auto-discovers foir.config.ts)
--forceOverwrite platform state on three-way-merge conflicts with admin-UI edits
--publishPromote ALL updated resources — including breaking model changes — to the published channel after the push. New resources and additive model updates auto-publish; breaking model changes and updated operations / auth providers / profile schema are otherwise left as drafts, and this flag releases them too.
--rebuildAccept lookup renames. A lookup with the same keyBy but a changed name rebuilds its projection rows (old rows dropped, new rows re-emitted). Without this flag the server rejects renames. Pure add/remove of lookups does not need it.
--rotate-keysRotate existing API keys and rewrite their values in .env
--dry-runPrint what the push would create / update / delete and exit without changing anything.
--allow-deleteSkip the interactive confirmation when the push deletes resources (for CI). Without this flag, deletions prompt on a TTY and abort when there’s no TTY.
--env <path>Path to .env file (default: .env)

Examples

# Push the config file in the current directory foir push # Push a specific config file foir push --config ./configs/blog.config.ts # Apply and publish in one step — including design tokens foir push --publish # Overwrite admin-UI edits when the three-way merge reports conflicts foir push --force # Preview the create / update / delete plan without changing anything foir push --dry-run # In CI: allow deletions to proceed without an interactive prompt foir push --allow-delete

remove

Remove a config and all its provisioned resources (models, operations, hooks, schedules).

foir remove <key> [options]
OptionDescription
--forceSkip the confirmation prompt

Examples

# Remove a config (with confirmation prompt) foir remove my-blog-config # Remove without confirmation foir remove my-blog-config --force

Data Portability

export

Export the project as a restorable Postgres database — typed tables, real foreign keys, your media, and your access rules as row-level security. See the Export to Postgres guide for the full walkthrough, and Your Data Is Portable for what the commitment is.

You must be the owner of the workspace: exporting reads the whole project at once.

CommandDescription
foir export postgresExport the project as a restorable Postgres bundle
OptionDescription
-o, --out <path>Write the archive to this path (default: foir-export-<date>.tar.gz).
--target <dsn>Apply the bundle directly into this Postgres. Requires psql. The connection string never leaves your machine — the bundle is applied from here, so your database password is never sent to Foir.
--postgisExport location fields as PostGIS geography(Point,4326) rather than JSON. Your database needs the postgis extension.
--include-rawAlso emit a full-fidelity JSON mirror of every record, drafts and versions and variants included.
--include-credentialsAlso include your customers’ password hashes (portable argon2id, so nobody resets). Prompts for your password to confirm, and records the export in your audit log.

Examples

# Write an archive you can restore later foir export postgres # …somewhere specific foir export postgres --out ./backups/myproject.tar.gz # Restore straight into a database you own (never leaves your machine) foir export postgres --target "postgresql://user:pass@localhost:5432/myproject" # With PostGIS geometry and the full-fidelity mirror foir export postgres --postgis --include-raw --target "$DATABASE_URL"

The command prints what it could not carry — a reference pointing at something already deleted, a value that wouldn’t fit its column — before it prints success. Nothing is dropped silently.

Embeddings and AI

embeddings

Manage vector embeddings for semantic search and similarity. Pairs with the AI & Search feature; the embedding pipeline runs on the platform but the CLI is how you trigger writes, deletes, and ad-hoc searches outside the admin app.

CommandDescription
foir embeddings writeWrite an embedding vector for a record
foir embeddings delete <recordId>Delete the embedding for a record
foir embeddings searchSearch by vector similarity
foir embeddings list <recordId>List embeddings stored for a record
foir embeddings stats [modelKey]Embedding statistics, optionally scoped to a model
foir embeddings similar <recordId>Find records similar to the given record
OptionApplies toDescription
-d, --data <json>write, searchInput payload as a JSON string. search requires --data.
--file <path>writeInput payload from a JSON file.
--confirmdeleteSkip confirmation prompt.
--model-key <key>similarLimit matches to a specific model.
--first <n>similarPage size.

The write payload is {"recordId":"…","vector":[…]} (with optional dimensions, provider, modelName). The search payload is {"queryVector":[…],"modelKey":"…","first":N}queryVector is required.

Examples

# Write an embedding from a file foir embeddings write --file embeddings.json # Semantic search by vector similarity foir embeddings search --data '{"queryVector":[0.12,0.04,-0.31],"modelKey":"article","first":10}' # Find similar records, scoped to a model foir embeddings similar clx123 --model-key article --first 5 # Embedding statistics for a single model foir embeddings stats article --json # Project-wide stats (no model key) foir embeddings stats --json # Delete the embedding attached to a record foir embeddings delete clx123 --confirm
Last updated on