stablyai/orca · error · Error

Spritesheet is too large (${(sheetStat.size / (1024 * 1024))

Error message

Spritesheet is too large (${(sheetStat.size / (1024 * 1024)).toFixed(1)} MB).

What it means

Thrown at pet.ts:321-324 when sheetStat.size exceeds MAX_BYTES (64*1024*1024 = 64 MB). This bounds the spritesheet so a user cannot point the import at a multi-gigabyte file and OOM the renderer when it builds a Blob URL. The message includes the actual size in MB for clarity.

Source

Thrown at src/main/ipc/pet.ts:322

    if (await isSymlink(sheetSrc)) {
      throw new Error('spritesheet must not be a symlink.')
    }
    const sheetClass = classifyFile(sheetSrc)
    if (!sheetClass || sheetClass.ext === '.svg') {
      // SVG can't be used as a sprite sheet (no pixel grid).
      throw new Error('Spritesheet must be a PNG, APNG, JPG, GIF, or WebP.')
    }
    let sheetStat: Awaited<ReturnType<typeof stat>>
    try {
      sheetStat = await stat(sheetSrc)
    } catch {
      throw new Error('Spritesheet file not found.')
    }
    if (!sheetStat.isFile()) {
      throw new Error('Spritesheet path is not a file.')
    }
    if (sheetStat.size > MAX_BYTES) {
      throw new Error(
        `Spritesheet is too large (${(sheetStat.size / (1024 * 1024)).toFixed(1)} MB).`
      )
    }

    let sprite: NonNullable<CustomPet['sprite']> | undefined
    if (manifest.frame) {
      // Why: only decode when a frame layout needs validating — nativeImage can fail on some WebP variants in headless contexts.
      const sheetBuf = await readFile(sheetSrc)
      // Why: defend against TOCTOU — file may have grown between stat and read.
      if (sheetBuf.byteLength > MAX_BYTES) {
        throw new Error('Spritesheet exceeded the size limit.')
      }
      const dims = await readSheetDimensions(sheetBuf)
      if (!dims) {
        throw new Error('Could not decode the spritesheet image.')
      }
      const { width: fw, height: fh } = manifest.frame
      if (dims.width % fw !== 0 || dims.height % fh !== 0) {

View on GitHub (pinned to 1136503c6a)

Solutions

  1. Downscale or recompress the image so it is under 64 MB (e.g. reduce frame count, lower resolution to the actual frame dimensions).
  2. For animated sheets, reduce the number of frames or use APNG/WebP compression.
  3. Confirm the file is a real image and not a mislabeled large binary.

Example fix

# before — 200 MB uncompressed PNG
# after — re-export at frame resolution
convert huge.png -resize 512x512 sheet.png
Defensive patterns

Strategy: validation

Validate before calling

import { stat } from 'node:fs/promises'
const MAX_BYTES = 64 * 1024 * 1024
async function assertSheetUnderLimit(p: string) {
  const st = await stat(p)
  if (st.size > MAX_BYTES) throw new Error(`spritesheet ${(st.size/1048576).toFixed(1)} MB exceeds 64 MB`)
}

Try / catch

try { await importPetBundle(p) }
catch (e) { if (e instanceof Error && e.message.startsWith('Spritesheet is too large')) { /* shrink the image */ } else throw e }

Prevention

When it happens

Trigger: The spritesheet file is larger than 64 MB at the time stat() runs. Any image format that passes the classifyFile gate can trigger it if the file is oversized.

Common situations: An uncompressed PNG from a high-resolution source; an APNG with many frames; a GIF with a large palette; a bundle author who did not downscale the source art.

Related errors


AI-assisted analysis of stablyai/orca@1136503c6a (2026-08-12). Data as JSON: /api/errors/6f8686a30f309214. Report an issue: GitHub.