siyuan-note/siyuan · error

write notebook crypt backup failed: %w

Error message

write notebook crypt backup failed: %w

What it means

Returned by CreateEncryptedBox when writeNotebookCryptBackup fails to write the recovery backup of the wrapped DEK (BoxCrypt blob). The %w wraps the I/O error. This backup is critical for recovery if the main .syconf is lost; failure triggers cleanup of the half-created notebook.

Source

Thrown at kernel/model/crypto.go:2583

	}()

	enc, dek, err := WrapNewDEK(id, kek)
	if err != nil {
		return "", err
	}

	box := &Box{ID: id}
	boxConf := box.GetConf()
	boxConf.Encrypted = true
	boxConf.BoxCrypt = enc
	if err = encryptBoxMetadata(id, boxConf, dek); err != nil {
		return "", fmt.Errorf("encrypt notebook metadata failed: %w", err)
	}
	if err = box.SaveConf(boxConf); err != nil {
		return "", fmt.Errorf("save encrypted notebook conf failed: %w", err)
	}
	if err = writeNotebookCryptBackup(id, enc); err != nil {
		return "", fmt.Errorf("write notebook crypt backup failed: %w", err)
	}
	// 回读校验加密配置已落盘,避免写失败后按普通笔记本处理
	verifyConf := box.GetConf()
	if verifyConf == nil || !verifyConf.Encrypted || verifyConf.BoxCrypt == nil {
		err = errors.New("encrypted notebook metadata verification failed after write")
		return "", err
	}
	markRuntimeEncryptedBox(id)
	invalidateEncryptedPublishAccessCache()

	// 复用刚派生的 DEK 直接开 db + 缓存,省去再次 Argon2id 解锁
	cachedDEKsLock.Lock()
	if err = sql.OpenEncryptedDB(id, dek); err != nil {
		cachedDEKsLock.Unlock()
		return "", err
	}
	if err = treenode.OpenEncryptedBlockTreeDB(id, dek); err != nil {
		sql.CloseEncryptedDB(id)

View on GitHub (pinned to 251596fc0d)

Solutions

  1. Check disk space and permissions on the backup directory (typically under the workspace's crypto backup path).
  2. Ensure no other process holds a lock on the backup file location.
  3. Retry CreateEncryptedBox after resolving the I/O issue — the deferred cleanup will have removed the failed attempt.
Defensive patterns

Strategy: try-catch

Try / catch

id, err := model.CreateEncryptedBox(name, password)
if err != nil {
    if strings.Contains(err.Error(), "write notebook crypt backup failed") {
        // backup path I/O issue — check backup directory permissions/space
    }
    return err
}

Prevention

When it happens

Trigger: writeNotebookCryptBackup encounters a disk I/O error writing the backup file (separate from the main notebook conf). Same causes as SaveConf failure: disk full, permissions, read-only FS.

Common situations: The backup path is on a different volume or subdirectory that has different permissions. Disk ran out of space between writing .syconf and writing the backup. File-lock contention on the backup location.

Related errors


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