Repository navigation
fix(notes): ignore todo-looking lines inside fenced code blocks - #69
Conversation
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
rociiu
left a comment
There was a problem hiding this comment.
A single line starting with three backticks disables every todo below it.
fencedLines treats any line that starts with ``` or ~~~ as opening or closing a fence. The preview (remark, CommonMark) is stricter, so the two can disagree. For example:
```npm install```
- [ ] real todoTo the preview, the first line is a paragraph with inline code, because a backtick fence's info string can't contain backticks. So - [ ] real todo renders as a clickable checkbox. fencedLines instead treats that line as an opening fence, so every todo after it:
- drops out of the
taskStats"x of y done" count; - does nothing when clicked in the preview, because
toggleTaskLinereturns the text unchanged.
On main those todos work, so this is a regression. The highlighter has the same loose rule (WriterEditor.tsx:73, :232), but there it only affected colors.
Other cases where the two disagree:
- A line indented 4+ spaces (` ```) is indented code, not a fence.
- A
~~~line inside a block opened with backticks (or the reverse) doesn't close it. - A closing fence must use the same character, be at least as long as the opener, and have nothing after it but spaces. So
```jsinside an open block is content.
Suggested fix: open a fence only on ^ {0,3}({3,}|~{3,})`, where a backtick fence's remaining text contains no backticks. Close it only on the same character, at least as long, followed by nothing but spaces. Please add a test with the inline ```code``` line followed by a todo.
rociiu
left a comment
There was a problem hiding this comment.
Review notes. The main concern: the new fence detection doesn't match CommonMark, which is what the preview (react-markdown) renders. When the two disagree, real todos outside code blocks stop counting and can't be toggled from the preview. That's a regression from main.
Two more points outside the diff lines:
- The editor's own toggle paths skip the fence check (
toggleTaskAt, used by Cmd+Enter, clicking[ ], andtoggleTaskAtCursor). They still use plainTASK_RE, so Cmd+Enter on- [ ] exampleinside a ``` block flips it to[x]and edits the code example, even though the counter and preview say it isn't a todo. - Duplicated fence logic. The highlighter still has its own
/^\s*(```|~~~)/inhighlightLineand in the render loop, each with its own toggle. Once the matching rules are fixed, the render loop should usefencedLines(lines)/FENCE_REso the highlighter, counter and toggle agree.
There was a problem hiding this comment.
This flips state on any ``` or ~~~ line. In CommonMark a fence closes only on the same character with at least the same length as the opener.
Example: a note documenting Markdown uses a ````md (or ~~~) block containing a example. The inner closes the block early, and the real closing fence then opens a new one. Every real - [ ] below it drops out of `taskStats`, and clicking its checkbox in the preview does nothing, because `toggleTaskLine` returns the text unchanged.
Suggestion: remember the opening fence's character and length, and close only on a line of the same character that is at least as long and has nothing else on it.
| }; | ||
|
|
||
| const TASK_RE = /^(\s*(?:[-*+]|\d+[.)])\s+)\[([ xX])\](\s|$)/; | ||
| const FENCE_RE = /^\s*(```|~~~)/; |
There was a problem hiding this comment.
This also matches lines CommonMark does not treat as fences:
- lines indented 4+ spaces (indented code)
- a backtick fence whose info string contains a backtick, e.g.
```npm i```on its own line, which is inline code
Either one opens a phantom fence, and every todo after it in the note stops counting or toggling. Something like /^ {0,3}({3,}|~{3,})/` plus a no-backticks-in-info check for backtick fences would match the renderer.

Problem: the notes todo counter (
taskStats, shown on the note list and in the editor) andtoggleTaskLinetreat any line that looks like- [ ] textas a todo, even inside a fenced code block. A note that documents Markdown with an example in a code fence gets inflated "x of y done" counts for items the preview renders as plain code and that cannot be checked.Fix: track fenced blocks the same way the editor's highlighter already does (a line starting with three backticks or tildes toggles the fence) and skip those lines in both functions. Todos outside fences behave as before.
Test: new
apps/web/test/writer-tasks.test.ts; both cases fail on main and pass now. Web suite,tsc --noEmit -p apps/webandbiome lint apps/webpass.