Practical Example: Clock In a Shift
An end-to-end walkthrough — get notified the moment an employee clocks in a shift in Factorial.
This example walks through a complete webhook integration, from subscription to payload, using the attendance/shift/clock_in event.
When is the event triggered?
The event fires when an employee clocks in a shift and the timer starts — for example by clicking Clock in in Factorial, or clocking in from the mobile app.
Step 1 — Create the subscription
Use attendance/shift/clock_in as the subscription_type:
curl --request POST \
--url https://api.factorialhr.com/api/2026-10-01/resources/api_public/webhook_subscriptions \
--header 'x-api-key: YOUR_API_KEY' \
--header 'content-type: application/json' \
--header 'accept: application/json' \
--data '{
"company_id": 55,
"subscription_type": "attendance/shift/clock_in",
"target_url": "https://yourapp.com/webhooks/factorial/clock-in",
"name": "Shift clock in",
"challenge": "2zal4e6d",
"enabled": true,
"api_version": "2026-10-01"
}'curl --request POST \
--url https://api.factorialhr.com/api/2026-10-01/resources/api_public/webhook_subscriptions \
--header 'Authorization: Bearer YOUR_ACCESS_TOKEN' \
--header 'content-type: application/json' \
--header 'accept: application/json' \
--data '{
"company_id": 55,
"subscription_type": "attendance/shift/clock_in",
"target_url": "https://yourapp.com/webhooks/factorial/clock-in",
"name": "Shift clock in",
"challenge": "2zal4e6d",
"enabled": true,
"api_version": "2026-10-01"
}'Keep the id from the response so you can disable or delete the subscription later.
Step 2 — Receive the payload
When an employee clocks in, Factorial sends:
{
"employee_id": 1,
"now": "2026-06-23T11:00:00.000+00:00",
"latitude": 52.377956,
"longitude": 4.89707,
"accuracy": 5,
"observations": "I clocked in 10 minutes before",
"location_type": "business_trip",
"workplace_id": 5,
"time_settings_break_configuration_id": 2,
"project_worker_id": 3,
"subproject_id": 4
}| Field | Description |
|---|---|
employee_id | The employee who clocked in |
now | Timestamp of the clock in |
latitude / longitude / accuracy | Geolocation captured at clock in, when available |
observations | Free-text note entered by the employee |
location_type | Where the shift is worked, e.g. office, work_from_home, business_trip |
workplace_id | The workplace associated with the shift |
time_settings_break_configuration_id | Break configuration applied to the shift |
project_worker_id / subproject_id | Project assignment, when time is tracked against projects |
Step 3 — Handle it
app.post("/webhooks/factorial/clock-in", async (req, res) => {
if (req.get("x-factorial-wh-challenge") !== process.env.FACTORIAL_WH_CHALLENGE) {
return res.sendStatus(401);
}
const shift = req.body;
// Acknowledge immediately, then process out of band
res.sendStatus(200);
// Retries carry an identical body, so this key skips duplicates
const dedupeKey = `clock_in:${shift.employee_id}:${shift.now}`;
if (await processedEvents.exists(dedupeKey)) return;
await externalTimeTracker.startShift({
employeeId: shift.employee_id,
startedAt: shift.now,
workplaceId: shift.workplace_id
});
await processedEvents.insert(dedupeKey);
});Why subscribe to this event?
- Trigger an action in an external system the moment an employee starts work — access control, machine assignment, task dispatch.
- Keep shifts in sync with an external time-tracking or workforce-management platform.
- Feed real-time presence data into dashboards or operational tooling.
Related
- Webhooks Subscriptions — managing the subscription lifecycle
- Payloads & Event Types — other events you can subscribe to
- Best Practices & Troubleshooting — building a reliable handler
Updated 9 days ago
Did this page help you?

