API v1 · Resources
Notes
A note is a piece of raw content captured against a project — a
recording, a written snippet, an imported article, etc. Notes are the
input side of Scripe's content pipeline; turn one into a draft with
POST /v1/posts/generations
(source.type: "note"), and the resulting post lives in
posts.
The v1 API exposes the notes the authenticated workspace owns, scoped to a specific project, with date filters and cursor pagination. Notes attached to deleted projects are not returned.
A note may have at most one queue slot — the day on which it's scheduled for content production. The slot is included inline so you don't have to make a second call.
GET /v1/notes
List notes inside a project. projectId is required; everything else is
optional.
curl -i 'https://api.scripe.io/v1/notes?projectId=proj_01J9ZA…&limit=100' \
-H "Authorization: Bearer scripe_sk_live_…" \
-H "Scripe-Api-Version: 2026-08-10"Query parameters
| Name | Type | Required | Default | Notes |
|---|---|---|---|---|
projectId | string | yes | — | proj_* id. 404 if the project doesn't belong to the workspace. |
folderId | string | no | — | Filter to a single folder (UI grouping). Pass an empty value or omit to disable. |
dateFrom | string | no | — | YYYY-MM-DD. Filters by the note's queue-slot date. Inclusive. |
dateTo | string | no | — | YYYY-MM-DD. Inclusive. End-of-day in UTC. |
q | string | no | — | Free-text search over the note body (search / query are accepted aliases). Case- and accent-insensitive substring match; words AND-ed; "quoted phrase" matched whole; 200 chars / 6 terms max. Narrows the page — never re-ranks. |
limit | integer | no | 50 | 1…200. |
cursor | string | no | — | Opaque cursor from a previous response. |
dateFrom / dateTo filter on the queue slot's date, not on the
note's createdAt. A note without a slot is excluded from a date-filtered
result set; remove the date params to see notes that aren't yet
scheduled.
Response
HTTP/1.1 200 OK
Content-Type: application/json
{
"data": [
{
"id": "note_01J9ZA…",
"projectId": "proj_01J9ZA…",
"folderId": null,
"content": "Brain-dump from this morning's call …",
"createdAt": "2026-05-15T08:21:00.000Z",
"updatedAt": "2026-05-15T08:23:11.000Z",
"slot": {
"date": "2026-05-20T00:00:00.000Z",
"contentType": "PERSONAL"
}
}
],
"pagination": {
"next_cursor": "eyJjcmVhdGVkQXQiOiIyMDI2L…",
"has_more": true,
"total": 42
}
}pagination.total is how many notes the filters match across every
page — the one-request answer to "how many notes do I have"; see
Conventions § Counting without paging.
Semantics
Field types and nullability live in the OpenAPI reference tab
(Note). What that schema doesn't tell you:
contentis the raw user content. We do not redact PII or strip HTML — if you're rendering this somewhere user-facing, sanitize on your end. It may be empty for notes captured by audio first.folderIdis the internal id of the dashboard folder grouping, if any.slotis the queue slot, present only when the note is scheduled.slot.dateis the full ISO timestamp the note is queued for — thedateyou sent on create, or the creation time when you omit it, not a date-only value normalised to midnight.dateFrom/dateTofilter against it by day.slot.contentTypeis one ofPERSONAL,BUSINESS_INTERNAL,BUSINESS_EXTERNAL,EDUCATIONAL,UNKNOWN, ornullwhen the slot carries no classification — the enum is in the OpenAPI reference tab.
Pagination caveats
- Order is
(createdAt DESC, id DESC)— newest first. The cursor encodes that tuple. - Changing any filter (
projectId,folderId,dateFrom,dateTo,limit) mid-loop will likely emit400 bad_cursor. Restart the loop with the new filters.
GET /v1/notes/{noteId}
Single note read. Returns the same shape, wrapped in data.
curl -i https://api.scripe.io/v1/notes/note_01J9ZA… \
-H "Authorization: Bearer scripe_sk_live_…" \
-H "Scripe-Api-Version: 2026-08-10"Response
HTTP/1.1 200 OK
Content-Type: application/json
{
"data": {
"id": "note_01J9ZA…",
"projectId": "proj_01J9ZA…",
"folderId": null,
"content": "Brain-dump from this morning's call …",
"createdAt": "2026-05-15T08:21:00.000Z",
"updatedAt": "2026-05-15T08:23:11.000Z",
"slot": null
}
}Errors
| Status | Code |
|---|---|
| 400 | invalid_request, bad_cursor, bad_pagination |
| 401 | unauthenticated, invalid_token, key_revoked, key_expired |
| 403 | scope_missing (need notes:read) |
| 404 | not_found |
| 429 | rate_limited |
POST /v1/notes
Create a note + paired calendar slot. Required scope: notes:write.
curl -i https://api.scripe.io/v1/notes \
-X POST \
-H "Authorization: Bearer scripe_sk_live_…" \
-H "Scripe-Api-Version: 2026-08-10" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: a-unique-id-from-your-side" \
-d '{
"projectId": "proj_01J9ZA…",
"content": "Brain-dump from the standup",
"contentType": "PERSONAL"
}'Request body
| Field | Type | Required | Notes |
|---|---|---|---|
projectId | string (proj_*) | yes | Must belong to the workspace; otherwise 404 not_found. |
content | string | no | Up to 100,000 chars. Defaults to empty string. |
folderId | string | null | no | Internal folder id from the dashboard. Omit or null for the inbox. |
date | string (ISO 8601) | no | Slot placement. Defaults to "now". |
contentType | string | no | One of PERSONAL, BUSINESS_INTERNAL, BUSINESS_EXTERNAL, EDUCATIONAL, UNKNOWN. Defaults to PERSONAL. |
Both note writes (POST /v1/notes and PATCH /v1/notes/{noteId})
honour Idempotency-Key, and we strongly recommend setting it — see
idempotency.md. Replay within 24h returns the same
response with header Idempotent-Replayed: true.
Response
HTTP/1.1 200 OK
Content-Type: application/json
Idempotent-Replayed: false
{
"data": {
"id": "note_01J9ZA…",
"projectId": "proj_01J9ZA…",
"folderId": null,
"content": "Brain-dump from the standup",
"createdAt": "2026-05-15T08:21:00.000Z",
"updatedAt": "2026-05-15T08:21:00.000Z",
"slot": {
"date": "2026-05-15T08:21:00.000Z",
"contentType": "PERSONAL"
}
}
}Errors
| Status | Code |
|---|---|
| 400 | invalid_request (missing projectId) |
| 401 | unauthenticated, invalid_token, key_revoked, key_expired |
| 403 | scope_missing (need notes:write) |
| 404 | not_found (project not in workspace) |
| 409 | idempotency_key_conflict (same key, different body) |
| 413 | payload_too_large (content > 100KB) |
| 422 | unprocessable (bad shape, invalid contentType) |
| 429 | rate_limited |
PATCH /v1/notes/{noteId}
Update a note's body and/or move it between folders. Required scope:
notes:write. The note's calendar placement (its queue-slot date) is
not writable here.
curl -i https://api.scripe.io/v1/notes/note_01J9ZA… \
-X PATCH \
-H "Authorization: Bearer scripe_sk_live_…" \
-H "Scripe-Api-Version: 2026-08-10" \
-H "Content-Type: application/json" \
-d '{ "content": "Refined brain-dump" }'Request body
At least one field is required.
| Field | Type | Notes |
|---|---|---|
content | string | New body, up to 100,000 chars. Replaces the existing content. |
folderId | string | null | Move to a folder, or null for the root/inbox. Omit to leave unchanged. |
Response
The updated note in the same envelope as GET /v1/notes/{noteId}.
Errors
| Status | Code |
|---|---|
| 400 | invalid_request (neither content nor folderId present) |
| 401 | unauthenticated, invalid_token, key_revoked, key_expired |
| 403 | scope_missing (need notes:write) |
| 404 | not_found (note not in workspace) |
| 413 | payload_too_large (content > 100KB) |
| 422 | unprocessable (bad shape) |
| 429 | rate_limited |
Deleting notes
Note deletion is an MCP-only verb
(delete_note). Its default is the
reversible archive
(the note moves into the project's Archive folder, restorable from the
dashboard, notes:write); permanent: true removes the note and its
paired calendar slot forever — that path requires the
notes:destroy scope (never implied by notes:write or any alias)
and runs the two-phase confirmation. A REST DELETE route may follow
in a later phase.
What's NOT here (yet)
- Audio / transcript downloads. A note may have an attached recording; the v1 API doesn't expose the storage URLs. Use sources for the truncated transcript.
- Pinned / starred filters. Dashboard-only state, not exposed in v1.
- Search / full-text query. No
?q=parameter. Filter client-side for now. - Slot rescheduling. Moving a note's calendar date is a calendar
concern; neither
PATCH /v1/notes/{noteId}nor MCPupdate_notewrites it. - REST delete. Deletion is MCP-only for now (see above).