itwanger/toBeBetterJavaer · error · Error
Downloaded file is empty
Error message
Downloaded file is empty
What it means
Thrown by downloadImage() in scripts/convert-mdnice-images-to-cdn.js when the response body, after being buffered into a Buffer, has zero bytes. A 2xx response with an image Content-Type but an empty body means nothing would be uploaded, so the script refuses before touching OSS.
Source
Thrown at scripts/convert-mdnice-images-to-cdn.js:373
}
async function downloadImage(url) {
const response = await fetch(url, {
redirect: "follow",
headers: {
"User-Agent": "toBeBetterJavaer-image-cdn/1.0",
},
});
if (!response.ok) {
throw new Error(`Download failed with HTTP ${response.status}`);
}
const contentType = normalizeContentType(response.headers.get("content-type"));
if (contentType && !contentType.startsWith("image/") && contentType !== "application/octet-stream") {
throw new Error(`Unexpected content type: ${contentType}`);
}
const body = Buffer.from(await response.arrayBuffer());
if (body.length === 0) {
throw new Error("Downloaded file is empty");
}
return { body, contentType };
}
function normalizeContentType(contentType) {
if (!contentType) {
return "";
}
return contentType.split(";")[0].trim().toLowerCase();
}
function contentTypeForPath(filePath) {
const extension = path.extname(filePath).toLowerCase();
switch (extension) {
case ".png":
return "image/png";
case ".jpg":
case ".jpeg":View on GitHub (pinned to 6617f5fd0b)
Solutions
- Rerun the command — empty bodies from transient network faults usually resolve on retry
- Verify manually: `curl -o /tmp/x.png <url> && ls -l /tmp/x.png` to confirm the source serves bytes
- If the source is permanently empty, replace the image reference with a working copy of the asset
Defensive patterns
Strategy: retry
Validate before calling
const res = await fetch(url, { headers: { "User-Agent": "toBeBetterJavaer-image-cdn/1.0" } });
const len = Number(res.headers.get("content-length") || "-1");
if (len === 0) console.warn(`Source serves an empty body: ${url}`); Try / catch
catch (err) { if (err.message === "Downloaded file is empty") { await sleep(backoff); return retryOnce(); } throw err; } Prevention
- Retry the full run once before investigating — empty bodies are usually transient
- Verify suspicious sources with curl -o and ls -l
- Run conversions on a stable network
When it happens
Trigger: Source server returns 200 with correct Content-Type and zero-length body (truncated upload on the origin, a bad proxy response, or a redirect chain that terminates in an empty stream). Requires --write mode since dry runs never download.
Common situations: Flaky upstream CDNs; interrupted origin uploads; middleboxes (corporate proxies, VPNs) returning empty bodies; rare but real on mobile hotspots.
Related errors
- Download failed with HTTP ${response.status}
- Unexpected content type: ${contentType}
- ${optionName} must be a positive integer
AI-assisted analysis of itwanger/toBeBetterJavaer@6617f5fd0b (2026-08-14).
Data as JSON: /api/errors/a0484284f2d983df.
Report an issue: GitHub.