Cron Groups API
Cron groups organize cron jobs into logical collections for easier management.
Endpoints
| Method | Path | Description |
|---|---|---|
| GET | /api/cron-groups | List cron groups |
| POST | /api/cron-groups | Create cron group |
| GET | /api/cron-groups/{id} | Get cron group |
| PATCH | /api/cron-groups/{id} | Update cron group |
| DELETE | /api/cron-groups/{id} | Delete cron group |
| POST | /api/cron-groups/reorder | Reorder groups |
Cron Group Object
{
"id": "cc0f1a8e-2b4d-4f19-9a3c-7e5b1d206f44",
"organizationId": "9f1c2b7e-3a4d-4f88-91b2-7c0e5d8a6f31",
"name": "Health Checks",
"slug": "health-checks",
"description": "Periodic health check webhooks",
"sortOrder": 1,
"isCollapsed": false,
"jobCount": 5,
"createdAt": "2026-01-01T00:00:00Z",
"updatedAt": "2026-01-15T10:30:00Z"
}Responses nest this object under group, and the list endpoint returns an array of them under
groups. Every response carries all ten fields.
| Field | Note |
|---|---|
slug | Derived from name on create, and re-derived whenever name changes. Not settable directly |
sortOrder | The display position, zero-based. The field is sortOrder, not order |
isCollapsed | Whether the group is collapsed in the dashboard |
jobCount | Number of cron jobs in the group. Read-only |
Info
A group ID or its slug works anywhere {id} appears. Get, update, and delete all accept either.
List Cron Groups
GET /api/cron-groupsExample
curl https://api.hookbase.app/api/cron-groups \
-H "Authorization: Bearer whr_your_api_key"Response
{
"groups": [
{
"id": "cc0f1a8e-2b4d-4f19-9a3c-7e5b1d206f44",
"name": "Health Checks",
"slug": "health-checks",
"sortOrder": 1,
"jobCount": 5
},
{
"id": "d71b3c92-8e5a-4c07-b6f1-2a9d40e8b355",
"name": "Sync Jobs",
"slug": "sync-jobs",
"sortOrder": 2,
"jobCount": 3
}
]
}Create Cron Group
POST /api/cron-groupsRequest Body
| Field | Type | Required | Description |
|---|---|---|---|
| name | string | Yes | Group name |
| description | string | No | Optional description |
Example
curl -X POST https://api.hookbase.app/api/cron-groups \
-H "Authorization: Bearer whr_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"name": "Data Sync",
"description": "Periodic data synchronization jobs"
}'Response
201 Created. sortOrder is assigned automatically — one past the highest existing group — and the
slug is derived from the name.
{
"group": {
"id": "b83e6d10-4f2a-4d77-8c15-9ab3e7f21c60",
"organizationId": "9f1c2b7e-3a4d-4f88-91b2-7c0e5d8a6f31",
"name": "Data Sync",
"slug": "data-sync",
"description": "Periodic data synchronization jobs",
"sortOrder": 3,
"isCollapsed": false,
"jobCount": 0,
"createdAt": "2026-01-15T10:30:00Z",
"updatedAt": "2026-01-15T10:30:00Z"
}
}Errors
| Status | Error | Cause |
|---|---|---|
| 400 | Name is required | name missing, not a string, or blank |
| 400 | A group with this name already exists | Another group already derives the same slug |
Get Cron Group
GET /api/cron-groups/{id}Accepts the group's ID or its slug.
Response
The group object and nothing else — jobCount says how many jobs are in it, but the jobs themselves
are not included, and no endpoint returns a group's jobs. Each job carries a groupId, so list the
jobs with GET /api/cron and filter on it yourself — there is no groupId query parameter. See the
Cron API.
{
"group": {
"id": "cc0f1a8e-2b4d-4f19-9a3c-7e5b1d206f44",
"organizationId": "9f1c2b7e-3a4d-4f88-91b2-7c0e5d8a6f31",
"name": "Health Checks",
"slug": "health-checks",
"description": "Periodic health check webhooks",
"sortOrder": 1,
"isCollapsed": false,
"jobCount": 5,
"createdAt": "2026-01-01T00:00:00Z",
"updatedAt": "2026-01-15T10:30:00Z"
}
}| Status | Error |
|---|---|
| 404 | Group not found |
Update Cron Group
PATCH /api/cron-groups/{id}Request Body
All optional; only fields present in the body are changed.
| Field | Type | Description |
|---|---|---|
| name | string | Group name. Changing it re-derives slug |
| description | string | Description (null or "" clears it) |
| sortOrder | number | Display position |
| isCollapsed | boolean | Whether the group is collapsed in the dashboard |
Response
The updated group object under group, in the same shape as
Get Cron Group.
Errors
| Status | Error | Cause |
|---|---|---|
| 400 | Name cannot be empty | name present but blank |
| 400 | A group with this name already exists | The new name derives a slug another group holds |
| 404 | Group not found | No group with that ID or slug |
Delete Cron Group
DELETE /api/cron-groups/{id}Warning
Deleting a group does not delete the cron jobs within it. Jobs are moved to the "Ungrouped" category.
Response
{
"success": true
}Deleting requires an API key with the delete scope.
| Status | Error |
|---|---|
| 404 | Group not found |
Reorder Groups
POST /api/cron-groups/reorderRequest Body
| Field | Type | Required | Description |
|---|---|---|---|
| groupIds | string[] | Yes | Group IDs in the desired order. Each group's sortOrder becomes its index in this array, starting at 0 |
Example
curl -X POST https://api.hookbase.app/api/cron-groups/reorder \
-H "Authorization: Bearer whr_your_api_key" \
-H "Content-Type: application/json" \
-d '{
"groupIds": [
"d71b3c92-8e5a-4c07-b6f1-2a9d40e8b355",
"cc0f1a8e-2b4d-4f19-9a3c-7e5b1d206f44",
"b83e6d10-4f2a-4d77-8c15-9ab3e7f21c60"
]
}'Response
{
"success": true
}The reordered groups are not echoed back; re-list them to read the new sortOrder values.
Info
Unlisted groups keep their current sortOrder. Only the IDs you send are renumbered, so a
partial list can collide with a group you left out. Send every group ID to renumber them cleanly.
Errors
| Status | Error | Cause |
|---|---|---|
| 400 | groupIds must be an array | groupIds missing or not an array |
| 404 | One or more groups not found | An ID is not a string or does not belong to this organization. Nothing is reordered |
Related
- Cron Jobs API — Manage individual cron jobs
- Cron Guide — Cron scheduling concepts