Files
simplenote-web/api-spec.yaml
Bulma 90e4dd0807 feat(architecture): add complete technical architecture for SimpleNote
- ARCHITECTURE.md: main architecture document
- api-spec.yaml: full OpenAPI 3.0 spec
- folder-structure.md: detailed folder layout
- data-format.md: JSON schemas for .meta.json, .library.json, .tag-index.json
- env-template.md: environment variables documentation
- cli-protocol.md: CLI-to-API communication protocol
2026-03-28 03:18:25 +00:00

878 lines
24 KiB
YAML

openapi: 3.0.3
info:
title: SimpleNote API
description: REST API for SimpleNote document management system
version: 1.0.0
contact:
name: SimpleNote Team
servers:
- url: http://localhost:3000/api/v1
description: Local development server
tags:
- name: Auth
description: Authentication and token management
- name: Documents
description: Document CRUD operations
- name: Libraries
description: Library (folder) management
- name: Tags
description: Tag-based search and management
paths:
# ============ AUTH ============
/auth/token:
post:
tags: [Auth]
summary: Generate a new API token
description: Admin-only endpoint to generate a new bearer token
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [label]
properties:
label:
type: string
description: Human-readable label for the token
example: "cli-default"
responses:
'200':
description: Token generated successfully
content:
application/json:
schema:
type: object
properties:
token:
type: string
example: "snk_a1b2c3d4e5f6..."
label:
type: string
example: "cli-default"
createdAt:
type: string
format: date-time
'401':
description: Unauthorized - invalid admin token
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'400':
description: Missing required fields
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/auth/verify:
get:
tags: [Auth]
summary: Verify current token is valid
security:
- BearerAuth: []
responses:
'200':
description: Token is valid
content:
application/json:
schema:
type: object
properties:
valid:
type: boolean
example: true
token:
type: string
example: "snk_a1b2c3d4e5f6..."
'401':
description: Token is invalid or missing
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
# ============ DOCUMENTS ============
/documents:
get:
tags: [Documents]
summary: List all documents
security:
- BearerAuth: []
parameters:
- name: tag
in: query
description: Filter by tag
schema:
type: string
example: "backend"
- name: library
in: query
description: Filter by library ID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440000"
- name: type
in: query
description: Filter by document type
schema:
type: string
enum: [requirement, note, spec, general]
example: "requirement"
- name: status
in: query
description: Filter by status
schema:
type: string
enum: [draft, approved, implemented]
example: "draft"
- name: limit
in: query
description: Max results to return
schema:
type: integer
default: 50
example: 20
- name: offset
in: query
description: Skip first N results
schema:
type: integer
default: 0
example: 0
responses:
'200':
description: List of documents
content:
application/json:
schema:
type: object
properties:
documents:
type: array
items:
$ref: '#/components/schemas/Document'
total:
type: integer
example: 42
limit:
type: integer
example: 20
offset:
type: integer
example: 0
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
post:
tags: [Documents]
summary: Create a new document
security:
- BearerAuth: []
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [title, libraryId]
properties:
title:
type: string
description: Document title
example: "API Authentication Design"
libraryId:
type: string
description: Target library ID
example: "550e8400-e29b-41d4-a716-446655440000"
content:
type: string
description: Markdown content (optional, defaults to template)
example: "# API Authentication\n\n## Description\n..."
tags:
type: array
items:
type: string
example: ["backend", "api", "auth"]
type:
type: string
enum: [requirement, note, spec, general]
default: general
priority:
type: string
enum: [high, medium, low]
default: medium
status:
type: string
enum: [draft, approved, implemented]
default: draft
responses:
'201':
description: Document created
content:
application/json:
schema:
$ref: '#/components/schemas/Document'
'400':
description: Invalid request body
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Library not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/documents/{id}:
get:
tags: [Documents]
summary: Get a document by ID
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Document UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440001"
responses:
'200':
description: Document found
content:
application/json:
schema:
$ref: '#/components/schemas/Document'
'404':
description: Document not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
put:
tags: [Documents]
summary: Update a document
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Document UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440001"
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
title:
type: string
example: "Updated Title"
content:
type: string
example: "# Updated Content\n\nNew markdown..."
tags:
type: array
items:
type: string
example: ["backend", "api"]
type:
type: string
enum: [requirement, note, spec, general]
priority:
type: string
enum: [high, medium, low]
status:
type: string
enum: [draft, approved, implemented]
responses:
'200':
description: Document updated
content:
application/json:
schema:
$ref: '#/components/schemas/Document'
'400':
description: Invalid request body
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Document not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
delete:
tags: [Documents]
summary: Delete a document
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Document UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440001"
responses:
'200':
description: Document deleted
content:
application/json:
schema:
type: object
properties:
deleted:
type: boolean
example: true
id:
type: string
example: "550e8400-e29b-41d4-a716-446655440001"
'404':
description: Document not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/documents/{id}/export:
get:
tags: [Documents]
summary: Export document as raw Markdown
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Document UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440001"
responses:
'200':
description: Raw Markdown file
content:
text/markdown:
schema:
type: string
example: |
---
id: REQ-001
title: API Authentication
---
# API Authentication
## Description
...
'404':
description: Document not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/documents/{id}/tags:
post:
tags: [Tags]
summary: Add tags to a document
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Document UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440001"
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [tags]
properties:
tags:
type: array
items:
type: string
example: ["new-tag", "another-tag"]
responses:
'200':
description: Tags added
content:
application/json:
schema:
$ref: '#/components/schemas/Document'
'400':
description: Invalid tags array
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Document not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
# ============ LIBRARIES ============
/libraries:
get:
tags: [Libraries]
summary: List root-level libraries
security:
- BearerAuth: []
responses:
'200':
description: List of root libraries
content:
application/json:
schema:
type: object
properties:
libraries:
type: array
items:
$ref: '#/components/schemas/Library'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
post:
tags: [Libraries]
summary: Create a new library
security:
- BearerAuth: []
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [name]
properties:
name:
type: string
description: Library name
example: "Backend Requirements"
parentId:
type: string
nullable: true
description: Parent library ID for nesting (null for root)
example: "550e8400-e29b-41d4-a716-446655440000"
responses:
'201':
description: Library created
content:
application/json:
schema:
$ref: '#/components/schemas/Library'
'400':
description: Invalid request body
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: Parent library not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/libraries/{id}:
get:
tags: [Libraries]
summary: Get library contents (documents and sub-libraries)
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Library UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440000"
responses:
'200':
description: Library contents
content:
application/json:
schema:
type: object
properties:
library:
$ref: '#/components/schemas/Library'
documents:
type: array
items:
$ref: '#/components/schemas/Document'
subLibraries:
type: array
items:
$ref: '#/components/schemas/Library'
'404':
description: Library not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/libraries/{id}/tree:
get:
tags: [Libraries]
summary: Get full subtree of a library
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Library UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440000"
responses:
'200':
description: Full library tree
content:
application/json:
schema:
$ref: '#/components/schemas/LibraryTree'
'404':
description: Library not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/libraries/{id}/documents:
get:
tags: [Documents]
summary: List documents in a specific library
security:
- BearerAuth: []
parameters:
- name: id
in: path
required: true
description: Library UUID
schema:
type: string
example: "550e8400-e29b-41d4-a716-446655440000"
responses:
'200':
description: List of documents in library
content:
application/json:
schema:
type: object
properties:
libraryId:
type: string
documents:
type: array
items:
$ref: '#/components/schemas/Document'
'404':
description: Library not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
# ============ TAGS ============
/tags:
get:
tags: [Tags]
summary: List all tags with document counts
security:
- BearerAuth: []
responses:
'200':
description: All tags with counts
content:
application/json:
schema:
type: object
properties:
tags:
type: array
items:
type: object
properties:
name:
type: string
example: "backend"
count:
type: integer
example: 5
total:
type: integer
example: 15
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
/tags/{tag}:
get:
tags: [Tags]
summary: Get all documents with a specific tag
security:
- BearerAuth: []
parameters:
- name: tag
in: path
required: true
description: Tag name
schema:
type: string
example: "backend"
responses:
'200':
description: Documents with tag
content:
application/json:
schema:
type: object
properties:
tag:
type: string
example: "backend"
documents:
type: array
items:
$ref: '#/components/schemas/Document'
count:
type: integer
example: 5
'404':
description: Tag not found
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Unauthorized
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
components:
securitySchemes:
BearerAuth:
type: http
scheme: bearer
bearerFormat: JWT
description: API token with `snk_` prefix
schemas:
Error:
type: object
properties:
error:
type: string
example: "Document not found"
code:
type: string
example: "NOT_FOUND"
Document:
type: object
properties:
id:
type: string
format: uuid
example: "550e8400-e29b-41d4-a716-446655440001"
title:
type: string
example: "API Authentication Design"
path:
type: string
example: "/libraries/550e8400/.../documents/550e8401/index.md"
content:
type: string
description: Raw markdown content
example: "# API Authentication\n\n## Description\n..."
tags:
type: array
items:
type: string
example: ["backend", "api", "auth"]
type:
type: string
enum: [requirement, note, spec, general]
example: "requirement"
status:
type: string
enum: [draft, approved, implemented]
example: "draft"
priority:
type: string
enum: [high, medium, low]
example: "high"
libraryId:
type: string
format: uuid
example: "550e8400-e29b-41d4-a716-446655440000"
createdBy:
type: string
description: Agent or user ID who created the document
example: "agent-001"
createdAt:
type: string
format: date-time
example: "2026-03-28T10:00:00Z"
updatedAt:
type: string
format: date-time
example: "2026-03-28T12:30:00Z"
Library:
type: object
properties:
id:
type: string
format: uuid
example: "550e8400-e29b-41d4-a716-446655440000"
name:
type: string
example: "Backend Requirements"
parentId:
type: string
nullable: true
format: uuid
description: Parent library ID, null for root
example: null
path:
type: string
description: Absolute path to library folder
example: "/data/libraries/550e8400"
documentCount:
type: integer
description: Total documents in this library (excludes sub-libraries)
example: 12
createdAt:
type: string
format: date-time
example: "2026-03-28T09:00:00Z"
updatedAt:
type: string
format: date-time
example: "2026-03-28T09:00:00Z"
LibraryTree:
type: object
properties:
id:
type: string
format: uuid
name:
type: string
documents:
type: array
items:
type: object
properties:
id:
type: string
title:
type: string
subLibraries:
type: array
items:
$ref: '#/components/schemas/LibraryTree'