siyuan-note/siyuan · error

Conf.Language(386)

Error message

Conf.Language(386)

What it means

checkEncryptedImportFlashcards rejects importing a document into an encrypted notebook when the document contains flashcard attributes (custom-riff-decks IAL). Encrypted notebooks are isolated islands: flashcard decks and scheduling depend on the global database, so import must be refused. The message (i18n key 386) names the offending document title so the user can remove its flashcards in the source notebook.

Solutions

  1. Remove the flashcard attributes (custom-riff-decks IAL) from the document in the source notebook and re-export
  2. Import into a non-encrypted notebook instead
  3. Recreate the flashcards manually in the target notebook after import
Defensive patterns

Strategy: validation

Validate before calling

const hasFlashcards = (tree) => tree.blocks.some(b => b.attributes && b.attributes["custom-riff-decks"]);
if (targetNotebook.encrypted && hasFlashcards(parsedDoc)) {
  throw new Error(`Document "${parsedDoc.title}" contains flashcards and cannot be imported into an encrypted notebook`);
}

Type guard

const isEncryptedNotebook = (box) => typeof box === "object" && box !== null && box.encrypted === true;

Prevention

When it happens

Trigger: Calling importSY/ImportSYNotebookBundle with a .sy.zip whose target notebook is encrypted, while any block in the imported document tree carries a non-empty custom-riff-decks IAL attribute.

Common situations: User exports a notebook containing spaced-repetition flashcards and imports it into an encrypted notebook; also hit in tests TestCheckEncryptedImportFlashcards and via importSY0 during notebook bundle import.

Understand the failure class

Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.

Related errors


AI-assisted analysis of siyuan-note/siyuan@9f775e8a12 (2026-09-19). Data as JSON: /api/errors/23ba12f87525f395. Report an issue: GitHub.

Appendix: source

Thrown at kernel/model/import.go:338

	}

	containsFlashcardAttrs := false
	ast.Walk(tree.Root, func(n *ast.Node, entering bool) ast.WalkStatus {
		if entering && n.IsBlock() && n.IALAttr(NodeAttrRiffDecks) != "" {
			containsFlashcardAttrs = true
			return ast.WalkStop
		}
		return ast.WalkContinue
	})
	if !containsFlashcardAttrs {
		return nil
	}

	title := tree.Root.IALAttr("title")
	if "" == title {
		title = filepath.Base(sourcePath)
	}
	return errors.New(fmt.Sprintf(Conf.Language(386), htmlstd.EscapeString(title)))
}

// importedBlockDocTitles 建立本次导入块 ID 到所属文档标题的映射,供闪卡卡片反查文档。
func importedBlockDocTitles(trees map[string]*parse.Tree) map[string]string {
	ret := map[string]string{}
	for _, tree := range trees {
		if nil == tree || nil == tree.Root {
			continue
		}
		title := tree.Root.IALAttr("title")
		ast.Walk(tree.Root, func(n *ast.Node, entering bool) ast.WalkStatus {
			if entering && "" != n.ID {
				ret[n.ID] = title
			}
			return ast.WalkContinue
		})
	}
	return ret

View on GitHub (pinned to 9f775e8a12)