← Developers
Start here
QuickstartSDKAuthentication
Identity
Sign in with Shin ID
Access
EntitlementsUsage & Qualified Active Days
Money
Purchases & refundsWebhooksVerifying signatures
Selling
Importing a productGitHub importSelling without the SDKCurrencies and pricingBuy with Guiru from your own site
Operating
Integration diagnosticsErrors & rate limitsTestingMobile API
Reference
ReferenceVersioning & changesFor agents
Machine-readable
llms.txt
Money

Webhooks

Six events, one envelope, at-least-once delivery with exponential backoff.

The envelopeEventsDeliveryIdempotency

Register an endpoint in your product console and subscribe it to the events you want. Only public URLs are accepted — a localhost or private-range target is refused at delivery time, so use a tunnel while developing.

The envelope

json
{
  "id": "0a4b…",                          // unique per delivery attempt group: your idempotency key
  "event": "purchase.completed",
  "created_at": "2026-09-20T22:14:03.114Z",
  "data": { "purchase_id": "…", "user_id": "…", "product_id": "…", "gross_minor": 4990, "currency": "BRL" }
}
Headers
guiru-eventstring
The event name, so you can route before parsing.
guiru-signature`t=…,v1=…`
HMAC-SHA256 over timestamp.body. See verifying.
guiru-signature-previous`t=…,v1=…`
Present only during a secret rotation window — signed with the old secret so a receiver that has not redeployed yet still verifies.
user-agent`Guiru-Webhooks/1.0`
Not an authentication mechanism. Never treat it as one.

Events

entitlement.created
Someone gained access: a purchase cleared, a subscription started, Member opened the product, or an operator granted it.
entitlement.canceled
Access was cancelled. ends_at may be in the future — a cancelled subscription usually runs to the end of its period.
entitlement.expired
Access ran out on its own.
entitlement.refunded
Access was withdrawn because the money went back.
purchase.completed
A Buy with Guiru payment cleared. Carries gross_minor and currency — the currency the buyer actually paid in.
purchase.refunded
A purchase was refunded, or lost a chargeback (chargeback: true).
webhook.test
Sent when you press *Send test* in the console. Same signature, same envelope; data.message says it is a test. Handle it by acknowledging with 2xx and doing nothing.

Delivery

Delivery is at-least-once. We wait up to ten seconds for a response; any 2xx is success, anything else is a failure and is retried with exponential backoff: 1 minute, 5 minutes, 30 minutes, 2 hours, 12 hours, then the delivery is marked dead and stops. Recent deliveries, their status codes and their errors are listed in the product console.

Careful

Answer 2xx as soon as you have durably accepted the event, and do the work after. A handler that runs a slow job before responding turns a 200 into a timeout, and a timeout into four more copies of the same event.

Idempotency

Key on id from the envelope and ignore an event you have already applied. Order is not guaranteed either — an entitlement.created can land after the entitlement.canceled that followed it — so make each handler state-setting rather than state-advancing, or re-read the entitlement and trust that instead.

PreviousPurchases & refundsNextVerifying signatures
Guiru
AboutStoreHow Guiru worksQuality BarGSPGuiru MemberStatus
Buying
Buy with GuiruYour libraryRefundsBuyer termsTrust & safety
Builders
For buildersSubmit a productGuiru ProPricing & feesPromoteDeveloper docs
Help
Help centreYour libraryBuying & refundsHow a product gets listedHow ranking worksReport a problem
Legal
All policiesTermsPrivacyCookiesCreator PoolAffiliate disclosure
Your account
Account settingsSign in
Shin AI
Shin WebsiteKatsuiTrouble? Message Mario
Find your next favourite. Software, games and digital products on Guiru.Guiru Beta · Feedback© 2026 Shinai Tecnologias I.S.
Beta
StoreLibraryBuildersMember
Sign in
StoreSearchLibraryMemberSign in