Fasáda Webhooks
Všetko ide cez jednu fasádu RoundlyConsulting\Webhooks\Facades\Webhooks (globálny alias Webhooks) nad WebhooksManager. Ploché slovesá posielajú; for($owner) obmedzí všetko na jedného vlastníka; inbound() a outbound() spravujú jednotlivé smery:
use RoundlyConsulting\Webhooks\DataTransferObjects\PruneOptions;
use RoundlyConsulting\Webhooks\Facades\Webhooks;
// Sending
Webhooks::send($endpoint, 'invoice.paid', ['invoice' => 42]); // one endpoint
Webhooks::send($endpoint, 'invoice.paid', $payload, id: 'invoice-42-paid'); // idempotent
Webhooks::broadcast('system.maintenance', $payload); // owner-less endpoints only
Webhooks::for($team)->broadcast('invoice.paid', $payload); // every subscribed endpoint of $team
// The two directions — app-wide, or scoped to one owner
$created = Webhooks::inbound()->create(handler: 'billing');
$endpoints = Webhooks::for($team)->outbound()->endpoints();
// Registries, retention and testing
Webhooks::schemes()->extend('github', GitHubScheme::class);
Webhooks::handlers()->register('billing', BillingWebhookHandler::class);
$result = Webhooks::prune(new PruneOptions(dryRun: true));
$fake = Webhooks::fake();Metódy manažéra
| Metóda | Vracia | Čo robí |
|---|---|---|
send(OutboundEndpoint $endpoint, string $eventType, array|Arrayable|JsonSerializable $payload, ?string $id = null) | OutboundDelivery | Zaradí jedno podpísané doručenie; s $id vráti opakovanie prvé doručenie a nič nové nezaradí. |
broadcast(string $eventType, array|Arrayable|JsonSerializable $payload, ?Model $owner = null) | Collection<int, OutboundDelivery> | Každý zapnutý endpoint vlastníka $owner, ktorý typ odoberá; null znamená len endpointy bez vlastníka. |
for(Model $owner) | Accessors\OwnerWebhooks | Prístup obmedzený na jedného vlastníka: inbound(), outbound(), broadcast(), owner(). |
inbound() | Accessors\InboundWebhooks | Prijímanie: endpointy, spracovanie požiadaviek, overenie, replay, záznam. |
outbound() | Accessors\OutboundWebhooks | Odosielanie: endpointy, send, ping, opätovné doručenie, pravidelný beh, záznam. |
schemes() | Accessors\SchemeRegistry | Register podpisových schém. |
handlers() | Accessors\HandlerRegistry | Register handlerov prichádzajúcich webhookov. |
prune(?PruneOptions $options = null) | PruneResult | Retencia — to, čo spúšťa webhooks:prune. |
Webhooks::fake() | Testing\WebhooksFake | Len na fasáde — nahrávací fake, naviazaný aj v kontajneri. |
Po spustení Webhooks::fake() sú na fasáde dostupné aj sent(), broadcasts(), redelivered(), replayed() a všetky assert…() — pozrite Testovanie.
inbound() — InboundWebhooks
| Metóda | Vracia | Čo robí |
|---|---|---|
create(?string $handler = null, string $scheme = 'default', ?string $name = null, ?string $secret = null, ?InboundEndpointOptions $options = null, ?Model $owner = null) | CreatedInboundEndpoint | Nový endpoint: endpoint, url, secret (zobrazí sa raz). Neznámy handler alebo schéma vyhodí výnimku. |
update(InboundEndpoint $endpoint, InboundEndpointChanges $changes) | InboundEndpoint | Názov, handler, schéma, voľby; clear vráti nullable polia na predvolené. |
enable($endpoint) · disable($endpoint) | InboundEndpoint | Vypnutý endpoint odpovedá 404 rovnako ako neznámy. |
delete(InboundEndpoint $endpoint) | void | Mäkké zmazanie; URL odpovedá 404 a tajné kľúče sa okamžite vymažú. |
rotateSecret(InboundEndpoint $endpoint, ?CarbonInterface $grace = null, ?string $secret = null) | RotatedSecret | Nový (alebo importovaný) tajný kľúč; starý overuje až do konca prechodného obdobia. |
find(int|string $id) · endpoints() | InboundEndpoint · Collection | Prístupy obmedzené na vlastníka vidia len jeho endpointy (EndpointNotFoundException). |
receive(string $key, Request $request) | Response | Celé spracovanie prichádzajúcej požiadavky — to, čo spúšťa trasa. |
verify(InboundEndpoint $endpoint, Request $request) | VerifiedWebhook | Len schéma: bez kontroly veľkosti, bez deduplikácie, nič sa neuloží (nonce RFC 9421 sa zaznamená hneď). |
replay(InboundDelivery $delivery) | InboundDelivery | Spustí handler znova nad uloženým obsahom, označené ako replay. |
deliveries(?InboundEndpoint $endpoint = null) | Builder<InboundDelivery> | Záznam prichádzajúcich doručení ako dopyt. |
outbound() — OutboundWebhooks
| Metóda | Vracia | Čo robí |
|---|---|---|
create(string $url, array $events = ['*'], ?string $name = null, array $headers = [], string $scheme = 'default', ?OutboundEndpointOptions $options = null, ?Model $owner = null) | CreatedOutboundEndpoint | Nový endpoint; URL posúdi ochrana pred SSRF. endpoint, secret (zobrazí sa raz). |
update(OutboundEndpoint $endpoint, OutboundEndpointChanges $changes) | OutboundEndpoint | Nová URL sa posúdi znova; nové hlavičky nahradia staré. |
enable($endpoint) · disable($endpoint) | OutboundEndpoint | Vypnutie vyvolá EndpointDisabled(manual) a zruší čakajúce doručenia; zapnutie vynuluje počítadlo zlyhaní. |
delete(OutboundEndpoint $endpoint) | void | Mäkké zmazanie; čakajúce doručenia sa zrušia; tajné kľúče, URL a vlastné hlavičky sa okamžite vymažú. |
rotateSecret(OutboundEndpoint $endpoint, ?CarbonInterface $grace = null) | RotatedSecret | Počas prechodného obdobia podpisujú oba tajné kľúče. |
find(int|string $id) · endpoints() | OutboundEndpoint · Collection | Endpointy s prednačítaným vlastníkom. |
send($endpoint, string $eventType, $payload, ?string $id = null) | OutboundDelivery | To isté ako Webhooks::send(). |
ping(OutboundEndpoint $endpoint) | OutboundDelivery | Testovacia udalosť webhook.ping bez ohľadu na odbery endpointu. |
redeliver(OutboundDelivery $delivery) | OutboundDelivery | Nová séria pod rovnakým webhook-id. |
redeliverFailed(OutboundEndpoint $endpoint, ?CarbonInterface $since = null, bool $includeCancelled = false) | RedeliveryResult | Každé zlyhané (voliteľne aj zrušené) doručenie endpointu. |
dispatchDue() | int | Pravidelný beh — to, čo spúšťa webhooks:retry; počet odoslaných jobov. |
deliveries(?OutboundEndpoint $endpoint = null) | Builder<OutboundDelivery> | Záznam odchádzajúcich doručení ako dopyt. |
attempts(OutboundDelivery $delivery) | Collection<int, OutboundAttempt> | Každý pokus každej série v poradí. |
for($owner) — hranica
Webhooks::for($owner) vráti OwnerWebhooks s metódami inbound(), outbound(), broadcast(string $eventType, $payload) a owner(). Jeho prístupy odmietnu endpoint alebo doručenie iného vlastníka výnimkou EndpointNotFoundException, akoby neexistovali; create() nastaví vlastníka a find(), endpoints() a deliveries() vidia len riadky tohto vlastníka. Metóda webhooks() z traitu HasWebhooks vracia rovnaký prístup.
schemes() a handlers() — registre
| SchemeRegistry | HandlerRegistry |
|---|---|
extend(string $name, class-string|Closure $scheme) | register(string $alias, class-string|Closure $handler) |
forget(string $name) | forget(string $alias) |
names(): list<string> | aliases(): list<string> |
has(string $name): bool | has(string $alias): bool |
resolve(string $name): SignatureScheme | resolve(string $alias): InboundHandler |
^[a-z0-9][a-z0-9_.-]{0,63}$ | ^[a-z0-9][a-z0-9_.-]{0,99}$ |
UnknownSchemeException | UnknownHandlerException |
Closure schémy je továreň (vracia schému); closure handlera je samotný handler. Triedy sa vytvárajú cez kontajner, takže funguje injektovanie do konštruktora. Oba registre platia pre celý proces: zaregistrujte v boot() service providera a platia pre každú požiadavku, každý job workera a každú požiadavku Octane. Registrácia vo vnútri požiadavky alebo jobu platí tiež do konca procesu, podobne ako Gate::define(). forget() odstráni registráciu vykonanú za behu; nakonfigurovaná ostane.
Makro trasy
Route::webhooks(string $prefix = 'webhooks', array $middleware = []): Route pripojí spracovanie prichádzajúcich webhookov na vašu vlastnú trasu — pozrite Prijímanie webhookov.
Dátové objekty
V RoundlyConsulting\Webhooks\DataTransferObjects, všetky final readonly:
| Trieda | Polia a metódy |
|---|---|
CreatedInboundEndpoint | endpoint, url, secret — tajný kľúč je skrytý v print_r, var_dump a json_encode. |
CreatedOutboundEndpoint | endpoint, secret (skrytý). |
RotatedSecret | secret (skrytý), graceEndsAt (CarbonImmutable). |
InboundEndpointOptions | ?rateLimitPerMinute, ?maxPayloadBytes, ?contentTypes, ?toleranceSeconds, ?schemeOptions |
InboundEndpointChanges | ?name, ?handler, ?scheme, ?options, list<string> clear |
OutboundEndpointOptions | ?rateLimitPerMinute, ?schemeOptions, ?description |
OutboundEndpointChanges | ?url, ?events, ?name, ?headers, ?scheme, ?options, list<string> clear |
InboundWebhook | deliveryId, endpoint, ?type, payload, headers, receivedAt, isReplay, run, attempt; get(), header(), owner(), isFirstAttempt() |
IncomingWebhook | headers (lower-cased, first value), body, receivedAt, endpointKey, toleranceSeconds, schemeOptions, ?request; header() |
VerifiedWebhook | ?deliveryId, ?timestamp, ?eventType, idIsSigned, slot, replayProtected = false, ?commit; committed() |
OutgoingWebhook | id (msg_…), timestamp, body, eventType |
SignatureHeaders | headers (array<string, string>) |
SanitizeContext | direction, endpoint, ?eventType |
PruneOptions · PruneResult | dryRun = false, ?now · inboundPayloads, outboundBodies, attemptBodies, inboundDeliveries, outboundDeliveries, attempts, expiredSecrets, endpoints, dryRun; total() |
RedeliveryResult | queued, skippedPruned |
DoctorFinding | level, check, ?detail; message(), error(), warning() |
SignedRequestData | uri, headers, body; server() |
Enumy
V RoundlyConsulting\Webhooks\Enums, s reťazcovými hodnotami, preloženými popiskami (webhooks::enums.*) a pomocníkmi z enums-for-laravel — label(), labels(), values(), options(), fromLabel(), is(). Hodnoty sú snake_case názvu prípadu:
| Enum | Hodnoty |
|---|---|
InboundStatus | received, queued, processing, processed, failed |
OutboundStatus | pending, sending, retrying, succeeded, failed, cancelled |
RejectionReason | not_found … sanitizer_failed — status(): int, publicCode(): string (endpoint_disabled reads not_found) |
AttemptError | http_status, redirect_not_followed, timeout, connection, tls, unresolved, blocked, cannot_pin, too_many_redirects, redirect_downgrade, signing, worker_lost, unexpected |
DisableReason | consecutive_failures, gone, manual |
DuplicateResponse | accept, conflict |
SecretSlot | current, previous |
SecretEncoding | standard_webhooks, raw |
Direction | inbound, outbound |
FindingLevel | error, warning |
Prejavte lásku k open source
Tento balík je zadarmo pod licenciou MIT. Ak vám šetrí čas, jednorazový príspevok alebo členstvo na Patreone nám pomôže ho ďalej udržiavať, testovať a dokumentovať.
Ďalšie spôsoby podpory vrátane kryptomienOdoslaním daru súhlasíte s našimi podmienkami prijímania darov.
Chcete to zabudovať do svojho produktu?
Naše balíky integrujeme do zákazkových Laravel a AI riešení. Napíšte nám, na čom pracujete, a ozveme sa do 48 hodín.