siyuan-note/siyuan · error

incompatible encrypted index

Error message

incompatible encrypted index

What it means

This is the deliberate compatibility gate. The stored metadata row's kind, schema_version, and cipher_settings fingerprint are compared against the values the current build computes; any mismatch means the index was produced by a different format version or different SQLCipher parameters (page size, KDF iterations, HMAC algorithm), and the library refuses to open or rewrite it, preserving the original data rather than risking misinterpretation.

Source

Thrown at kernel/util/encrypted_index.go:62

		if _, err = db.Exec("CREATE TABLE encrypted_index_meta (kind TEXT NOT NULL, schema_version INTEGER NOT NULL, cipher_settings TEXT NOT NULL)"); err != nil {
			return err
		}
		_, err = db.Exec("INSERT INTO encrypted_index_meta VALUES (?, ?, ?)", kind, schema, string(encoded))
		return err
	}
	var storedKind, storedSettings string
	var storedSchema, rows int
	if err = db.QueryRow("SELECT count(*) FROM encrypted_index_meta").Scan(&rows); err != nil {
		return err
	}
	if rows != 1 {
		return errors.New("invalid encrypted index compatibility metadata")
	}
	if err = db.QueryRow("SELECT kind, schema_version, cipher_settings FROM encrypted_index_meta").Scan(&storedKind, &storedSchema, &storedSettings); err != nil {
		return err
	}
	if storedKind != kind || storedSchema != schema || storedSettings != string(encoded) {
		return errors.New("incompatible encrypted index")
	}
	return nil
}

View on GitHub (pinned to 8641553a1f)

Solutions

  1. Use the kernel version recorded in the index's schema_version — check the release notes / docs/ENCRYPTED-NOTEBOOK.md for the compatible version and run that first so it can migrate
  2. Do not edit encrypted_index_meta or regenerate cipher salts to force a match; instead rebuild the derived index from the source documents, which are unaffected
  3. If a deliberate cipher-parameter change is required, follow the documented format-version migration, which authenticates the source and preserves recovery material
Defensive patterns

Strategy: try-catch

Validate before calling

var stored string
if err := db.QueryRow("SELECT cipher_settings FROM encrypted_index_meta").Scan(&stored); err == nil {
    log.Printf("index built with settings: %s", stored)
}

Try / catch

if err := CheckEncryptedIndexCompatibility(db, kind, schema); err != nil {
    if strings.Contains(err.Error(), "incompatible encrypted index") {
        return fmt.Errorf("open with the creating kernel version or rebuild the index; err: %w", err)
    }
    return err
}

Prevention

When it happens

Trigger: Opening an encrypted index created with a different cipher configuration (e.g. different cipher_page_size/kdf_iter) or a different schema_version/kind than the running kernel expects — returned after CheckEncryptedIndexCompatibility reads the single metadata row.

Common situations: Rolling back to an older SiYuan version after the index schema advanced; changing SQLCipher defaults between releases; restoring an index file into a workspace configured with different encryption parameters.

Related errors


AI-assisted analysis of siyuan-note/siyuan@8641553a1f (2026-09-11). Data as JSON: /api/errors/3ec58dd5f21cec54. Report an issue: GitHub.