Draft & Publish
Техническое руководство из исходного проекта Notty. Примеры, параметры и эксплуатационные ограничения.
Notty CMS supports a draft/publish workflow, future publication timestamps, revisions, and approval workflows.
Enable Draft & Publish
Set draftAndPublish: true in your schema options:
{
"kind": "collectionType",
"info": { "singularName": "article", "pluralName": "articles", "displayName": "Article" },
"options": {
"draftAndPublish": true
},
"attributes": {
"title": { "type": "string", "required": true },
"body": { "type": "richtext" }
}
}
When enabled, new entries start as drafts. They have published_at: null until explicitly published.
Basic Workflow
1. Create a Draft
curl -X POST http://localhost:2102/api/content/article \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "title": "Work in Progress", "body": "<p>Draft content...</p>" }'
Response includes "published_at": null — this entry is a draft.
2. Edit the Draft
curl -X PUT http://localhost:2102/api/content/article/1 \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "body": "<p>Updated draft content.</p>" }'
3. Publish
curl -X PUT http://localhost:2102/api/content/article/1/publish \
-H "Authorization: Bearer $TOKEN"
Response now includes "published_at": "2024-01-15T10:30:00.000Z".
4. Unpublish
curl -X PUT http://localhost:2102/api/content/article/1/unpublish \
-H "Authorization: Bearer $TOKEN"
Sets published_at back to null.
Filter by Publish Status
# Only published entries
curl "http://localhost:2102/api/content/article?published=true" \
-H "Authorization: Bearer $TOKEN"
# Only drafts
curl "http://localhost:2102/api/content/article?published=false" \
-H "Authorization: Bearer $TOKEN"
# All entries (default for admin)
curl "http://localhost:2102/api/content/article" \
-H "Authorization: Bearer $TOKEN"
Scheduled Publishing
Publish an entry at a future date:
curl -X PUT http://localhost:2102/api/content/article/1/publish \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "publishedAt": "2024-06-01T09:00:00.000Z" }'
Notty stores the future published_at timestamp. The entry is treated as unpublished until that moment is reached.
Current behavior: this is timestamp-based scheduling. There is no separate public cron endpoint for content publication, and delayed
entry.publishwebhooks are not emitted automatically when the future timestamp is reached.
Bulk Operations
Publish Multiple Entries
curl -X PATCH http://localhost:2102/api/content/article/bulk-update \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{
"ids": [1, 2, 3],
"data": { "published_at": "2024-01-15T10:00:00.000Z" }
}'
Delete Multiple Drafts
curl -X DELETE http://localhost:2102/api/content/article/bulk-delete \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "ids": [4, 5] }'
Revisions
When revisions are enabled for your project, Notty stores entry history. Revision endpoints are available to authenticated administrators only.
List Revisions
curl http://localhost:2102/api/content/article/1/revisions \
-H "Authorization: Bearer $TOKEN"
View a Specific Revision
curl http://localhost:2102/api/content/article/1/revisions/3 \
-H "Authorization: Bearer $TOKEN"
Restore a Revision
curl -X POST http://localhost:2102/api/content/article/1/revisions/3/restore \
-H "Authorization: Bearer $TOKEN"
Restoring creates a new revision with the restored data, so you never lose the current state.
Approval Workflow
For teams that need editorial review before publishing, enable a workflow in your schema:
{
"options": {
"draftAndPublish": true,
"workflow": {
"enabled": true,
"initialState": "draft",
"states": [
{ "name": "draft", "label": "Draft", "color": "#6b7280" },
{ "name": "review", "label": "In Review", "color": "#f59e0b" },
{ "name": "approved", "label": "Approved", "color": "#22c55e", "publishable": true },
{ "name": "rejected", "label": "Rejected", "color": "#ef4444" }
],
"transitions": [
{ "from": "draft", "to": "review", "label": "Submit for Review" },
{
"from": "review",
"to": "approved",
"roles": ["admin", "super-admin"],
"label": "Approve"
},
{
"from": "review",
"to": "rejected",
"roles": ["admin", "super-admin"],
"label": "Reject"
},
{ "from": "rejected", "to": "draft", "label": "Revise" },
{ "from": "approved", "to": "draft", "label": "Unpublish" }
]
}
}
}
Transition an Entry
# Submit for review
curl -X PUT http://localhost:2102/api/content/article/1/workflow/transition \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "to": "review", "comment": "Ready for editor review" }'
View Workflow State
curl http://localhost:2102/api/content/article/1/workflow \
-H "Authorization: Bearer $TOKEN"
View Transition History
curl http://localhost:2102/api/content/article/1/workflow/history \
-H "Authorization: Bearer $TOKEN"
Content Releases
Group multiple entries into a release that can be published together:
Create a Release
curl -X POST http://localhost:2102/api/admin/content-releases \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{
"name": "Spring Launch",
"scheduledAt": "2024-03-20T09:00:00.000Z"
}'
Add entries to the release, then publish them all at once or on schedule.
Comments & Collaboration
Leave comments on content entries for team discussion:
Add a Comment
curl -X POST http://localhost:2102/api/content/article/1/comments \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "body": "The intro paragraph needs a stronger hook." }'
Resolve a Comment
curl -X PUT http://localhost:2102/api/content/article/1/comments/5/resolve \
-H "Authorization: Bearer $TOKEN"
Entry Assignments
Assign content entries to team members:
curl -X POST http://localhost:2102/api/content/article/1/assignments \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "userId": 3, "role": "reviewer" }'
Источник: docs/guide/publishing.md. Снимок документации исходного проекта. Технический справочник сохраняет язык оригинала.