Hooksy is a local-first webhook capture tool. It gives you a public URL you can hand to any external service, stores whatever it sends locally, and lets you inspect the requests in a clean UI — all running on your own machine.
It's a personal utility in the spirit of RequestBin or webhook.site, but with no accounts, no cloud storage, and no server to trust — everything lives in a local SQLite file.
npm installnpm startThis builds the frontend and server, then starts everything: the local HTTP
server, the UI, SQLite persistence, and a public tunnel. It also opens the UI
in your default browser automatically. If you'd rather it didn't, set
HOOKSY_NO_OPEN=1 npm start.
For active development, use:
npm run devThis runs the Vite dev server and the API server together with hot reload.
Other scripts:
npm run build # build frontend + server
npm run typecheck # type-check both frontend and serverClick Create listener URL in the top bar. Enter a name for the bin, e.g.
PayPal Sandbox — Hooksy normalizes it into a URL-safe path (paypal-sandbox)
and shows the full listener URL live as you type:
https://<your-public-url>/hook/paypal-sandbox
Copy it with the Copy URL button and paste it into the external service's webhook settings. The modal also lists your existing bins so you can quickly grab a URL for one you've already used.
If the public tunnel isn't connected yet, the modal falls back to your local URL and warns you that external services won't be able to reach it until the tunnel is up.
Hooksy accepts any HTTP method at:
/hook/:binName
/hook/:binName/anything/else
Whatever you send — GET, POST, PUT, PATCH, DELETE, etc. — is captured and
grouped under binName. Every request gets a 200 { "ok": true } response,
which is what most webhook providers expect to consider delivery successful.
JSON bodies are parsed and stored both as pretty-printed JSON and as the raw payload. Form bodies and multipart uploads are also parsed (for file uploads, only metadata — field name, filename, content type, size — is kept, not the file contents). Anything else is stored as a raw body so you can still inspect it without Hooksy crashing on unexpected content types.
On startup, Hooksy opens a tunnel using localtunnel, which proxies a public HTTPS URL to your local server. No account or token is required for the default flow.
The UI shows both URLs:
Local: http://localhost:61337
Public: https://<random-id>.loca.lt
If the tunnel fails to connect, Hooksy keeps running locally — you'll see a clear warning that external services can't reach it until the tunnel is restored. Use the Restart tunnel button in the UI to try again.
If you only need local capture (e.g. testing with a service that can already
reach localhost, or via your own reverse proxy), disable the tunnel with an
environment variable:
HOOKSY_DISABLE_TUNNEL=1 npm startCaptured requests and bins are stored in a local SQLite database at:
data/hooksy.db
relative to the project root. Nothing is sent anywhere else. Hooksy keeps the latest 1,000 requests by default and automatically prunes older ones.
From the UI:
- Delete request — removes a single selected request.
- Clear "<bin>" — removes all requests in the currently selected bin, but keeps the bin itself.
- Delete "<bin>" — permanently removes the bin along with every request in it.
- Clear all — removes every captured request across all bins.
All of these ask for confirmation before deleting anything.
Click Pause capture to stop storing new requests. While paused, incoming
requests still get a 200 { "ok": true } response (so the sender doesn't see
failures or retries) — they're just not saved. Useful when a service is
retrying aggressively or being noisy while you're not actively testing.
Hooksy is a single-user local tool. It intentionally has no login, accounts,
teams, permissions, cloud sync, or hosted deployment — just npm start and
a webhook inbox on your machine.