koala73/worldmonitor · error
JODI Gas ZIP fetch failed: HTTP
Error message
JODI Gas ZIP fetch failed: HTTP ${resp.status} What it means
Thrown by fetchAndParseCsv in the JODI Gas seeder when the HTTP response for the JODI Gas ZIP archive has a non-ok status. The script downloads the monthly JODI Gas world ZIP and unblocks it locally, so any 4xx/5xx from the host aborts the seed. redirect:'error' also means redirect responses surface as failures here.
Solutions
- Open the JODI Gas website and confirm the current ZIP URL; update zipUrl in scripts/seed-jodi-gas.mjs if the path changed.
- Retry later if the status is 5xx or 429 — the host is temporarily unavailable or rate limiting.
- Check network/proxy configuration and whether the environment allows outbound HTTPS to the JODI host.
- Verify the request headers (User-Agent) are not being rejected; test the URL in a browser or with curl -I.
Example fix
// before
if (!resp.ok) throw new Error(`JODI Gas ZIP fetch failed: HTTP ${resp.status}`);
// after
if (!resp.ok) {
if (resp.status === 404) console.warn('JODI ZIP URL may be stale; check current archive path');
throw new Error(`JODI Gas ZIP fetch failed: HTTP ${resp.status}`);
} Defensive patterns
Strategy: retry
Validate before calling
const head = await fetch(zipUrl, { method: 'HEAD' }); if (!head.ok) console.warn(`JODI ZIP URL unhealthy: HTTP ${head.status}`); Try / catch
try { const zip = await fetchAndParseCsv(zipUrl, signal); } catch (e) { if (/HTTP \d{3}/.test(e.message)) { console.error('JODI host returned an error status; check URL freshness or retry later', e.message); } throw e; } Prevention
- Pin and periodically re-verify the JODI ZIP URL with a HEAD check in CI
- Add exponential backoff retries for 5xx/429 statuses
- Keep the browser-like User-Agent header to avoid bot blocking
- Alert on repeated 404s, which indicate the archive path moved
When it happens
Trigger: fetch(zipUrl) returns resp.ok === false, i.e. any HTTP 4xx/5xx status on the JODI Gas ZIP URL (e.g. 404 after the archive path changed, 403 from bot blocking, 5xx from the host).
Common situations: JODI renames or moves the monthly ZIP so the hardcoded URL 404s; CDN/WAF blocks the request despite the Chrome User-Agent; the JODI site is down for maintenance returning 5xx; an offline/proxied CI environment intercepts the request.
Understand the failure class
Background: "API error: {status}" and "HTTP 401/403/404/429/5xx" errors: non-2xx HTTP responses explained — this error's family across 27 libraries.
Related errors
AI-assisted analysis of koala73/worldmonitor@e586b8b4b8 (2026-09-22).
Data as JSON: /api/errors/021e70a930e776d1.
Report an issue: GitHub.
Appendix: source
Thrown at scripts/seed-jodi-gas.mjs:292
}
async function fetchAndParseCsv() {
// Discovery and archive download share the existing total request budget.
const signal = AbortSignal.timeout(120_000);
const catalogResponse = await fetch(CATALOG_URL, {
headers: { 'User-Agent': CHROME_UA },
signal,
redirect: 'error',
});
if (!catalogResponse.ok) throw new Error(`JODI Gas catalog fetch failed: HTTP ${catalogResponse.status}`);
const zipUrl = resolveGasArchiveUrl(await catalogResponse.json());
console.log(` Fetching JODI Gas ZIP from ${zipUrl}`);
const resp = await fetch(zipUrl, {
headers: { 'User-Agent': CHROME_UA, 'Accept-Encoding': 'identity' },
signal,
redirect: 'error',
});
if (!resp.ok) throw new Error(`JODI Gas ZIP fetch failed: HTTP ${resp.status}`);
const arrayBuf = await resp.arrayBuffer();
const zipBuf = Buffer.from(arrayBuf);
console.log(` ZIP downloaded: ${(zipBuf.length / 1024 / 1024).toFixed(1)} MB`);
const entry = findZipEntry(zipBuf, CSV_FILENAME);
if (!entry) throw new Error(`Could not find ${CSV_FILENAME} in ZIP`);
console.log(` Found entry: ${entry.entryName} (compression=${entry.compression})`);
const compressed = zipBuf.slice(entry.dataOffset, entry.dataOffset + entry.compSize);
let csvBuf;
if (entry.compression === 0) {
csvBuf = compressed;
} else if (entry.compression === 8) {
csvBuf = await inflateRawAsync(compressed);
} else {
throw new Error(`Unsupported ZIP compression method: ${entry.compression}`);
}View on GitHub (pinned to e586b8b4b8)