siyuan-note/siyuan · error
empty HEIF image
Error message
empty HEIF image
What it means
Returned by heif.GetOrCreate (kernel/heif/cache.go:95), and by convert/ImageSize, when the source slice for a .heic/.heif asset is zero bytes. GetOrCreate is called from the asset preview endpoints (kernel/server/serve.go:1255) on bytes read via ReadFileLimited, so in practice a zero-length HEIF file was stored in assets/ or passed in by the caller.
Source
Thrown at kernel/heif/cache.go:95
func IsPath(path string) bool {
path = strings.ToLower(path)
if index := strings.IndexAny(path, "?#"); index >= 0 {
path = path[:index]
}
ext := filepath.Ext(path)
return ext == ".heic" || ext == ".heif"
}
func GetOrCreate(ctx context.Context, source []byte, options Options) (Result, error) {
if options.Mode != ModePreview && options.Mode != ModeThumbnail {
return Result{}, ErrInvalidMode
}
if options.Encrypted && options.BoxID == "" {
return Result{}, errors.New("encrypted HEIF cache requires a notebook ID")
}
if len(source) == 0 {
return Result{}, errors.New("empty HEIF image")
}
if len(source) > MaxInputBytes {
return Result{}, ErrInputTooLarge
}
if err := ctx.Err(); err != nil {
return Result{}, err
}
digest := cacheDigest(source, options.Mode)
etag := `"heif-` + digest + `"`
cacheKey := digest
if options.Encrypted {
cacheKey = options.BoxID + ":" + digest
if data := getMemoryCache(cacheKey); data != nil {
return Result{Data: data, ETag: etag}, nil
}
} else if cachePath := existingDiskCache(options.Mode, digest); cachePath != "" {
return Result{Path: cachePath, ETag: etag}, nilView on GitHub (pinned to afa823b6b4)
Solutions
- Check the file size on disk - a 0-byte .heic must be re-exported or re-downloaded from the original source
- Re-import the photo from the camera or source device
- If it came from your own pipeline, fix the upload/write step that truncated it
Example fix
// before
result, err := heif.GetOrCreate(ctx, source, opts) // source == []byte{}
// after
if len(source) == 0 {
return errors.New("empty HEIF image")
}
result, err := heif.GetOrCreate(ctx, source, opts) Defensive patterns
Strategy: validation
Validate before calling
// Go: guard before calling the heif package
if len(source) == 0 {
return errors.New("empty HEIF image")
}
result, err := heif.GetOrCreate(ctx, source, opts) Prevention
- Validate non-zero file size at upload/import time
- Treat 0-byte assets as transfer failures and re-fetch the original
- Stat asset files before generating previews in batch tooling
When it happens
Trigger: Inserting/uploading an empty or truncated .heic file; an asset write that failed silently leaving a 0-byte file; calling the heif package directly with an empty slice (len(source) == 0).
Common situations: Failed phone camera exports; interrupted downloads of HEIF photos; cloud-storage placeholder files synced as 0 bytes; unit tests with empty byte-slice fixtures.
Related errors
- ErrInputTooLarge
- ErrImageTooLarge
- source is not an encrypted asset
- invalid asset type [%s]
- asset path must be a file
AI-assisted analysis of siyuan-note/siyuan@afa823b6b4 (2026-08-18).
Data as JSON: /api/errors/6d260a99f6226226.
Report an issue: GitHub.