Webhooks
Webhooks let you connect SimpleCommenter with any external service. Send data out when events happen, or receive updates back to sync changes from other systems.
Two Types of Webhooks
SimpleCommenter supports two webhook directions:
- Name
Outbound- Type
- Sends data out
- Description
When events happen in SimpleCommenter (new comment, reply, status change), we send data to your URL.
- Name
Inbound- Type
- Receives data
- Description
External systems can call our API to update comments in SimpleCommenter (add replies, change status/priority).
Outbound Webhooks
Send data to your servers when events occur in SimpleCommenter.
Setup
- Go to Project Settings > Integrations
- Click Webhook
- Click New Webhook
- Configure your webhook:
- Name - A friendly identifier
- Trigger Event - When to fire the webhook
- URL - Your endpoint
- Authentication - Optional auth for your endpoint
- Enable the webhook with the toggle
- Click Save
Trigger Events
You can create separate webhooks for each event type:
- Name
New Comment- Type
- comment
- Description
Fires when a visitor submits new feedback.
- Name
Reply- Type
- reply
- Description
Fires when someone replies to a comment.
- Name
Status/Priority Update- Type
- status_update
- Description
Fires when a comment's status or priority changes.
Endpoint Requirements
Your webhook endpoint must:
- Accept
POSTorPUTrequests (configurable) - Accept
application/jsoncontent type - Return a
2xxstatus code - Be publicly accessible (no localhost in production)
Payload Reference
All outbound webhooks send JSON. The type field tells you which event triggered the webhook.
New Comment Payload
{
"type": "comment",
"commentId": "507f1f77bcf86cd799439011",
"commentNumber": 42,
"title": "Bug Report",
"text": "The checkout button doesn't work on mobile",
"status": "todo",
"priority": "normal",
"date": "2024-01-15T10:30:00.000Z",
"by": "John Doe",
"domain": "https://example.com",
"slug": "/checkout",
"link": "https://example.com#simple-comment=507f1f77bcf86cd799439011",
"metadata": {
"browser": "Chrome 120",
"os": "iOS 17"
},
"attachments": [
{
"type": "image",
"url": "https://s3.amazonaws.com/...",
"name": "Screenshot"
},
{
"type": "file",
"url": "https://s3.amazonaws.com/...",
"name": "error-log.txt"
}
]
}
- Name
type- Type
- string
- Description
Always
"comment"for new comments.
- Name
commentId- Type
- string
- Description
Unique identifier for the comment.
- Name
commentNumber- Type
- number
- Description
Human-readable comment number (e.g., #42).
- Name
title- Type
- string | null
- Description
Comment title if provided.
- Name
text- Type
- string
- Description
The feedback message content.
- Name
status- Type
- string
- Description
Current status:
todo,in_progress,review,rework,on_hold,blocked,done,cancelled,wont_fix.
- Name
priority- Type
- string
- Description
Priority level:
low,normal,high.
- Name
date- Type
- string
- Description
ISO 8601 timestamp when submitted.
- Name
by- Type
- string
- Description
Name or email of person who submitted.
- Name
domain- Type
- string
- Description
The website domain.
- Name
slug- Type
- string
- Description
Page path where feedback was submitted.
- Name
link- Type
- string
- Description
Direct link to view the comment.
- Name
metadata- Type
- object
- Description
Additional context (browser, OS, custom fields).
- Name
attachments- Type
- array
- Description
Screenshots and uploaded files with presigned URLs.
Reply Payload
{
"type": "reply",
"commentId": "507f1f77bcf86cd799439011",
"commentNumber": 42,
"replyText": "Thanks for reporting! We're looking into this.",
"date": "2024-01-15T11:00:00.000Z",
"by": "Support Team",
"domain": "https://example.com",
"slug": "/checkout",
"link": "https://example.com#simple-comment=507f1f77bcf86cd799439011",
"metadata": {},
"attachments": []
}
- Name
type- Type
- string
- Description
Always
"reply"for replies.
- Name
replyText- Type
- string
- Description
The reply message content.
- Name
by- Type
- string
- Description
Name of the person who replied.
Status Update Payload
{
"type": "status_update",
"commentId": "507f1f77bcf86cd799439011",
"commentNumber": 42,
"status": "in_progress",
"priority": "high",
"previousStatus": "todo",
"previousPriority": "normal",
"updatedFields": ["status", "priority"],
"date": "2024-01-15T11:30:00.000Z",
"by": "Jane Smith",
"domain": "https://example.com",
"slug": "/checkout",
"link": "https://example.com#simple-comment=507f1f77bcf86cd799439011"
}
- Name
type- Type
- string
- Description
Always
"status_update"for status/priority changes.
- Name
status- Type
- string
- Description
New status value.
- Name
priority- Type
- string
- Description
New priority value.
- Name
previousStatus- Type
- string
- Description
Status before the change.
- Name
previousPriority- Type
- string
- Description
Priority before the change.
- Name
updatedFields- Type
- array
- Description
Which fields changed:
["status"],["priority"], or["status", "priority"].
Authentication
Outbound Authentication
Protect your endpoint by requiring authentication. SimpleCommenter supports:
- Name
None- Type
- No auth
- Description
No authentication header sent.
- Name
Bearer Token- Type
- Authorization header
- Description
Sends
Authorization: Bearer your-tokenheader.
- Name
Basic Auth- Type
- Authorization header
- Description
Sends
Authorization: Basic base64(username:password)header.
Inbound Webhooks (Two-Way Sync)
Allow external systems to update SimpleCommenter by calling our API.
Generate an Integration Token
- Go to Project Settings > Integrations > Webhook
- In the Inbound Actions section, select which actions to allow:
- Reply to comments - Add replies from external systems
- Update status/priority - Change comment status or priority
- Click Generate Token
- Copy the token immediately (it won't be shown again)
Store your integration token securely. Anyone with this token can perform the allowed actions on your comments.
API Endpoint
POST https://simplecommenter.com/api/integrations/action
Request Format
{
"token": "your-integration-token",
"action": "reply",
"payload": {
"commentId": "507f1f77bcf86cd799439011",
"text": "This has been fixed in version 2.1",
"name": "Bot",
"email": "bot@example.com"
}
}
Available Actions
Reply Action
Add a reply to a comment from an external system.
{
"token": "your-integration-token",
"action": "reply",
"payload": {
"commentId": "507f1f77bcf86cd799439011",
"text": "Thanks for your feedback!",
"name": "Support Bot",
"email": "support@example.com"
}
}
- Name
commentId- Type
- string
- required
- Description
The ID of the comment to reply to.
- Name
text- Type
- string
- required
- Description
The reply message.
- Name
name- Type
- string
- Description
Display name for the reply author.
- Name
email- Type
- string
- Description
Email for the reply author.
Status Update Action
Change a comment's status or priority.
{
"token": "your-integration-token",
"action": "status_update",
"payload": {
"commentId": "507f1f77bcf86cd799439011",
"status": "done",
"priority": "high"
}
}
- Name
commentId- Type
- string
- required
- Description
The ID of the comment to update.
- Name
status- Type
- string
- Description
New status. Must be one of:
todo,in_progress,review,rework,on_hold,blocked,done,cancelled,wont_fix.
- Name
priority- Type
- string
- Description
New priority. Must be one of:
low,normal,high.
At least one of status or priority is required for status_update action.
Response Format
Success Response
{
"success": true,
"message": "Integration action completed successfully",
"result": {
"_id": "507f1f77bcf86cd799439011",
"oldStatus": "todo",
"newStatus": "done"
}
}
Error Responses
Invalid Token (403)
{
"error": "Invalid token"
}
Action Not Allowed (403)
{
"error": "Action not allowed"
}
Comment Not Found (500)
{
"error": "Comment with ID xyz not found"
}
Invalid Status (500)
{
"error": "Invalid status: invalid. Must be one of: todo, in_progress, ..."
}
Example: Node.js Webhook Handler
const express = require('express');
const app = express();
app.use(express.json());
app.post('/webhook', (req, res) => {
const { type, commentId, commentNumber } = req.body;
switch (type) {
case 'comment':
console.log(`New comment #${commentNumber}: ${req.body.text}`);
// Create ticket in your system, send to Slack, etc.
break;
case 'reply':
console.log(`Reply to #${commentNumber}: ${req.body.replyText}`);
break;
case 'status_update':
console.log(`#${commentNumber} status: ${req.body.previousStatus} → ${req.body.status}`);
break;
}
res.status(200).json({ received: true });
});
app.listen(3000);
Example: Calling Inbound API
const response = await fetch('https://simplecommenter.com/api/integrations/action', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
token: process.env.SIMPLECOMMENTER_TOKEN,
action: 'status_update',
payload: {
commentId: '507f1f77bcf86cd799439011',
status: 'done'
}
})
});
const result = await response.json();
console.log(result.success ? 'Updated!' : result.error);
Use Cases
Sync with Project Management Tools
When a new comment comes in, create a task in your project management tool. When the task is completed there, call the inbound API to update the status in SimpleCommenter.
Custom Notifications
Send new comments to Discord, Slack, or email using your own formatting and routing logic.
Analytics & Reporting
Forward all webhook events to your data warehouse to build custom dashboards and reports.
Automated Responses
Use the inbound API to automatically reply to comments that match certain criteria (e.g., auto-acknowledge bug reports).
Next Steps
- Trello Integration - Automatic two-way sync with Trello
- API Reference - Full API documentation