Loading Documentation Hub...
Scanning documentation library
Loading Documentation Hub...
Scanning documentation library
Documentation
📚 Documentation
Loading Documentation Hub...
Scanning documentation library
Scanning documentation library
Scanning documentation library
Scanning documentation library
Підготовка контенту платформи Ring
Підготовка контенту платформи Ring
Підготовка контенту платформи Ring
The Zemna.AI Scientific Editor is a Tiptap-based rich text editor built for academic writing. It includes LaTeX equation support, automatic saving, version history, and publication persistence via the Ring Platform database layer.
Status: Phase 2 (Sprints 2.1–2.3) complete. Figure/table support and export are planned for Sprints 2.4–2.5.
| Feature | Description |
|---|---|
| Rich text | Headings (H1–H6), bold, italic, underline, lists, block quotes, code blocks, tables, links, images |
| LaTeX | Inline and display math via KaTeX; equation modal with live preview and templates |
| Auto-save | 30-second debounced save; first save creates a publication, then updates via PUT |
| Version history | Snapshot and restore versions; list versions with timestamps and optional summaries |
| Publications | Content stored as Tiptap JSON; load by URL ?id=... or create new |
The Zemna.AI Scientific Editor is a Tiptap-based rich text editor built for academic writing. It includes LaTeX equation support, automatic saving, version history, and publication persistence via the Ring Platform database layer.
Status: Phase 2 (Sprints 2.1–2.3) complete. Figure/table support and export are planned for Sprints 2.4–2.5.
| Feature | Description |
|---|---|
| Rich text | Headings (H1–H6), bold, italic, underline, lists, block quotes, code blocks, tables, links, images |
| LaTeX | Inline and display math via KaTeX; equation modal with live preview and templates |
| Auto-save | 30-second debounced save; first save creates a publication, then updates via PUT |
| Version history | Snapshot and restore versions; list versions with timestamps and optional summaries |
| Publications | Content stored as Tiptap JSON; load by URL ?id=... or create new |
The Zemna.AI Scientific Editor is a Tiptap-based rich text editor built for academic writing. It includes LaTeX equation support, automatic saving, version history, and publication persistence via the Ring Platform database layer.
Status: Phase 2 (Sprints 2.1–2.3) complete. Figure/table support and export are planned for Sprints 2.4–2.5.
| Feature | Description |
|---|---|
| Rich text | Headings (H1–H6), bold, italic, underline, lists, block quotes, code blocks, tables, links, images |
| LaTeX | Inline and display math via KaTeX; equation modal with live preview and templates |
| Auto-save | 30-second debounced save; first save creates a publication, then updates via PUT |
| Version history | Snapshot and restore versions; list versions with timestamps and optional summaries |
| Publications | Content stored as Tiptap JSON; load by URL ?id=... or create new |
The editor uses Tiptap with StarterKit and extensions for scientific writing:
Content is stored as Tiptap JSON in the publication content field; the editor accepts initial content as either HTML string or JSON for loading saved publications.
Equations are stored as custom Tiptap nodes (mathBlock) with latex and display attributes.
The editor uses Tiptap with StarterKit and extensions for scientific writing:
Content is stored as Tiptap JSON in the publication content field; the editor accepts initial content as either HTML string or JSON for loading saved publications.
Equations are stored as custom Tiptap nodes (mathBlock) with latex and display attributes.
The editor uses Tiptap with StarterKit and extensions for scientific writing:
Content is stored as Tiptap JSON in the publication content field; the editor accepts initial content as either HTML string or JSON for loading saved publications.
Equations are stored as custom Tiptap nodes (mathBlock) with latex and display attributes.
?id= in URL; first Save or first auto-save creates a publication via POST /api/publications and sets the publication id for subsequent saves.?id=<publicationId>; the page loads the publication and sets title and content (JSON). Auto-save and manual Save use PUT /api/publications/:id.?id= in URL; first Save or first auto-save creates a publication via POST /api/publications and sets the publication id for subsequent saves.?id=<publicationId>; the page loads the publication and sets title and content (JSON). Auto-save and manual Save use PUT /api/publications/:id.?id= in URL; first Save or first auto-save creates a publication via POST /api/publications and sets the publication id for subsequent saves.?id=<publicationId>; the page loads the publication and sets title and content (JSON). Auto-save and manual Save use PUT /api/publications/:id.Publications and versions use the Ring Platform database abstraction (PostgreSQL with JSONB):
Publications and versions use the Ring Platform database abstraction (PostgreSQL with JSONB):
Publications and versions use the Ring Platform database abstraction (PostgreSQL with JSONB):
publications: id, data (JSONB), created_at, updated_at.data holds: user_id, title, content (Tiptap JSON), status, template_id.publication_versions: id, data (JSONB), created_at, updated_at.data holds: publication_id, version_number, content, change_summary, created_by.publications: id, data (JSONB), created_at, updated_at.data holds: user_id, title, content (Tiptap JSON), status, template_id.publication_versions: id, data (JSONB), created_at, updated_at.data holds: publication_id, version_number, content, change_summary, created_by.publications: id, data (JSONB), created_at, updated_at.data holds: user_id, title, content (Tiptap JSON), status, template_id.publication_versions: id, data (JSONB), created_at, updated_at.data holds: publication_id, version_number, content, change_summary, created_by.Schema is defined in data/schema.sql; the PostgreSQL adapter has fieldMappings for both collections.
Schema is defined in data/schema.sql; the PostgreSQL adapter has fieldMappings for both collections.
Schema is defined in data/schema.sql; the PostgreSQL adapter has fieldMappings for both collections.
sequenceDiagram
participant User
participant Editor
participant useAutoSave
participant API
participant DB
User->>Editor: Edit content / title
Editor->>useAutoSave: touch(publicationId, payload)
useAutoSave->>useAutoSave: Debounce 30s
Note over useAutoSave: Timer fires
useAutoSave->>API: POST /api/publications (new) or PUT /api/publications/:id
API->>DB: create() or update()
DB-->>API: publication
API-->>useAutoSave: 200 + publication
useAutoSave->>Editor: onFirstSave(id) if new
useAutoSave->>Editor: lastSaved updatedsequenceDiagram
participant User
participant Editor
participant useAutoSave
participant API
participant DB
User->>Editor: Edit content / title
Editor->>useAutoSave: touch(publicationId, payload)
useAutoSave->>useAutoSave: Debounce 30s
Note over useAutoSave: Timer fires
useAutoSave->>API: POST /api/publications (new) or PUT /api/publications/:id
API->>DB: create() or update()
DB-->>API: publication
API-->>useAutoSave: 200 + publication
useAutoSave->>Editor: onFirstSave(id) if new
useAutoSave->>Editor: lastSaved updatedsequenceDiagram
participant User
participant Editor
participant useAutoSave
participant API
participant DB
User->>Editor: Edit content / title
Editor->>useAutoSave: touch(publicationId, payload)
useAutoSave->>useAutoSave: Debounce 30s
Note over useAutoSave: Timer fires
useAutoSave->>API: POST /api/publications (new) or PUT /api/publications/:id
API->>DB: create() or update()
DB-->>API: publication
API-->>useAutoSave: 200 + publication
useAutoSave->>Editor: onFirstSave(id) if new
useAutoSave->>Editor: lastSaved updatedsequenceDiagram
participant User
participant Panel
participant API
participant DB
User->>Panel: Open Version History
Panel->>API: GET /api/publications/:id/versions
API->>DB: findByField(publication_versions, publication_id, id)
DB-->>API: versions[]
API-->>Panel: versions
User->>Panel: Restore version V
Panel->>API: POST /api/publications/:id/versions { action: 'restore', versionId: V }
API->>DB: updatePublication(id, content from V)
DB-->>API: publication
API-->>Panel: 200
Panel->>User: onRestore() → refetch publication, set editor contentsequenceDiagram
participant User
participant Panel
participant API
participant DB
User->>Panel: Open Version History
Panel->>API: GET /api/publications/:id/versions
API->>DB: findByField(publication_versions, publication_id, id)
DB-->>API: versions[]
API-->>Panel: versions
User->>Panel: Restore version V
Panel->>API: POST /api/publications/:id/versions { action: 'restore', versionId: V }
API->>DB: updatePublication(id, content from V)
DB-->>API: publication
API-->>Panel: 200
Panel->>User: onRestore() → refetch publication, set editor contentsequenceDiagram
participant User
participant Panel
participant API
participant DB
User->>Panel: Open Version History
Panel->>API: GET /api/publications/:id/versions
API->>DB: findByField(publication_versions, publication_id, id)
DB-->>API: versions[]
API-->>Panel: versions
User->>Panel: Restore version V
Panel->>API: POST /api/publications/:id/versions { action: 'restore', versionId: V }
API->>DB: updatePublication(id, content from V)
DB-->>API: publication
API-->>Panel: 200
Panel->>User: onRestore() → refetch publication, set editor content| Method | Path | Description |
|---|---|---|
| GET | /api/publications | List current user's publications |
| POST | /api/publications | Create publication (body: title, content, status, template_id) |
| GET | /api/publications/[id] | Get publication (ownership checked) |
| PUT | /api/publications/[id] | Update publication (ownership checked) |
| DELETE | /api/publications/[id] | Delete publication (ownership checked) |
| GET | /api/publications/[id]/versions | List versions for publication |
| POST | /api/publications/[id]/versions | Snapshot (action: snapshot) or restore (action: restore, versionId) |
| Method | Path | Description |
|---|---|---|
| GET | /api/publications | List current user's publications |
| POST | /api/publications | Create publication (body: title, content, status, template_id) |
| GET | /api/publications/[id] | Get publication (ownership checked) |
| PUT | /api/publications/[id] | Update publication (ownership checked) |
| DELETE | /api/publications/[id] | Delete publication (ownership checked) |
| GET | /api/publications/[id]/versions | List versions for publication |
| POST | /api/publications/[id]/versions | Snapshot (action: snapshot) or restore (action: restore, versionId) |
| Method | Path | Description |
|---|---|---|
| GET | /api/publications | List current user's publications |
| POST | /api/publications | Create publication (body: title, content, status, template_id) |
| GET | /api/publications/[id] | Get publication (ownership checked) |
| PUT | /api/publications/[id] | Update publication (ownership checked) |
| DELETE | /api/publications/[id] | Delete publication (ownership checked) |
| GET | /api/publications/[id]/versions | List versions for publication |
| POST | /api/publications/[id]/versions | Snapshot (action: snapshot) or restore (action: restore, versionId) |
All routes require authentication; ownership is enforced for get/update/delete and versions.
All routes require authentication; ownership is enforced for get/update/delete and versions.
All routes require authentication; ownership is enforced for get/update/delete and versions.
| Area | Path |
|---|---|
| Editor page | app/(authenticated)/[locale]/editor/page.tsx |
| Scientific editor | components/editor/scientific-editor.tsx |
| Toolbar | components/editor/editor-toolbar.tsx |
| LaTeX extension | components/editor/extensions/latex-extension.tsx |
| Equation modal | components/editor/equation-editor.tsx |
| Version history panel | components/editor/version-history-panel.tsx |
| Auto-save hook | hooks/use-auto-save.ts |
| Publication types | features/publications/types/index.ts |
| Publication service | features/publications/services/publication-service.ts |
| API routes | app/(public)/api/publications/ |
| Area | Path |
|---|---|
| Editor page | app/(authenticated)/[locale]/editor/page.tsx |
| Scientific editor | components/editor/scientific-editor.tsx |
| Toolbar | components/editor/editor-toolbar.tsx |
| LaTeX extension | components/editor/extensions/latex-extension.tsx |
| Equation modal | components/editor/equation-editor.tsx |
| Version history panel | components/editor/version-history-panel.tsx |
| Auto-save hook | hooks/use-auto-save.ts |
| Publication types | features/publications/types/index.ts |
| Publication service | features/publications/services/publication-service.ts |
| API routes | app/(public)/api/publications/ |
| Area | Path |
|---|---|
| Editor page | app/(authenticated)/[locale]/editor/page.tsx |
| Scientific editor | components/editor/scientific-editor.tsx |
| Toolbar | components/editor/editor-toolbar.tsx |
| LaTeX extension | components/editor/extensions/latex-extension.tsx |
| Equation modal | components/editor/equation-editor.tsx |
| Version history panel | components/editor/version-history-panel.tsx |
| Auto-save hook | hooks/use-auto-save.ts |
| Publication types | features/publications/types/index.ts |
| Publication service | features/publications/services/publication-service.ts |
| API routes | app/(public)/api/publications/ |
/editor (or /[locale]/editor). The editor loads with the default scientific template; publication id is set on first save./editor?id=<publicationId>. The page fetches the publication and sets the title and content (Tiptap JSON) in the editor.Restore does not delete versions; it updates the publication content and leaves the version history intact.
/editor (or /[locale]/editor). The editor loads with the default scientific template; publication id is set on first save./editor?id=<publicationId>. The page fetches the publication and sets the title and content (Tiptap JSON) in the editor.Restore does not delete versions; it updates the publication content and leaves the version history intact.
/editor (or /[locale]/editor). The editor loads with the default scientific template; publication id is set on first save./editor?id=<publicationId>. The page fetches the publication and sets the title and content (Tiptap JSON) in the editor.Restore does not delete versions; it updates the publication content and leaves the version history intact.
See Phase 2: Scientific Editor Enhancement for the full sprint breakdown.
| Schema |
data/schema.sql |
See Phase 2: Scientific Editor Enhancement for the full sprint breakdown.
| Schema |
data/schema.sql |
See Phase 2: Scientific Editor Enhancement for the full sprint breakdown.
| Schema |
data/schema.sql |