> ## Documentation Index
> Fetch the complete documentation index at: https://rive-android-hoist-worker.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# Command Reference

> Every Rive CLI command, flag, and exit code.

```bash theme={null}
rive COMMAND
```

Run `rive --help` for this list in your terminal, and `rive --version` to print the
installed version.

## Commands

| Command | Does |
| - | - |
| `rive create` | Scaffold a Rive project locally. It creates the following: `rive.yaml`, `scene.rml`, `AGENTS.md`, `.gitignore` |
| `rive <project-dir>` | Open the preview window and rebuild as you edit. The directory defaults to `.` |
| `rive login` | Sign in with your Rive account |
| `rive logout` | Sign out |
| `rive whoami` | Show who you are signed in as |
| `rive docs` | The CLI's own authoring documentation |
| `rive samples` | Clone a runnable example project to your machine |
| `rive schema` | Look up types |
| `rive inspect` | Print the resolved scene |
| `rive push` | Build the project and upload it to a Rive file in your account. Needs `rive login` |
| `rive pull` | Overwrite the local project from the Rive file it is linked to. Needs `rive login` |
| `rive doctor` | Check the environment: version, auth, ports, project |
| `rive lsp` | Language server over stdio, for editor integrations |
| `rive update` | Install the latest published CLI |
| `rive switch` | Pick a CLI version, or select one by name |
| `rive uninstall` | Remove a cached CLI version |
| `rive analytics` | Show or set usage analytics (`on` \| `off`) |

<Note>
  `update`, `switch` and `uninstall` are only supported for the installer build under
  `~/.rive/bin`. If installing the CLI via Homebrew, use the `brew` methods to manage CLI versioning and updates.
</Note>

## Project flags

These apply to `rive <project-dir>`.

### Build modes

Mutually exclusive, so pick one. `--screenshot` under [Capture](#capture) counts
as one of them. With none of them, the CLI opens the preview window and rebuilds as
you edit.

| Flag | Does |
| - | - |
| `--verify` | Check the project without writing a `.riv`. Exit 1 on errors |
| `--once` | Write an unsigned `.riv`. Exit 1 on errors |
| `--publish` | Write a signed `.riv`. Needs `rive login`, and may watermark the output, see the note below. Exit 1 on errors |
| `--test` | Run `Tests` scripts. Exit 6 on failures |

<Note>
  `--publish` may add a watermark to the graphic. A clean `.riv` needs two things: the
  project bound to a file in your Rive account, and that file in a workspace on the
  [Cadet plan or higher](https://rive.app/pricing). Binding is done by
  [`rive push`](/cli/reference/project-config#pushing-to-a-rive-file), which records
  `push.fileId` in `rive.yaml`. The watermark applies whether or not the project has
  scripts.
</Note>

### Modifiers

These attach to whichever mode you chose.

| Flag | Does |
| - | - |
| `--init` | Write `rive.yaml` if missing, then continue |
| `--rev=<path>` | Also write an editor `.rev`. Needs `rive login`. Combines with `--once` or `--publish`, and on its own does an `--once` build too. Refused with `--verify`, `--test` and `--screenshot` |

### Capture

| Flag | Does |
| - | - |
| `--screenshot[=<path>]` | Build, render one frame without a window, write a PNG. Defaults to `build/<name>.png` |
| `--viewport=<WxH>` | The size the scene is laid out at: the capture size with `--screenshot`, and the window size when watching. Defaults to the artboard's own size |
| `--bench=<frames>` | Build, time that many frames without a window, report advance and render statistics plus WASM memory growth |

`--bench` runs instead of `--screenshot`, not alongside it. Passing both times the
frames and writes no PNG, without saying so. It is a build mode in its own right, so
it does not combine with `--verify`, `--once`, `--publish` or `--test`. It renders at
the artboard's own size and ignores `--viewport`, and it runs 300 warm-up frames
before the ones it times.

### Driving the scene

| Flag | Does |
| - | - |
| `--data=<path=value>` | Set one view model property before the scene runs. Repeat the flag for several properties |
| `--pointer=<kind@x,y>` | Simulate one pointer event at artboard coordinates. Repeatable |
| `--advance=<N\|Ns\|Nms>` | Step the scene forward. Repeatable, and runs in order with the other interactions |
| `--key=<key[:phase][+mods]>` | Simulate a keystroke. Repeatable, and runs in order with the other interactions |
| `--data-dump[=<path>]` | Write the bound view model values, globals and nested artboards as JSON. Defaults to `build/<name>.data.json`; `-` or `stdout` writes to standard output |
| `--data-dump-filter=<paths>` | Keep only these property paths, comma separated. Globs allowed, as in `battery/*,score` |
| `--data-dump-every=<N\|Ns\|Nms>` | Sample every N frames rather than once at the end, as JSON Lines |
| `--artboard=<name>` | Artboard to show on launch. An unknown name falls back to the first artboard without warning |
| `--fit=<mode>` | How the artboard maps into the view: `fill`, `contain`, `cover`, `fit-width`, `fit-height`, `none`, `scale-down`, or `layout` (the default) |

Interactions run in the order you write them, and `--pointer` and `--advance` need
`--screenshot`.

#### Advancing time

`--advance` steps the scene where it sits among the other interactions. A bare number
is whole frames at 60fps; `1s` or `250ms` is animation time, stepped in 1/60s frames
with one shorter frame for any remainder. The time forms take a decimal point, so
`1.5s` is 90 frames.

```bash theme={null}
rive myproject --screenshot=out.png --advance=60      # 60 frames
rive myproject --screenshot=out.png --advance=1s      # the same, written as time
rive myproject --screenshot=out.png --advance=250ms
```

Position it for what you need:

| Where | Does |
| - | - |
| Before a gesture | Plays an intro before the interaction lands |
| Between two gestures | Lets one action's transition finish before the next starts |
| After the last gesture | Settles the scene before the capture |

```bash theme={null}
rive myproject --screenshot=out.png \
  --advance=1s \
  --pointer=click@120,60 \
  --advance=20
```

A sign, whitespace, trailing text, a decimal point on a bare frame count, or a value
above a 32-bit unsigned integer is rejected with exit code 2.

<Note>
  `--advance` replaces `--frame`. A bare `--advance=N` means what `--frame=N` meant, so
  `--frame=20` becomes `--advance=20`. Passing `--frame` is an error naming `--advance`.

  `--bench` takes its own frame count and does not combine with `--advance`, `--pointer`,
  `--gamepad`, `--semantics` or `--semantic-action`.
</Note>

#### Setting data

`--data` takes a property path and a value. The path starts at the view model
instance bound to the artboard, and every segment is a property name, so a flat view
model takes the bare property and a nested one takes a path:

```bash theme={null}
rive myproject --screenshot=out.png --data=level=100
rive myproject --screenshot=out.png --data=battery/level=100
```

Each `--data` sets one property. Repeat the flag to set several:

```bash theme={null}
rive myproject --screenshot=out.png \
  --data=settings/speed=42 \
  --data=settings/scale=9
```

<Note>
  A path that matches no property logs `data: no property at "<path>"` and is dropped.
  The build still succeeds, and the scene renders with that property's authored value.
  Under `--quiet` you see nothing at all, so confirm your values landed rather than
  assuming they did.
</Note>

#### Reading data back

`--data` sets values going in; `--data-dump` reads them back out. It builds, runs
headless, and writes the bound view model values as JSON, so a test can assert on
what the scene computed:

```bash theme={null}
rive myproject --data-dump=- --advance=60
```

`--data-dump-every` turns that into a time series instead of a single reading: a
header, a frame-0 baseline, then only what changed on each sample. It takes a whole
number of frames at 60fps, and counts the frames gestures advance internally.

#### Simulating a keystroke

`--key` sends a key through the same dispatch path a real one takes. The phase is
`down`, `repeat` or `up`, and defaults to `press`, which is a down then an up.
Modifiers attach with `+`:

```bash theme={null}
rive myproject --screenshot=out.png --key=right
rive myproject --screenshot=out.png --key=a:down
rive myproject --screenshot=out.png --key=tab:down+shift
```

Key names are the same ones the markup uses, so `right`, `escape`, `f1` and `kpEnter`
all resolve.

<Note>
  Keys only reach whatever holds Rive focus. With nothing focused, the CLI says so and
  names the fix: the file needs a `FocusData` on the listener's target, and something to
  focus it.
</Note>

#### Simulating a pointer

`--pointer` takes a kind and a position. `down`, `up`, `move`, `exit`, and `click` each
take a single point. `click` expands to a move, a press and a release with a frame between
each, because a state machine only sees a gesture when it next runs:

```bash theme={null}
rive myproject --screenshot=out.png --pointer=click@120,60
```

`--pointer` only checks the shape of the value. A kind that is not `down`, `up`,
`move`, `exit`, `click` or `drag` parses fine, then fails at delivery with
`pointer: unknown gesture` and exits with `1`.

`drag` is a fifth kind, and the only one with a different shape:
`drag@x1,y1>x2,y2[:steps]`. It moves to the first point, presses, emits `steps` moves
along the line to the second point, then releases. `steps` defaults to 8. Every event
gets its own frame, so a drag runs for `steps + 3` frames: a higher count is a finer
and slower sweep, a lower one a flick. Scroll physics reads the velocity that implies,
so the count changes how far a scroll throws.

```bash theme={null}
rive myproject --screenshot=out.png --pointer='drag@200,300>200,80:12'
```

<Note>
  Quote the `drag` value so the shell does not read `>` as a redirection.
</Note>

### Serving

| Flag | Does |
| - | - |
| `--serve[=port]` | Also push builds to connected players. Defaults to port `9640` |
| `--headless-serve` | Serve with no local window. Takes its port from `--serve=<port>` |

### Other

| Flag | Does |
| - | - |
| `--quiet` | No terminal log at all, compiler errors included. Read the exit code, `--format=json`, or `logs.problems` instead |
| `--optimize` | Compile scripts at Luau O2 instead of O1. The scripts run faster and the bytecode is harder to debug |
| `--immediate` | Render on the main thread |
| `--format=json` or `--format=human` | `human` is the default terminal log. `json` needs `--once`, `--verify`, `--publish` or `--test`, and prints one JSON report object on stdout. `--json` is an alias for `--format=json` |

## Preview window commands

Type these in the terminal while the preview window is open.

| Key | Does |
| - | - |
| `s` or `screenshot [path]` | Write a PNG of the window |
| `p` or `pause` | Toggle playback |
| `a` or `artboard [name]` | Switch the shown artboard |
| `f` or `fit [mode]` | Switch how the artboard maps into the window. Bare `f` lists the modes |
| `z` or `size` | Resize the window to the artboard, and follow it again after a manual drag |
| `rev [path]` | Write an editor `.rev`. Needs `rive login` |
| `?` or `help` | List commands |

## Per-command flags

### `create`

```bash theme={null}
rive create                          # prompt for a name, then write that directory
rive create <dir>                    # write the project in <dir> (`.` is the cwd)
rive create [dir] --from-rev=<file.rev>
```

`--from-rev` converts an editor `.rev` into a project: `scene.rml` plus its scripts
and assets as files. Without a `<dir>`, the `.rev`'s own name is used. The directory
must be empty or new.

`--from-remote-file` does the same conversion on a file downloaded from your Rive
account. Without a file ID, the CLI lists your projects and files to pick from. `rive.yaml`
records the link, so `rive push` updates that source file and `rive pull` brings any remote changes in.
This requires a logged in session with `rive login`.

```bash theme={null}
rive create myproject --from-remote-file        # pick from a list
rive create myproject --from-remote-file=512    # or name the file id
```

### `schema`

```bash theme={null}
rive schema <Type>          # properties of a type, inherited included
rive schema --search <text> # find a type or property by name, then pick one
```

| Flag | Does |
| - | - |
| `--list` | Pick a type to describe. Where no picker can draw, prints every type name |
| `--animatable` | Only properties that can be keyed |
| `--bindable` | Only properties that can be data bound |
| `--all` | Include editor-only properties |
| `--json` | JSON output: the type as one object, or the `--list` / `--search` results as an array |

### `docs`

```bash theme={null}
rive docs                 # the documentation index
rive docs <topic>         # one topic, for example `layout` or `luau/protocols`
```

| Flag | Does |
| - | - |
| `--list` | Pick a topic to read |
| `--search <text>` | Lines matching text across every topic |
| `--path` | Print the docs directory on disk |

### `samples`

```bash theme={null}
rive samples          # pick one and copy it into a new directory
rive samples --path   # print the samples directory on disk
```

### `inspect`

```bash theme={null}
rive inspect [dir]    # resolved scene as JSON. The directory defaults to `.`
```

Exits `1` when `problems` contains an error, and `1` with a message on stderr when
the directory has no `rive.yaml`.

| Flag | Does |
| - | - |
| `--json` | JSON output (the default) |
| `--summary` | Problems plus object counts per type, per artboard and for the other roots. Not the tree |
| `--all` | Include editor-only properties |
| `--artboard=<name>` | One artboard only. An unknown name gives an empty `artboards` list and still exits `0` |

### `push`

```bash theme={null}
rive push [dir]       # build the project and send it to the bound Rive file
```

This uploads the project to your Rive account, replacing the bound file's contents and adding an
entry to its revision history. It is the same artifact `--rev` would export.

| Flag | Does |
| - | - |
| `--project=<id>` | Project for the first push. Falls back to `push.projectId` in `rive.yaml`; a single project is picked automatically, and several open a picker |
| `--list` | List your projects with their ids, then exit |
| `--name=<label>` | Revision history label. Defaults to `rive-cli push` |
| `--optimize` | Compile scripts at O2 |
| `--quiet` | Suppress build logs |

See [Pushing to a Rive file](/cli/reference/project-config#pushing-to-a-rive-file).

### `pull`

```bash theme={null}
rive pull [dir]       # overwrite the project from its linked Rive file
```

Downloads the Rive file the project is linked to and writes it over the project: the
scene markup, and every script, shader and asset as a file. Files whose bytes already
match are left alone, and build inputs missing from the remote file are reported
rather than deleted.

`rive.yaml` takes the remote file's main artboard and build settings and keeps every
other line. `AGENTS.md`, `CLAUDE.md` and anything else you added are untouched.

| Flag | Does |
| - | - |
| `--yes` | Skip the confirmation. Required in CI, and anywhere there is no terminal to ask on |
| `--quiet` | Only report what changed |

This command names the file and the project and asks before it runs, defaulting to no:

```text theme={null}
Pulling file 2603061 overwrites /path/to/myproject's scene, scripts and assets with the remote file's.
Overwrite local changes? [y/N]:
```

<Warning>
  At this time, pull replaces your local project's scene, scripts and assets with the remote file's.
</Warning>

### `doctor`

```bash theme={null}
rive doctor [project-dir]
```

| Flag | Does |
| - | - |
| `--format=json` | Machine-readable report on stdout |

`doctor` prints five checks (`version`, `update`, `auth`, `live-link` and `project`),
each `ok`, `warn` or `fail`. It exits `0` when everything is `ok` or `warn`, and `1`
when a check fails.

## Signing in

| What you run | Session needed |
| - | - |
| `--publish`, `--rev`, `rive push`, `rive pull`, `create --from-remote-file` | Yes, with `rive login` |
| Preview window, `--once`, `--verify`, `--test`, `--screenshot`, `--serve`, `--headless-serve` | No, and these work offline |
| `create`, `docs`, `samples`, `schema`, `inspect` | No |
| `update`, `whoami`, `doctor` | No account, but they reach the network. `whoami` exits `3` when you are not signed in and `7` when it cannot reach Rive; `doctor` reports a missing session as a warning and still exits `0`, but exits `1` when a check fails |

Credentials live outside the project: `~/.config/rive/app.rive.cli/` on macOS and
Linux, honouring `XDG_CONFIG_HOME`, and Windows Credential Manager on Windows.

<Note>
  A gated mode checks the session live, so `--publish` and `--rev` fail on a dropped
  connection even with valid stored credentials.
</Note>

## Exit codes

| Code | Meaning |
| - | - |
| `0` | OK |
| `1` | Build errors, or any failure without a more specific code |
| `2` | A flag the CLI parsed and rejected: a bad `--pointer`, `--data`, `--advance` or `--viewport` value; `--frame`, which is gone; `--format` given anything but `json` or `human`; `--format=json` without a build mode; two build modes at once; `--rev` with a mode that writes nothing; an interaction with no `--screenshot`; or `rive` with no arguments outside a project |
| `3` | Not logged in, or the session was rejected |
| `6` | Test cases failed. The build itself was fine |
| `7` | A service could not be reached, so it is safe to retry |

<Note>
  Any argument without a leading `--` is read as the project directory. Passing more
  than one is not an error: the CLI builds the one furthest right and says nothing about
  the others, so a stray word changes what gets built.
</Note>

## JSON output

`--format=json` on `--once`, `--verify`, `--publish` or `--test` prints one JSON
object on stdout. `data` differs per mode. `--verify` and `--once` carry the build:

```json theme={null}
{"success": true, "command": "build", "data": {"riv": "./build/myproject.riv", "bytes": 140, "buildMs": 2.0, "problems": []}, "errors": [], "warnings": []}
```

`--test` carries the run:

```json theme={null}
{"success": false, "command": "test", "data": {"passed": 5, "failed": 1, "noTestsFound": false, "failures": [{"test": "clamp > intentional failure", "line": 29, "message": "5 is not equal to 10"}]}, "errors": ["clamp > intentional failure: 5 is not equal to 10"], "warnings": []}
```

`command` is the mode, not the flag: `"build"` for `--once`, `"verify"` for
`--verify`, `"publish"` for `--publish`, `"test"` for `--test`. Each entry in
`data.problems` is `{severity, kind, code, script, line, column, message}`, with
`severity` one of `error`, `warning` or `hint`. `errors` repeats them as
`script:line message` strings. `data.riv` is `null` on `--verify`
and on any failed build. Logs stay on stderr, so stdout carries nothing else.

## Environment variables

| Variable | Overrides |
| - | - |
| `RIVE_API_BASE` | The API host. A custom host also gets its own stored login |
| `RIVE_NO_TUI` | Any value except `0` disables interactive pickers |
| `TERM` | Unset, empty, or `dumb` disables interactive pickers |
| `NO_COLOR` | Draws pickers without color |
| `RIVE_HOME` | The CLI's install and state root. Defaults to `~/.rive` |
| `XDG_CONFIG_HOME` | Relocates the credential directory on macOS and Linux |
| `RIVE_DOCS_DIR` | The directory `rive docs` reads |
| `RIVE_SAMPLES_DIR` | The directory `rive samples` copies from |
| `RIVE_ANALYTICS` | Forces analytics consent: `on`/`1`/`true`/`yes`, or `off`/`0`/`false`/`no` |

<Note>
  Interactive pickers draw on stderr, so redirecting stdout alone does not disable
  them. Where no picker can draw (`TERM=dumb`, `RIVE_NO_TUI=1`, or stdin not a
  terminal as in CI), the CLI falls back to printing the list instead.
</Note>
