{"record":{"id":"f5dd40ded9cad7f2","repo":"ianstormtaylor/slate","slug":"cannot-get-the-leaf-node-at-path-path-because-f5dd40","errorCode":null,"errorMessage":"Cannot get the leaf node at path [${path}] because it refers to a non-leaf node: ${Scrubber.stringify(\n          node\n        )}","messagePattern":"Cannot get the leaf node at path \\[(.+?)\\] because it refers to a non-leaf node: (.+?)","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/slate/src/utils/modify.ts","lineNumber":91,"sourceCode":"        )\n      }\n\n      return { ...node, children: f(node.children) }\n    })\n  }\n}\n\n/**\n * Replace a leaf, replacing all ancestors\n */\nexport const modifyLeaf = (\n  root: Ancestor,\n  path: Path,\n  f: (leaf: Text) => Text\n) =>\n  modifyDescendant(root, path, node => {\n    if (!Node.isText(node)) {\n      throw new Error(\n        `Cannot get the leaf node at path [${path}] because it refers to a non-leaf node: ${Scrubber.stringify(\n          node\n        )}`\n      )\n    }\n\n    return f(node)\n  })\n","sourceCodeStart":73,"sourceCodeEnd":100,"githubUrl":"https://github.com/ianstormtaylor/slate/blob/72a37c701e5da4bb13a305d416d9c070d19d3a45/packages/slate/src/utils/modify.ts#L73-L100","documentation":"Mirror of the element case: modifyLeaf throws when the path resolves to a non-Text node (an Element) but a text leaf is required. Text-level operations like setting text properties or splitting text need an actual Text node at the path.","triggerScenarios":"Text-level transforms or manual modifyLeaf calls with a path pointing at an Element (e.g. [0] when intending [0, 0]); ops assuming a leaf exists where an element sits.","commonSituations":"Off-by-one path depth in custom text transforms; documents where an inline element occupies the expected leaf slot; deserialized documents with unexpected nesting.","solutions":["Verify Node.isText(Editor.node(editor, path)[0]) before text-level operations","Descend to the first text leaf with Editor.leaf(editor, path) or Node.first to get a valid leaf path","Adjust path computation to target the actual leaf (usually one level deeper)"],"exampleFix":"// before\nTransforms.setNodes(editor, { bold: true }, { at: [0] }) // [0] is an element\n\n// after\nconst entry = Editor.leaf(editor, [0]) // first text leaf\nTransforms.setNodes(editor, { bold: true }, { at: entry[1] })","handlingStrategy":"type-guard","validationCode":"const [leaf, leafPath] = Editor.leaf(editor, path)\nTransforms.setNodes(editor, { bold: true }, { at: leafPath })","typeGuard":"const isTextAt = (editor: Editor, p: Path): boolean =>\n  Text.isText(Editor.node(editor, p)[0])","tryCatchPattern":null,"preventionTips":["Use Editor.leaf to resolve an actual leaf path for text ops","Check Text.isText on the resolved node before text-level changes","Beware off-by-one depth when mixing element and text transforms"],"tags":["path","text-node","leaf","internal-utility","slate"],"backgroundTag":"wrong-node-type-at-path","analyzedSha":"72a37c701e5da4bb13a305d416d9c070d19d3a45","analyzedAt":"2026-08-27T23:04:51.145Z","schemaVersion":2},"datasetVersion":"2026-08-28T00:17:15.603Z"}