ClientPress can send an HTTP POST request to any URL whenever something happens in a portal. This lets you connect ClientPress to external tools, automation platforms, and custom systems without any polling or manual effort.
Setting Up a Webhook #
- Go to Settings → ClientPress → Advanced → Webhooks
- Enter your Endpoint URL — the URL that should receive the webhook
- Optionally enter a Signing Secret to verify requests (recommended)
- Under Events to Send, check the events you want to fire
- Save settings
Leave the Endpoint URL blank to disable webhooks entirely.
Supported Events #
portal.created— Fires when a new portal is publishedfile.uploaded— Fires when a file is added to the Files tabfile.approved— Fires when a file is approvedfile.rejected— Fires when a file is rejectedtask.created— Fires when a new task is createdtask.completed— Fires when a task is marked completemessage.sent— Fires when a message is posted in Discussioninvite.accepted— Fires when a client accepts an invitation and creates their accountboard.topic_posted— Fires when a new topic is posted on the Message Boarddeliverable.uploaded— Fires when a deliverable is uploadeddeliverable.in_review— Fires when a deliverable is sent for client reviewdeliverable.approved— Fires when a client approves a deliverabledeliverable.revision_requested— Fires when a client requests a revision on a deliverable
Payload Format #
All webhook requests are HTTP POST with a JSON body and the following structure:
{
"event": "task.completed",
"portal_id": 42,
"portal_url": "https://your-site.com/client-portal/acme-corp/",
"timestamp": "2024-01-18T14:22:00+00:00",
"data": { }
}
The data object contains event-specific fields. For example, task.completed includes the task ID, title, and list ID. invite.accepted includes the new user’s ID, email, and display name.
Request Headers #
Every webhook request includes these headers:
Content-Type—application/jsonX-CP-Event— The event slug (e.g.task.completed)X-CP-Portal-ID— The portal’s post IDX-CP-Delivery— A unique UUID for this deliveryUser-Agent—ClientPress/{version}; https://clientpress.ioX-CP-Signature— Present only if a signing secret is configured
Verifying Webhook Signatures #
If you configure a signing secret, each request includes an X-CP-Signature header formatted as:
sha256={hex_encoded_hmac}
The HMAC is computed using SHA-256 over the raw JSON request body, signed with your secret. To verify a request on your endpoint:
- Read the raw request body (before parsing JSON)
- Compute
HMAC-SHA256(body, your_secret) - Compare the result to the value after
sha256=in the header - Use a constant-time comparison function to prevent timing attacks
Requests that fail signature verification should be rejected.
Delivery Behavior #
- Webhooks are sent fire-and-forget — they do not block or slow down portal actions
- There is no automatic retry if your endpoint is unavailable or returns an error
- Use the
X-CP-DeliveryUUID to detect and deduplicate any requests if needed - Your endpoint should respond with a
2xxstatus code to acknowledge receipt
Testing Your Webhook #
The easiest way to test is to use a tool like Webhook.site or RequestBin as a temporary endpoint. Paste the URL into the Webhook URL setting, trigger an event in a portal, and inspect the received payload.
