siyuan-note/siyuan · error
task list item marker can not be [ or ]
Error message
task list item marker can not be [ or ]
What it means
The single marker character cannot itself be '[' or ']'. Those characters are the checkbox delimiters in Markdown, so using them as the mark would produce ambiguous/unrenderable syntax like [[x]]; buildUpdatedTaskListItemBlockDOM rejects them explicitly.
Solutions
- Pass the semantic mark ('x', ' ', or another non-bracket character) instead of a character sliced from the raw DOM/Markdown text
- Parse the current state first (e.g. data-task / data-task-checked attributes or subtype) and toggle between 'x' and ' '
- Validate before the call: if (marker === '[' || marker === ']') reject the request
- Escape or sanitize user input used as a custom marker
Example fix
// before
const marker = rawText[1] === 'x' ? rawText[1] : rawText[0]; // may yield '[' or ']'
// after
const marker = isChecked ? 'x' : ' ';
if (marker === '[' || marker === ']') throw new Error('invalid marker'); Defensive patterns
Strategy: validation
Validate before calling
if (marker === '[' || marker === ']') {
throw new Error('marker cannot be a bracket; use x or space');
} Type guard
const isNonBracketMarker = (m) => m.length === 1 && !['[', ']'].includes(m);
Try / catch
try {
await fetchPost('/api/block/updateTaskListItemMarker', { id, marker });
} catch (e) {
if (String(e?.msg).includes('can not be [ or ]')) {
return fetchPost('/api/block/updateTaskListItemMarker', { id, marker: 'x' }); // fall back to default mark
}
throw e;
} Prevention
- Derive markers from semantic state (checked boolean), never from raw '[x]' text slices
- Whitelist allowed marks ('x', ' ') in your request helper
- Never index characters out of raw Markdown checkbox strings
When it happens
Trigger: Calling the marker update API with marker:'[' or marker:']' — typically from code that slices one character out of a raw "[x]" string at the wrong offset, or user-supplied input passed through unvalidated.
Common situations: String-parsing code doing marker = raw[0] on "[x]" yields '['; templating that substitutes a captured bracket; accidental passing of the literal bracket when toggling state.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
AI-assisted analysis of siyuan-note/siyuan@9f775e8a12 (2026-09-19).
Data as JSON: /api/errors/859d2e71d3ee0a67.
Report an issue: GitHub.
Appendix: source
Thrown at kernel/api/block_op.go:64
return "", errors.New("load tree failed: " + err.Error())
}
li := treenode.GetNodeInTree(tree, id)
if li == nil {
return "", errors.New("block not found")
}
if 3 != li.ListData.Typ {
return "", errors.New("block is not a task list item")
}
if 1 != len(marker) {
return "", errors.New("task list item marker length should be 1")
}
liMarker := marker[0]
if '[' == liMarker || ']' == liMarker {
return "", errors.New("task list item marker can not be [ or ]")
}
markerNode := li.ChildByType(ast.NodeTaskListItemMarker)
if nil == markerNode {
return "", errors.New("task list item marker not found")
}
markerNode.TaskListItemMarker = liMarker
markerNode.TaskListItemChecked = ' ' != markerNode.TaskListItemMarker
treenode.RefreshUpdated(li)
return luteEngine.RenderNodeBlockDOM(li), nil
}
var updateTaskListItemMarker = contractHandler(apicontract.UpdateTaskListItemMarker, func(c *gin.Context, request apicontract.TaskListMarkerRequest) apicontract.Response[[]*apicontract.BlockTransaction] {
ret := gulu.Ret.NewResult()
View on GitHub (pinned to 9f775e8a12)