siyuan-note/siyuan · error
Conf.Language(314)
Error message
Conf.Language(314)
What it means
When the asset referenced by exportPath belongs to an encrypted notebook, AcquireExportArtifactLease requires that the notebook be unlocked before it can resolve the asset path with the box DEK and register the lease. If the box is still locked, the function aborts with the localized message Conf.Language(314) ("the encrypted notebook is locked / must be unlocked"). This is an authentication/state precondition, not a data error.
Source
Thrown at kernel/model/encrypted_export.go:242
if !strings.HasPrefix(exportPath, "assets/") {
return nil, errors.New("unsupported export path")
}
relativePath, boxID, parseErr := assetPathAndBox(exportPath, "")
if parseErr != nil {
return nil, parseErr
}
if boxID == "" || !IsEncryptedBox(boxID) {
artifact, resolveErr := GetAssetAbsPath(relativePath)
if resolveErr != nil {
return nil, resolveErr
}
if ensureErr := EnsureAssetLocal(artifact); ensureErr != nil {
return nil, ensureErr
}
return registerMobileExportLease("", artifact, filepath.Base(artifact), "")
}
if !IsBoxUnlocked(boxID) {
return nil, errors.New(Conf.Language(314))
}
artifact, resolveErr := GetAssetAbsPathInBox(relativePath, boxID)
if resolveErr != nil {
return nil, resolveErr
}
if ensureErr := EnsureAssetLocal(artifact); ensureErr != nil {
return nil, ensureErr
}
if err = AcquireEncryptedBoxOperation(boxID); err != nil {
return nil, err
}
HoldBoxReadLock(boxID)
release := true
defer func() {
if release {
ReleaseBoxReadLock(boxID)
ReleaseEncryptedBoxOperation(boxID)View on GitHub (pinned to 8641553a1f)
Solutions
- Unlock the encrypted notebook first (call the box unlock API / prompt the user for the passphrase), then retry AcquireExportArtifactLease.
- Check IsBoxUnlocked(boxID) before requesting the lease and defer export until the box is unlocked.
- For automated flows, keep the box unlocked for the duration of the export and register the lease promptly after unlocking (leases also hold a box read lock).
Example fix
// before
lease, err := model.AcquireExportArtifactLease(exportPath)
// after
if _, boxID, perr := model.AssetPathAndBox(exportPath); perr == nil && !model.IsBoxUnlocked(boxID) {
if uerr := model.UnlockBox(boxID, passphrase); uerr != nil { return uerr }
}
lease, err := model.AcquireExportArtifactLease(exportPath) Defensive patterns
Strategy: try-catch
Validate before calling
if boxID != "" && model.IsEncryptedBox(boxID) && !model.IsBoxUnlocked(boxID) {
// prompt for passphrase / unlock first
} Try / catch
lease, err := model.AcquireExportArtifactLease(exportPath)
if err != nil {
if isBoxLockedError(err) { // localized Conf.Language(314)
if uerr := unlockBoxAndRetry(exportPath); uerr == nil {
lease, err = model.AcquireExportArtifactLease(exportPath)
}
}
if err != nil { return err }
} Prevention
- Check IsBoxUnlocked before any encrypted-box export flow
- Handle app restart: boxes start locked, unlock before background exports
- Keep export flows in the foreground so users can answer passphrase prompts
When it happens
Trigger: Calling AcquireExportArtifactLease (via materializeExportArtifact or AcquireMobileExportLease) with exportPath = "assets/<file>" where assetPathAndBox resolves the asset to an encrypted box (IsEncryptedBox(boxID) true) and IsBoxUnlocked(boxID) is false — i.e. the user has not supplied the passphrase or the box was re-locked.
Common situations: Background export/sync jobs running after the app restarted (boxes locked at boot); a mobile export request racing with the user locking the box; automated scripts that never unlocked the encrypted notebook; box auto-lock timeout elapsed before export.
Related errors
- Please unlock the encrypted notebook first
- Please unlock the encrypted notebook first
- %s
- Conf.Language(314)
- Conf.Language(314)
AI-assisted analysis of siyuan-note/siyuan@8641553a1f (2026-09-11).
Data as JSON: /api/errors/d4cf471d6e597d1b.
Report an issue: GitHub.