CLI
The commercehook CLI brings the inspector to your terminal, and one
thing the dashboard cannot do: listen forwards deliveries into the
handler running on your machine, which removes the tunnel from the
webhook development loop.
Install
npx commercehook --help
npx runs it without installing. For daily use:
npm install -g commercehook
No Node on the machine? Homebrew installs a standalone binary:
brew install commercehook/tap/commercehook
Standalone binaries for Linux and Windows are attached to each
release
with checksums. commercehook upgrade tells you how to update
whichever way you installed.
The npm package has no dependencies and is a few kilobytes. The CLI
checks npm once a day for a newer release and mentions it on stderr;
set CH_NO_UPDATE_NOTIFIER=1 to turn that off.
Sign in
commercehook login
Your browser opens on the same consent screen any connected app gets. Approve it and the terminal is signed in; the CLI appears under Connected apps in dashboard settings, where it can be disconnected like anything else. Sign-ins refresh themselves for 30 days of use, then ask again.
On a machine with no browser, two options:
commercehook login --with-api-key # prompts for a chk_ key, verifies it, stores it
or set CH_API_KEY in the environment and store nothing, which is what
CI wants. commercehook logout signs out properly: the grant is revoked
server-side, not just forgotten locally.
Stream deliveries to your machine
commercehook listen my-endpoint --forward-to http://localhost:3000/webhooks
Register your CommerceHook URL with the platform once, then develop
against the handler on your laptop. Each delivery is forwarded with its
original method, platform headers and raw body; headers that described
the original hop (host, cf-*, and friends) are stripped, and so are
credential headers (Authorization, Cookie), which CommerceHook
stores redacted and therefore has nothing real to forward. The event
id rides in x-commercehook-replay, and x-commercehook-forwarded: 1
marks live forwarding so a handler can tell it from a manual replay.
Every delivery is also captured and inspectable as normal, which is the
part a tunnel never gave anybody.
✓ 200 store/order/created 6ms d5d78de1-4e17-4ddd-8be5-35ea4e3b8b67
! 500 store/cart/created 12ms 0a1b2c3d-...
A non-2xx from your handler is reported and the stream continues: your handler erroring mid-edit is the loop doing its job.
Three things worth knowing, stated plainly:
- At-least-once. The cursor advances only after a forward attempt,
so a crash re-forwards anything unacknowledged. Deduplicate by the
x-commercehook-replayid if your handler cares, as with every webhook system. - Live, with a polling net. From 0.4.0,
listenrides the same stream the dashboard does, so deliveries forward the moment they arrive. If the socket drops (or your Node predates a built-in WebSocket), the CLI says so on stderr and polls every few seconds until the stream returns. Nothing is missed either way; only the lag changes. Still a dev loop, not a production transport. - Start with history if you want it.
--since 15mrewinds the stream;--replay-last 5forwards the most recent five first, oldest first. Ctrl-C prints what was forwarded and where to resume.
The commands
commercehook endpoints # list, with URL, event count, last delivery
commercehook endpoints create staging # new endpoint, prints the URL to register
commercehook endpoints rename staging stage2
commercehook endpoints delete stage2 # asks first; --yes for scripts
commercehook events my-endpoint # newest first
commercehook events my-endpoint --search order/created
commercehook events my-endpoint --tail # live, one line per delivery
commercehook event <event-id> # the inspector: headers, params, payload, replays, signature verdict
commercehook event <event-id> --raw # the body exactly as delivered, for jq
commercehook replay <event-id> --to https://staging.example.com/webhooks
commercehook whoami
commercehook version
commercehook upgrade # how to update this install, whichever way it arrived
Endpoints are referenced by id or by any unambiguous name prefix.
commercehook events prod works until you also have prod-eu, at
which point the CLI lists both and asks. It never guesses.
Where a delivery carries a platform signature and the secret is known
to CommerceHook (currently WooCommerce registrations made through us),
event prints the same verdict the dashboard shows: a tick when the
body verifies, MISMATCH when it does not, and nothing at all when
there is nothing to check.
Scripting
Every command takes --json and passes the API’s response through
untouched, so what the REST API docs say about shapes is
true here too. --tail and listen become NDJSON, one document per
line:
commercehook events my-endpoint --tail --json | jq .eventType
--api-url points the CLI at another instance (a local wrangler dev,
for example); CH_API_URL does the same from the environment.
Where things live
Config, including sign-in tokens, is stored at
~/.config/commercehook/config.json (or under $XDG_CONFIG_HOME),
created with 0600 permissions. Replays and forwards are attributed to
the signed-in account in the dashboard’s history, the same as actions
taken anywhere else.