sinatra.dev
v0.3.1
Published
Hand coding tasks to Sinatra from your terminal.
Maintainers
Readme
sinatra.dev CLI
Hand coding tasks to Sinatra from your terminal, follow the conversation, and get a GitHub pull request back when the work calls for one.
Install
Requires Node 22 or newer.
npm i -g sinatra.dev
sinatra --versionLog in
sinatra loginsinatra login opens your browser on a Sinatra page that asks you to approve the Sinatra CLI. Sign
in to Sinatra there if you aren't already, click Approve, and the CLI is logged in: there's no
token to create or copy. If you belong to more than one workspace, pick the default one. The CLI
stops waiting after 5 minutes.
The sign-in is saved in ~/.config/sinatra/config.json ($XDG_CONFIG_HOME/sinatra if set,
%APPDATA%\sinatra on Windows), readable only by you. Its access token lasts an hour, and the CLI
renews it as it goes. It stays signed in for up to 90 days, or until it goes 30 days unused; after
that, or if you disconnect Sinatra CLI under Connected apps on the dashboard's CLI & API
page (https://app.sinatra.dev/tokens), the CLI asks you to run sinatra login again.
If the browser doesn't open, sinatra login --no-browser prints the URL to open instead. The
browser must run on the same computer as the CLI, because Sinatra sends it back to a port the CLI
listens on there. Logged in to another machine over SSH, or with no browser at all, use a personal
access token instead:
sinatra login --tokenCreate a token on the same CLI & API page and paste it in; it isn't echoed.
In a script, pipe the token in and name the default workspace with -w. Piped input always reads a
token, without --token:
sinatra login -w <workspace-id> < token-fileWithout -w, piped input isn't asked for a workspace: set one later with sinatra workspace <id>.
A -w that isn't one of your workspaces is an error, and nothing is saved.
Commands
sinatra "fix the flaky retry test" # start a task and follow it
sinatra "explain this" -f notes.md -f err.log # attach text files (80KB total)
sinatra reply <task-id> "also update the docs" # follow up, then follow it
sinatra show <task-id> # a task and its conversation
sinatra tasks # recent tasks in your workspace
sinatra stop <task-id> # stop a running turn
sinatra tickets -q "flaky login" # open Linear and GitHub issues you could delegate
sinatra delegate ENG-123 # hand Sinatra a Linear or GitHub issue (owner/name#12, or its URL) as you
sinatra whoami # who you're logged in as, and your workspaces
sinatra workspace [<id>] # list workspaces, or set the default
sinatra logout # end the sign-in (or revoke the token) and forget it| Command | Options |
| --- | --- |
| sinatra login | --no-browser: print the sign-in URL instead of opening a browser; --token: paste a personal access token instead; --api-url <url>: another Sinatra API (https; plain http only for localhost); -w, --workspace <id>: the default workspace |
| sinatra [start] "<what to do>" | -r, --repo <owner/name>, -f, --file <path> (repeatable), -t, --title <title>, -w, --workspace <id>, --timeout <minutes>, --no-wait, --json (with --no-wait) |
| sinatra reply <task-id> "<message>" | -f, --file <path> (repeatable), -w, --timeout <minutes>, --no-wait, --json (with --no-wait) |
| sinatra show <task-id> | -w, --json |
| sinatra tasks | --status <status>, -n, --limit <n> (1 to 100, default 20), -w, --json |
| sinatra stop <task-id> | -w |
| sinatra tickets | -q, --query <text>, -r, --repo <owner/name> (searched first), -w, --json |
| sinatra delegate <ticket> | -w |
| sinatra whoami | --json |
| sinatra workspace [<id>] | none |
| sinatra logout | none |
| sinatra --version, -v / sinatra --help, -h | none |
An option a command doesn't use is an error, not silently ignored.
- Repository: inside a git checkout, the task runs on its GitHub repository: the
originremote, thenupstream; another GitHub remote counts only when neither is on GitHub. SSH host aliases from~/.ssh/config(likegit@github-work:owner/repo.git) count when they point at github.com. Iforigin's repository isn't connected to your workspace, the CLI says so and triesupstream's (so a fork falls through to the repository it forks); when none is connected, Sinatra's agent picks one. The CLI prints which remote it used.-r owner/namepicks a repository explicitly, and is never second-guessed. - Attachments:
-fattaches text files to a new task or a reply, up to 80KB together. Binary files are refused. - Following: after
startorreply, the CLI prints what Sinatra posts until the turn is done: Sinatra replied, or the task finished, failed, was cancelled, or paused. If the task is queued because your workspace is running as many tasks at a time as its plan allows, the CLI says so. It stops waiting after--timeoutminutes (30 by default); the task keeps going. Ctrl-C stops waiting too. After areplyto a task that had already stopped, if Sinatra hasn't picked the message up within two minutes, the CLI says so (exit 3) instead of reporting the previous turn's result. - Prompts that start with
-: put them after--:sinatra -- "-v is broken". A title that starts with-takes the=form:--title="-x title". - Workspace: commands use the default workspace from login.
sinatra workspace <id>changes it without logging in again;-w <id>overrides it for one command. - JSON:
--jsonprints the API's objects and nothing else, for scripts:whoami,tasks,show, andstartorreplywith--no-wait. - Prompts vs commands: a prompt that starts with a command word still starts a task, unless it
has exactly that command's shape.
sinatra start "..."always starts one. - Logout:
sinatra logoutends the browser sign-in on Sinatra (or revokes the token you pasted), then deletes the local file. If Sinatra can't be reached, the file is still deleted and the CLI warns that the sign-in or token may still be active: disconnect or revoke it on the CLI & API page. - Retries: every request that changes something carries an idempotency key, so a retry after a dropped connection never starts a second task or sends a message twice.
Exit codes
| Code | Meaning |
| --- | --- |
| 0 | Done: the turn finished, or the command succeeded |
| 1 | Error: bad usage, not logged in, or Sinatra refused the request |
| 2 | The task failed, was cancelled, or is paused (billing or access) |
| 3 | Still working when the CLI stopped waiting (--timeout), or your reply wasn't picked up yet |
