# Webhooks

You don't write routes for a provider's webhooks: Jadpo generates them
from the provider's package
([Webhooks as events](receiving-from-outside.md#webhooks-as-events)). A connection
with a webhook secret gets `POST /webhooks/<connection>` in the `webhooks`
API. For each request, the runtime:

- checks the provider's signature over the raw body;
- drops repeats, by the provider's event id;
- answers a handshake, where the package names one;
- writes each event to the outbox, where events wait to be delivered to
  subscribers ([Subscribers](subscribers.md)).

A webhook that needs a reply runs the app's answering action inside the
request
([Webhooks that need a reply](receiving-from-outside.md#webhooks-that-need-a-reply)).
You can change a webhook route's path, but you can't switch it off.

The route is `<prefix>/<connection>` under the prefix of the `webhooks` API
the app declares, whose record and OpenAPI document list it. Outside every
declared API, it is `/webhooks/<connection>`. `jadpo routes` shows it as
`generated webhook`, with `signature` for its authentication. An app route
at the same path is `route.path_overlap` (see the
[Integrations design notes](https://github.com/jadpo-dev/jadpo/blob/main/docs/language/notes/11-integrations.md)). Replies and
handshakes are in
[Webhook replies, handshakes and further signature schemes](webhook-replies-handshakes-and-further-signature-schemes.md).

Two kinds of sender have no provider package:

- A system that signs its webhooks but has no package gets the app's own
  integration in `shared/providers/`, whose webhooks are generated the
  same way ([Senders with no package](receiving-from-outside.md#senders-with-no-package)).
- A partner with an agreement signs in as a `Service`, with a service key
  ([Service credentials](service-credentials.md)), and calls an
  ordinary route.
