A webhook sends an HTTP request to a URL you choose whenever something happens in your salon, for example when an appointment is created or a client is updated. Use it to keep another system in sync with Softalon.
Before you start
- Your salon is on the Ultimate plan.
- You have the Super Administrator or Owner role.
- You have a URL that accepts
POSTrequests with a JSON body, starting withhttps://orhttp://.
Create a webhook
- 1
Step 1 of 4
Open Webhooks
Go to Settings › Developers › Webhooks and click Create Webhook.
- 2
Step 2 of 4
Enter the destination
Fill in Destination URL, for example
https://example.com/webhook, and optionally a Description so you can recognize it later. - 3
Step 3 of 4
Choose topics
Under Topics, select the events you want. The All Topics tab lists every available topic, and Selected Topics shows what you picked. Your URL only receives the topics you select.
- 4
Step 4 of 4
Save
Click Create Webhook.
You will see:Webhook Created, and the webhook appears in the table with its status switch on.
Topics
Topics are named resource.action. These are available:
For what each trigger means, see Automation triggers explained.
What Softalon sends
Each event is a POST request with a JSON body:
{
"topic": "booking/appointment.created",
"event": {
"id": "...",
"type": "booking/appointment.created",
"resource": "booking/appointment",
"resourceId": "...",
"salonId": "...",
"data": {
"object": { "...": "the full object" },
"previousAttributes": { "...": "changed fields, for updates" }
}
}
}
The request has these headers:
Verify the signature
Every webhook has a secret. Softalon signs the request body with it using HMAC-SHA256 and sends the hex result in X-Webhook-Signature. Compute the same value from the raw request body and compare. If they don't match, ignore the request.
const crypto = require("crypto");
function isValid(rawBody, header, secret) {
const expected = "sha256=" + crypto.createHmac("sha256", secret).update(rawBody).digest("hex");
return crypto.timingSafeEqual(Buffer.from(expected), Buffer.from(header));
}
To manage the secret, use the buttons in the Secret column:
- The eye button shows the full secret, and the copy button copies it.
- The regenerate button creates a new secret right away. The old secret stops working immediately, so update your system at the same time.
Deliveries and retries
- Your URL must answer with a
2xxstatus code within 10 seconds. Anything else counts as a failure. - A failed delivery is retried, up to 5 attempts in total. The waits between attempts grow: about 30 seconds, 1 minute, 2 minutes and 4 minutes.
- Use
X-Webhook-Delivery-Idto ignore a delivery you've already processed.
Each delivery has one of these statuses:
The app doesn't show a delivery log yet. You can read deliveries through the API at GET /v1/salons/:salonId/webhook-endpoints/:webhookEndpointId/deliveries. See Create an API app.
If the last 5 deliveries to a webhook are all exhausted, Softalon turns the webhook off. Fix your endpoint, then turn the status switch back on. Events that happen while a webhook is off aren't sent later.
Edit, pause or delete a webhook
- Pause: turn off the switch in the Status column.
- Edit: open the row's menu and choose Update.
- Delete: open the row's menu and choose Delete.
Webhooks only send while your salon has an active, trialing or past-due subscription on a plan that includes webhooks.
Common questions
Each delivery is sent separately and retried on its own schedule, so don't rely on the order requests arrive in. Use the object's own timestamps instead.