siyuan-note/siyuan · error
write notebook crypto backup failed: %w
Error message
write notebook crypto backup failed: %w
What it means
saveNotebookCryptoBackup writes the JSON backup with atomicWriteFile after creating the directory; this error wraps a failed atomic write. The backup file (e.g. at the data crypto backup path) could not be written, so the on-disk recovery copy is missing or stale even though Conf in memory was already updated. Encrypted-notebook recovery depends on this file, so it should be resolved immediately.
Source
Thrown at kernel/model/crypto.go:407
Conf.m.Unlock()
return errors.New("cannot save incomplete notebook crypto configuration")
}
Conf.NotebookCrypto.Spec = nc.Spec
Conf.NotebookCrypto.BackupID = nc.BackupID
Conf.NotebookCrypto.CreatedAt = nc.CreatedAt
Conf.NotebookCrypto.Checksum = nc.Checksum
Conf.NotebookCrypto.KEKMAC = nc.KEKMAC // 保持 Conf 与备份文件的 KEKMAC 一致
Conf.m.Unlock()
backupPath := dataCryptoBackupPath()
if err := os.MkdirAll(filepath.Dir(backupPath), 0755); err != nil {
return fmt.Errorf("mkdir notebook crypto backup dir failed: %w", err)
}
data, err := json.Marshal(nc)
if err != nil {
return fmt.Errorf("marshal notebook crypto backup failed: %w", err)
}
if err := atomicWriteFile(backupPath, data); err != nil {
return fmt.Errorf("write notebook crypto backup failed: %w", err)
}
return nil
}
// writeNotebookCryptoBackupData 将指定的 NotebookCrypto 写入备份文件(不依赖 Conf.NotebookCrypto)。
// kek 必须非 nil:在 Checksum 定型后计算 KEKMAC,保证落盘 MAC 与落盘内容一致。
func writeNotebookCryptoBackupData(nc *conf.NotebookCrypto, kek []byte) error {
if kek == nil {
return errors.New("cannot generate notebook crypto backup without KEK")
}
prepareBackupForWrite(nc)
nc.KEKMAC = computeKEKMAC(nc, kek)
if !notebookCryptoConfigurationComplete(nc) {
return errors.New("cannot write incomplete notebook crypto backup")
}
backupPath := dataCryptoBackupPath()
if err := os.MkdirAll(filepath.Dir(backupPath), 0755); err != nil {
return fmt.Errorf("mkdir notebook crypto backup dir failed: %w", err)View on GitHub (pinned to 8641553a1f)
Solutions
- Free disk space / raise quota on the workspace volume
- Check permissions and locks on the existing backup file at dataCryptoBackupPath and remove/repair it if not writable
- Verify the backup path is not occupied by a directory and the storage device is healthy (dmesg/SMART)
Example fix
// before: blind re-derivation that fails again
_, err := deriveKEK(password)
// after: precheck writability of the backup location
backupPath := dataCryptoBackupPath()
if err := checkWritableFile(filepath.Dir(backupPath)); err == nil {
_, err = deriveKEK(password)
} Defensive patterns
Strategy: try-catch
Validate before calling
f, err := os.OpenFile(dataCryptoBackupPath(), os.O_WRONLY|os.O_CREATE, 0644)
if err != nil {
// target not writable; fix before calling the API
} else {
f.Close()
}
Try / catch
if err := saveNotebookCryptoBackup(kek); err != nil {
if strings.Contains(err.Error(), "write notebook crypto backup failed") {
// check disk space/permissions on backupPath, then retry save
}
}
Prevention
- Ensure adequate free space and quota on the workspace volume
- Do not lock or open the backup file exclusively in other tools (sync/backup/AV)
- Verify the backup path is a writable file location, not a directory
- Re-save the backup after any transient I/O failure so the recovery copy is current
When it happens
Trigger: atomicWriteFile(backupPath, data) fails during EnableEncryptedNotebook, deriveKEK, or ChangeMasterPassword — disk full, permission denied on the target file, the path is a directory, or an I/O error on the underlying device.
Common situations: Disk quota/full disk; the backup file exists but is read-only or locked by another process (backup/sync tools, antivirus); the backup path collides with a directory; failing disk or network-mounted workspace.
Understand the failure class
Background: "failed to write file", "Could not save figure", "Error saving remote file" — file write failed: causes and fixes across languages and libraries — this error's family across 38 libraries.
Related errors
- mkdir notebook crypto backup dir failed: %w
- write notebook crypt backup failed: %w
- write data [%s] failed: %s
- save generated image failed: %w
- write box conf [%s] failed: %w
AI-assisted analysis of siyuan-note/siyuan@8641553a1f (2026-09-11).
Data as JSON: /api/errors/f5f94acee69a5999.
Report an issue: GitHub.