hcengineering/platform · error
No info for mark ${mark.type}
Error message
No info for mark ${mark.type} What it means
markString() resolves the open/close Markdown syntax for a mark from this.marks. When a mark has no explicit attrs.marker and no registered mark info, the serializer does not know how to translate it and throws. This guards against emitting Markdown with broken/missing emphasis formatting.
Source
Thrown at foundations/core/packages/text-markdown/src/serializer.ts:875
return wrap[0] + str + wrap[1]
}
// :: (string, number) → string
// Repeat the given string `n` times.
repeat (str: string, n: number): string {
let out = ''
for (let i = 0; i < n; i++) out += str
return out
}
// : (Mark, bool, string?) → string
// Get the markdown string for a given opening or closing mark.
markString (mark: MarkupMark, open: boolean, parent: MarkupNode, index: number): string {
let value = mark.attrs?.marker
if (value === undefined) {
const info = this.marks[mark.type]
if (info == null) {
throw new Error(`No info for mark ${mark.type}`)
}
value = open ? info.open : info.close
}
return typeof value === 'string' ? value : (value(this, mark, parent, index) ?? '')
}
}
function makeQuery (obj: Record<string, string | number | boolean | null | undefined>): string {
return Object.keys(obj)
.filter((it) => it[1] != null)
.map(function (k) {
return encodeURIComponent(k) + '=' + encodeURIComponent(obj[k] as string | number | boolean)
})
.join('&')
}
View on GitHub (pinned to 63e28dc964)
Solutions
- Register the mark in the serializer's marks table with open/close strings or functions
- Set an attrs.marker on the mark so markString can use it directly
- Strip unsupported marks from the document before serialization
Example fix
// before
marks: {} // 'highlight' mark missing
// after
marks: { highlight: { open: '==', close: '==' } } Defensive patterns
Strategy: validation
Validate before calling
for (const m of node.marks ?? []) {
if (!state.marks[m.type] && m.attrs?.marker === undefined) {
throw new Error(`mark ${m.type} has no markdown serialization`)
}
} Type guard
function hasMarkInfo(state: { marks: Record<string, unknown> }, mark: { type: string; attrs?: { marker?: string } }): boolean {
return mark.attrs?.marker !== undefined || state.marks[mark.type] != null
} Try / catch
try {
md = state.markString(mark, open, parent, index)
} catch (e) {
if (e.message.startsWith('No info for mark')) {
return '' // or strip the mark
}
throw e
} Prevention
- Register every mark type in your schema with the Markdown serializer
- Prefer explicit attrs.marker for simple string marks
- Test round-trip markdown conversion for all marks
When it happens
Trigger: Serializing a document containing a mark type (e.g. a custom annotation or link variant) that is not registered in the Markdown state's marks table and carries no marker attribute.
Common situations: Custom marks added by extensions, marks from pasted rich text, schema changes adding new mark types without Markdown serializer support.
Related errors
AI-assisted analysis of hcengineering/platform@63e28dc964 (2026-08-29).
Data as JSON: /api/errors/1f356ce4f7687d95.
Report an issue: GitHub.