Budibase/budibase · error · BadRequestError
Invalid zip - uncompressed contents exceed the maximum size
Error message
Invalid zip - uncompressed contents exceed the maximum size
What it means
Thrown by validatePWAZipEntries when the cumulative uncompressed size of all zip entries exceeds MAX_PWA_ZIP_TOTAL_SIZE (50MB). It runs after each per-file check and bounds the total extracted footprint of the PWA in storage.
Source
Thrown at packages/server/src/api/controllers/static/index.ts:138
return
}
fileCount++
if (fileCount > MAX_PWA_ZIP_FILE_COUNT) {
throw new BadRequestError(
`Invalid zip - too many files (max ${MAX_PWA_ZIP_FILE_COUNT})`
)
}
if (entry.uncompressedSize > MAX_PWA_ZIP_ENTRY_SIZE) {
throw new BadRequestError(
`Invalid zip - file "${entry.fileName}" exceeds the maximum size`
)
}
totalUncompressedSize += entry.uncompressedSize
if (totalUncompressedSize > MAX_PWA_ZIP_TOTAL_SIZE) {
throw new BadRequestError(
"Invalid zip - uncompressed contents exceed the maximum size"
)
}
}
}
const listFilesRecursively = async (directory: string): Promise<string[]> => {
const entries = await fsp.readdir(directory, { withFileTypes: true })
const files = await Promise.all(
entries.map(async entry => {
const entryPath = join(directory, entry.name)
if (entry.isDirectory()) {
return await listFilesRecursively(entryPath)
}
if (entry.isFile()) {
return [entryPath]
}View on GitHub (pinned to a81a902e9a)
Solutions
- Trim archive contents until total uncompressed size is under 50MB
- Optimize images (WebP/lossy compression) and drop unused locales
- Move large media to external hosting and reference by URL
Example fix
// before 60 uncompressed MB of PNGs in the zip // after converted to WebP: 40 uncompressed MB total
Defensive patterns
Strategy: validation
Validate before calling
function isPwaZipTotalSizeSafe(entries, maxTotal = 50 * 1024 * 1024) {
return entries.reduce((sum, e) => sum + e.uncompressedSize, 0) <= maxTotal
} Type guard
const isZipEntryList = (v: unknown): v is Array<{ fileName: string; uncompressedSize: number }> =>
Array.isArray(v) && v.every(e => typeof e?.fileName === 'string' && typeof e?.uncompressedSize === 'number') Try / catch
try {
await uploadPwaZip(zip)
} catch (err) {
if (err instanceof BadRequestError && err.message.includes('uncompressed contents exceed')) {
// trim/optimize archive contents and retry
} else throw err
} Prevention
- Sum uncompressed entry sizes before upload; keep under 50MB
- Beware small-but-dense zips (high compression ratio) that explode on extraction
- Host large media externally instead of bundling it
When it happens
Trigger: Uploading a PWA zip where the sum of all entries' uncompressedSize exceeds 50MB, even if each individual file is under 10MB.
Common situations: A media-heavy PWA with many images/videos, or a zip that decompresses far beyond its small compressed size (high compression ratio archive).
Related errors
- Invalid zip - file "${entry.fileName}" exceeds the maximum s
- Invalid zip - directory depth exceeds ${MAX_PWA_ZIP_DEPTH}
- Invalid zip - too many files (max ${MAX_PWA_ZIP_FILE_COUNT})
- Stream to upload is invalid/undefined
- Plugin missing .js file.
AI-assisted analysis of Budibase/budibase@a81a902e9a (2026-08-29).
Data as JSON: /api/errors/da7899b14781be77.
Report an issue: GitHub.