siyuan-note/siyuan · error · obsidianUserError

read referenced attachment [%s]: %w

Error message

read referenced attachment [%s]: %w

What it means

Wrapped error returned during asset validation in the analysis phase when a referenced (wiki-linked or embedded) attachment file cannot be read. validateObsidianReadableFile tries to open and read one byte from the file and re-validates its metadata; on failure, if the asset is referenced by at least one note, the error is wrapped via newObsidianUserError with i18n detail key 348 and the asset's relative path. Unreferenced unreadable assets are merely warned about, not fatal.

Source

Thrown at kernel/model/import_obsidian.go:541

	progress(35, "Analyzing Markdown syntax")
	if err = analyzeObsidianDocuments(ctx, ret, progress); err != nil {
		return nil, err
	}
	ret.Analysis.MarkdownCount = countObsidianSourceDocs(ret.Docs)
	var assetKeys []string
	for key := range ret.Assets {
		assetKeys = append(assetKeys, key)
	}
	sort.Strings(assetKeys)
	for _, key := range assetKeys {
		if err = ctx.Err(); err != nil {
			return nil, err
		}
		asset := ret.Assets[key]
		if err = validateObsidianReadableFile(asset.Source); err != nil {
			if ret.ReferencedAssets[key] != nil {
				return nil, newObsidianUserError(348, asset.Source.RelPath,
					fmt.Errorf("read referenced attachment [%s]: %w", asset.Source.RelPath, err))
			}
			ret.Analysis.Warnings = append(ret.Analysis.Warnings, asset.Source.RelPath)
			continue
		}
		ret.ImportAssets[key] = asset
		ret.Analysis.ImportableAssetCount++
		ret.Analysis.ImportableAssetSize += asset.Source.Size
	}
	ret.Analysis.UnreferencedFileCount = len(ret.ImportAssets) - len(ret.ReferencedAssets)
	if ret.Analysis.UnreferencedFileCount < 0 {
		ret.Analysis.UnreferencedFileCount = 0
	}
	progress(100, "Analysis completed")
	return ret, nil
}

func validateObsidianVaultRoot(localPath string) (string, error) {
	if strings.TrimSpace(localPath) == "" {

View on GitHub (pinned to 251596fc0d)

Solutions

  1. Ensure all referenced attachments are present and readable at the time of analysis; fix or remove broken wiki-link/embed references in the source notes.
  2. Pause cloud-sync and close Obsidian before analyzing to prevent mid-scan file changes.
  3. Check the asset path named in the error — restore the file or update the note's link to point at the correct location.
  4. If the asset is genuinely optional, remove the reference from the note so it falls into the unreferenced (warn-only) path.

Example fix

// before: note references [[attachment.png]] which is missing/unreadable
// analysis -> newObsidianUserError(348, relPath, "read referenced attachment [x]: ...")

// after: restore the file or remove the reference
// either: place attachment.png back in the vault
// or:   edit the note to remove the broken ![[attachment.png]] embed
Defensive patterns

Strategy: validation

Validate before calling

// Pre-check that referenced attachments are readable
func referencedAssetReadable(absPath string) error {
    f, err := os.Open(absPath)
    if err != nil { return err }
    defer f.Close()
    buf := make([]byte, 1)
    if _, err := f.Read(buf); err != nil && !errors.Is(err, io.EOF) { return err }
    return nil
}

Try / catch

if _, err := analyzeVault(ctx, localPath); err != nil {
    var ue *obsidianUserError
    if errors.As(err, &ue) && strings.Contains(err.Error(), "read referenced attachment") {
        return fmt.Errorf("a referenced attachment (%s) could not be read; restore it or fix the link", ue.RelPath)
    }
}

Prevention

When it happens

Trigger: During analyzeObsidianVault's asset-collection loop (line 533-543), a ReferencedAssets entry fails validateObsidianReadableFile — the file cannot be opened, read, or its size/mtime no longer matches the scan snapshot. Because at least one note references it, the analysis fails with this wrapped error rather than skipping it.

Common situations: An attachment referenced by a wiki link was deleted or moved between scan and validation; the file is locked or permission-denied on read; the file is on a network path that became unavailable; the file's size/mtime changed mid-analysis (sync client writing); a referenced asset is a broken symlink.

Related errors


AI-assisted analysis of siyuan-note/siyuan@251596fc0d (2026-08-12). Data as JSON: /api/errors/6522fb9cf1084f56. Report an issue: GitHub.