{"record":{"id":"37624d1b4d412a39","repo":"siyuan-note/siyuan","slug":"assetpath-is-not-an-image-referenced-by-the-docume","errorCode":null,"errorMessage":"assetPath is not an image referenced by the document","messagePattern":"assetPath is not an image referenced by the document","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"kernel/model/assets.go","lineNumber":392,"sourceCode":"\t}\n\treturn DocumentImageList{DocumentID: bt.RootID, Images: refs}, nil\n}\n\n// PrepareDocumentImage 校验并读取文档实际引用的本地资源图片，供当前模型直接接收图片输入。\nfunc PrepareDocumentImage(documentID, assetPath string) (PreparedDocumentImage, error) {\n\tassetPath = strings.TrimSpace(assetPath)\n\tif assetPath == \"\" {\n\t\treturn PreparedDocumentImage{}, errors.New(\"assetPath is required for analyze\")\n\t}\n\tif !strings.HasPrefix(AssetPathWithoutQuery(assetPath), \"assets/\") {\n\t\treturn PreparedDocumentImage{}, errors.New(\"only local assets/... images are supported\")\n\t}\n\tbt, err := resolveMultimodalDocument(documentID)\n\tif err != nil {\n\t\treturn PreparedDocumentImage{}, err\n\t}\n\tif !documentReferencesImage(bt.RootID, assetPath) {\n\t\treturn PreparedDocumentImage{}, errors.New(\"assetPath is not an image referenced by the document\")\n\t}\n\tdata, err := ReadAssetBytesInBox(bt.BoxID, assetPath)\n\tif err != nil {\n\t\treturn PreparedDocumentImage{}, fmt.Errorf(\"read image failed: %w\", err)\n\t}\n\tprepared, err := util.PrepareModelImage(\n\t\tdata, documentImageMaxBytes, documentImageMaxPixels, documentImageMaxEdge,\n\t)\n\tif err != nil {\n\t\treturn PreparedDocumentImage{}, err\n\t}\n\treturn PreparedDocumentImage{\n\t\tArtifact: ImageArtifactRef{Kind: \"image\", Path: assetPath, DocumentID: bt.RootID},\n\t\tData:     prepared.Data,\n\t\tMIMEType: prepared.MIMEType,\n\t\tPrepared: prepared,\n\t}, nil\n}","sourceCodeStart":374,"sourceCodeEnd":410,"githubUrl":"https://github.com/siyuan-note/siyuan/blob/251596fc0de2f9528c00c224252fd073a99973f4/kernel/model/assets.go#L374-L410","documentation":"Returned by PrepareDocumentImage when documentReferencesImage(rootID, assetPath) is false — i.e. the AST of the resolved document does not contain a NodeImage whose link destination equals the requested asset. This is a security/integrity guard: it prevents a caller from reading arbitrary asset files by claiming they belong to a document.","triggerScenarios":"Calling PrepareDocumentImage with a valid-looking assets/... path that exists on disk but is not actually embedded in the document; using a path from a different document; passing a stale path after the image was removed from the doc; passing a path that differs only by query string from the embedded form.","commonSituations":"An AI tool cached an asset path from a previous doc version and the image was since deleted/replaced; a cross-document reference where the caller mixed up rootIDs; an attempt to exfiltrate an unrelated asset via the vision pipeline.","solutions":["Call ListDocumentImages(documentID) and pass only one of the returned ImageArtifactRef.Path values.","If the asset was renamed/moved, re-insert it into the document so the AST references it, then retry.","Do not construct asset paths by hand or copy them from another document."],"exampleFix":"// before — caller hardcodes a guessed path\nprepared, err := model.PrepareDocumentImage(docID, \"assets/guess.png\")\n\n// after — caller enumerates actually-referenced images first\nimgs, err := model.ListDocumentImages(docID)\nif err != nil { return err }\nif len(imgs.Images) == 0 { return errors.New(\"document has no images\") }\nprepared, err := model.PrepareDocumentImage(docID, imgs.Images[0].Path)","handlingStrategy":"validation","validationCode":"// Fetch the document's actual images and only accept paths from that set.\nimgs, err := model.ListDocumentImages(documentID)\nif err != nil { return err }\nallowed := make(map[string]struct{}, len(imgs.Images))\nfor _, ref := range imgs.Images {\n    allowed[model.AssetPathWithoutQuery(ref.Path)] = struct{}{}\n}\nif _, ok := allowed[model.AssetPathWithoutQuery(assetPath)]; !ok {\n    return errors.New(\"asset is not referenced by this document\")\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Treat the document AST as the single source of truth for which assets are referable.","Never hand-assemble asset paths; always derive them from ListDocumentImages.","Re-enumerate images after edits that add/remove images — paths change."],"tags":["validation","security","assets","authorization"],"backgroundTag":null,"analyzedSha":"251596fc0de2f9528c00c224252fd073a99973f4","analyzedAt":"2026-08-12T21:18:37.123Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}