- Quickstarts
- Quickstart: command line
Quickstarts
Quickstart: command line
Install the published greatwait command and reach an observed callback one command at a time.
The same nine calls as the curl and JavaScript quickstarts, one command at a time, with nothing to write. Every command here is one you would use again on your own work.
Read Before you begin first: it lists the three prerequisites this cannot get for you.
Install it
npm install --global @greatwait/cli@0.1.0-alpha.4
greatwait --help
This page describes @greatwait/cli 0.1.0-alpha.4. The command reference
lists every command that version has.
Sign in
greatwait login --api-url https://api.greatwait.dev
That opens your browser. On a machine with none — a remote shell, a
container — --no-browser prints the address to open yourself, and the
command waits on a port it has already bound on this machine.
For automation, use a scoped API credential created in the dashboard. It is never taken as a command-line argument, because an argument is visible to every other process on the machine and is written to your shell history:
printf %s "$GREATWAIT_API_KEY" | greatwait login --api-key --api-url https://api.greatwait.dev
Credentials are stored per API origin, readable by you and nobody else.
Walk it
greatwait journey prints this sequence with the command for each step.
greatwait doctor
greatwait whoami
greatwait destinations create --url <your receiver>
greatwait schedules create --endpoint <destination> --in 30s
greatwait schedules create --endpoint <destination> --in 30s --idempotency-key <the same key>
greatwait schedules read <schedule>
greatwait occurrences wait <schedule> <occurrence>
greatwait attempts list <schedule> <occurrence>
greatwait destinations disable <destination>
What each step does
1. Check which service and environment you reached
greatwait doctor
Confirms the origin you are pointed at is a Greatwait API and says which environment it serves. It needs no credential, so it separates ‘wrong URL’ from ‘wrong key’.
If it does not work.
| When | Next move |
|---|---|
unexpected-answer | Something answered, but not this service. Check GREATWAIT_API_URL — a 404 here comes from a proxy in front of the API rather than from the API, so it carries no problem document to read. |
no-response | The origin did not answer. Check the hostname and that you can reach it from this network before going further. |
2. Check the credential
greatwait whoami
Proves the credential works and is bound to the project you think it is, before you create anything with it. A credential names exactly one project, and this is the cheapest call that says so.
If it does not work.
| When | Next move |
|---|---|
authentication_required | No credential reached the service. Export GREATWAIT_API_KEY in this shell and try again. |
credential_revoked | The credential was revoked. Create a new one in the dashboard; a revoked credential never comes back. |
credential_expired | The credential expired. Rotate it in the dashboard and export the new secret. |
scope_missing | The credential is missing schedules:read. Create one with the scopes this journey needs rather than widening this one. |
3. Create the destination
greatwait destinations create --url <your receiver>
Registers the address every occurrence of this schedule is delivered to, and mints the per-endpoint signing key your receiver verifies callbacks with.
If it does not work.
| When | Next move |
|---|---|
invalid_request | The URL was refused. It must be HTTPS on port 443, carry no credentials or fragment, and resolve to a public address — a localhost or private-range host cannot be reached from the service. |
plan_limit_reached | This project is at its destination ceiling. Disable a destination you no longer deliver to; disabled ones still count, because they stay readable for audit. |
state_conflict | An active destination already delivers to this address in this project — usually one a previous run of this journey created. Reuse that destination, disable it first, or give the new one a name of its own. |
4. Create the one-shot
greatwait schedules create --endpoint <destination> --in 30s
Creates the one-shot. The delay is converted to an absolute instant when the request is accepted, so the schedule reads back the same afterwards however it was expressed.
If it does not work.
| When | Next move |
|---|---|
not_found | The endpoint identifier is not one this credential’s project can deliver to — it belongs to another project, or there is no such endpoint. Create a destination in this project, or check the identifier. |
state_conflict | The endpoint is disabled. Enable it with endpoints.enable and the schedule is accepted as sent, or point the schedule at another destination. |
idempotency_key_reused | The same idempotency key was used for a different request. Use a new key, or send the byte-identical body the key was first used with. |
invalid_request | Give exactly one of at, delaySeconds, everySeconds and cron, and make sure the endpoint identifier is one this credential’s project owns. |
plan_limit_reached | This organization is at a plan ceiling — live schedules, distinct partition keys, or payload size. Nothing was created; reduce the payload or archive a schedule and retry. |
service_unavailable | The service could not accept the schedule right now. This is safe to retry with the same idempotency key, which is what the key is for. |
5. Retry it safely
greatwait schedules create --endpoint <destination> --in 30s --idempotency-key <the same key>
Repeats the previous call byte for byte, with the same key. This is the retry a network failure would have made for you, and it is the reason a create is safe to retry at all.
If it does not work.
| When | Next move |
|---|---|
idempotency_key_reused | The body differed from the first call. A replay must be byte-identical; a changed body with a used key is a conflict rather than a second write. |
6. Read the schedule back
greatwait schedules read <schedule>
Reads the schedule back from the partition that owns it, which is also where the version you need for a conditional write comes from.
If it does not work.
| When | Next move |
|---|---|
not_found | A schedule in another organization, project or environment answers not_found rather than a refusal. Check that this credential belongs to the project that created it. |
7. Wait for the occurrence to settle
greatwait occurrences wait <schedule> <occurrence>
Waits for the occurrence to settle. Delivery is at-least-once and a failing attempt is retried, so the state moves through due and dispatching before it settles.
Bounded wait. Poll until the occurrence reaches a terminal state, or until the deadline passes. It polls every 5 seconds and gives up after
If it does not work.
| When | Next move |
|---|---|
not-settled | The occurrence never settled inside the deadline. It is not lost: read it again later, and read its attempts to see how far delivery got. |
8. Read the delivery attempt
greatwait attempts list <schedule> <occurrence>
Reads the immutable delivery history. This is the point the journey exists for — the customer-readable outcome of a real call to their own address.
If it does not work.
| When | Next move |
|---|---|
attempt-failed | The attempt failed. Read diagnostic and remediation: they name the classified cause and the next action, and failureSnippet carries what your receiver said. |
receiver-unreachable | Nothing reached your receiver. Confirm the URL answers a POST from the public internet, and that it is not behind an allowlist Greatwait is not on. |
9. Clean up
greatwait destinations disable <destination>
Stops delivery to the destination you registered for this walkthrough. Disabling is deliberate rather than final: it leaves the history intact rather than deleting evidence of what happened, and endpoints.enable turns the destination back on if you want it again.
If it does not work.
| When | Next move |
|---|---|
not_found | Already gone, or never in this project. Nothing to clean up. |
Output and exit codes
--json is a versioned machine shape rather than a rendering of the
human text, and it goes to standard output whether the command worked or
not — the exit status is what says which. The sentence telling a person
what to do next goes to standard error.
| Code | Meaning |
|---|---|
| 0 | it worked |
| 1 | a defect in the command itself |
| 2 | the command line was wrong |
| 3 | no usable credential — greatwait login |
| 4 | the credential may not do this |
| 5 | the request was refused on its merits |
| 6 | the service could not answer now; the identical request may work later |
| 7 | a deadline passed |
| 130 | interrupted |
Clean up
greatwait destinations disable <destination>
greatwait logout
Disabling a destination stops delivery to it and keeps the attempts you
read above. It shows what it will change and asks before doing it; in a
script, where there is nobody to ask, add --yes or it refuses. logout
revokes the grant where it can and removes the local material either way.