{"record":{"id":"a74cefc3dc8a0437","repo":"siyuan-note/siyuan","slug":"conf-language-313-a74cef","errorCode":null,"errorMessage":"Conf.Language(313)","messagePattern":"Conf\\.Language\\(313\\)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"kernel/model/heading.go","lineNumber":218,"sourceCode":"\t\t\tlogging.LogWarnf(\"remove empty dir [%s] failed: %s\", subDir, removeErr)\n\t\t}\n\t}\n\n\tif nil == treenode.GetBlockTree(targetID) {\n\t\t// 目标块不存在时忽略处理\n\t\treturn\n\t}\n\n\ttargetTree, _ := LoadTreeByBlockID(targetID)\n\tif nil == targetTree {\n\t\t// 目标块不存在时忽略处理\n\t\treturn\n\t}\n\n\t// 禁止跨加密边界：Doc2Heading 会合并 srcTree 和 targetTree 的内容，\n\t// 不同加密笔记本各有独立 DEK，跨边界合并会导致密文用错 DEK 损坏数据\n\tif !IsSameCryptoBoundary(srcTree.Box, targetTree.Box) {\n\t\terr = errors.New(Conf.Language(313))\n\t\treturn\n\t}\n\n\tpivot := treenode.GetNodeInTree(targetTree, targetID)\n\tif nil == pivot {\n\t\terr = ErrBlockNotFound\n\t\treturn\n\t}\n\n\t// 生成文档历史 https://github.com/siyuan-note/siyuan/issues/14359\n\tgenerateOpTypeHistory(srcTree, HistoryOpUpdate)\n\n\t// 移动前先删除引用 https://github.com/siyuan-note/siyuan/issues/7819\n\tsql.DeleteRefsTreeQueue(srcTree)\n\tsql.DeleteRefsTreeQueue(targetTree)\n\n\tif ast.NodeListItem == pivot.Type {\n\t\tpivot = pivot.LastChild","sourceCodeStart":200,"sourceCodeEnd":236,"githubUrl":"https://github.com/siyuan-note/siyuan/blob/8641553a1f07374001902d3ce773285db1292b2d/kernel/model/heading.go#L200-L236","documentation":"Doc2Heading merges content of the source tree into a tree in another notebook. For encrypted notebooks each notebook has its own DEK (data encryption key); merging across two different notebooks would write content encrypted under the wrong key and corrupt data. The kernel therefore rejects any src/target pair that is not within the same crypto boundary with Conf.Language(313) ('Encrypted notebooks do not support this operation').","triggerScenarios":"Calling Doc2Heading where srcTree.Box and targetTree.Box are different notebooks and at least one (or the pair) crosses an encrypted-notebook boundary, i.e. IsSameCryptoBoundary(srcBox, targetBox) is false.","commonSituations":"Drag-dropping a doc from an encrypted notebook onto a heading in a normal notebook (or between two different encrypted notebooks); automation that moves docs between notebooks.","solutions":["Move the document within the same notebook, or convert to heading only when both source and target are in the same notebook","Decrypt (remove encryption from) the notebooks involved if cross-notebook merging is genuinely needed","Create a copy of content manually instead of using the merge transaction"],"exampleFix":null,"handlingStrategy":"validation","validationCode":"const boxes = new Set([srcBoxID, targetBoxID]);\n// only merge within the same notebook (or same crypto boundary)\nif (srcBoxID !== targetBoxID) throw new Error('cross-notebook merge not allowed for encrypted notebooks');","typeGuard":null,"tryCatchPattern":"try {\n  await fetchPost('/api/filetree/doc2Heading', {srcID, targetID});\n} catch (e) {\n  if (String(e.msg).includes('do not support this operation')) {\n    // fall back to moving the document instead of merging\n  } else throw e;\n}","preventionTips":["Restrict doc2Heading UI actions to same-notebook targets","Never assume encrypted and plain notebooks are interchangeable for merge operations","Check IsSameCryptoBoundary-equivalent conditions (same notebook) client-side"],"tags":["encrypted-notebook","crypto-boundary","document-structure"],"backgroundTag":"unsupported-operation","analyzedSha":"8641553a1f07374001902d3ce773285db1292b2d","analyzedAt":"2026-09-11T16:08:28.414Z","contentChangedAt":"2026-09-11T16:08:28.414Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}