Prose WIP

Prose is mymind's internal rich-text format. It is a structured JSON document based on the ProseMirror document model, and is served with the application/prose+json media type.

Work in progress

All APIs that accept and return content support Prose, but the schema below is still being filled in. Round-trip with caution until this page is complete.

When you receive it

Any endpoint that returns Content may return prose. You'll see it when content.type is application/prose+json, in which case content.body is a Prose document rather than a string.

For a lossy plain-text view of the same content, convert the prose to Markdown using the /convert endpoint.

Structure

A Prose document is a tree of nodes. Every node has a type and may have content (an array of child nodes), text (a leaf string), attrs (type-specific attributes), and marks (inline formatting like bold or links).

Example
{
  "type": "doc",
  "content": [
    {
      "type": "paragraph",
      "content": [
        { "type": "text", "text": "Hello, " },
        { "type": "text", "text": "world", "marks": [{ "type": "bold" }] },
        { "type": "text", "text": "." }
      ]
    }
  ]
}

Prose preserves features that have no Markdown equivalent — custom blocks and rich inline formatting — without losing information on round-trip.

Nodes

A Prose document is built from the following node types. text is the universal leaf — every node listed here is either a container of children or a self-closing block.

Type Attributes Description
doc — The root of every Prose document. Contains one or more block-level children.
paragraph — A run of inline content — text nodes and hardBreaks.
heading level A heading. level is an integer from 1 through 6.
bulletList — An unordered list. Wraps one or more listItem children.
orderedList — A numbered list. Wraps one or more listItem children.
listItem — A single entry inside a bulletList or orderedList.
taskList — A checklist. Wraps one or more taskItem children.
taskItem checked A single checkbox entry inside a taskList.
codeBlock language? A block of preformatted, monospaced code.
table — A table. Wraps one or more tableRow children.
tableRow — A row inside a table. Wraps one or more tableHeader or tableCell children.
tableHeader — A header cell — typically the first row of a table.
tableCell — A body cell inside a tableRow.
html — A block of raw HTML preserved verbatim through round-trips.
wikiLink text, target? An internal link to another object — text is the displayed label; target, when present, is the resolved object reference. Created by the [[Page Link]] Markdown extension.
image src?, alt?, title? A block-level image — it sits between blocks as a child of doc, never inside a paragraph. src is the image URL, alt is alternative text, title is the hover tooltip.
hardBreak — A forced line break inside a paragraph or heading.
horizontalRule — A horizontal divider between blocks.

Marks

Marks decorate ranges of text without breaking the underlying text node — bold, italic, links, and so on. A node carries an array of marks under its marks property.

Type Attributes Description
bold — Makes the text bold.
italic — Makes the text italic.
underline — Underlines the text.
strike — Strikes through the text.
code — Renders the text as inline monospaced code.
link href, title? Wraps the text in a hyperlink. title renders as the hover tooltip.
highlight — Highlights the text.
ins — Marks the text as inserted (e.g. tracked-change additions).
superscript — Raises the text as superscript.
subscript — Lowers the text as subscript.

Converting to and from other formats

Use the Convert endpoint to transform content between Prose, Markdown, and plain text. Set the source format on Content-Type and the target format on Accept.

Markdown → Prose
POST /convert
Content-Type: text/markdown
Accept: application/prose+json
Prose → Markdown
POST /convert
Content-Type: application/prose+json
Accept: text/markdown
Conversion may be lossy

Conversion can lose information in either direction whenever a feature isn't shared between the two formats. Going from Prose drops custom blocks and rich-formatting marks that have no Markdown or plain-text equivalent. Going to Prose drops Markdown constructs that don't map to a Prose node. To avoid data loss, use Prose directly.

See also