{"record":{"id":"b8c805003627d6f9","repo":"google/zx","slug":"failed-to-fetch-remote-script-remote-res-st","errorCode":null,"errorMessage":"Failed to fetch remote script: ${remote} (${res.status})","messagePattern":"Failed to fetch remote script: (.+?) \\((.+?)\\)","errorType":"exception","errorClass":"Fail","httpStatus":null,"severity":"error","filePath":"src/cli.ts","lineNumber":256,"sourceCode":"  if (ext === '.md') {\n    script = transformMarkdown(script)\n    tempPath = getFilepath(dir, base, EXT)\n  }\n  if (argSlice) updateArgv(argv._.slice(argSlice))\n\n  return { script, scriptPath, tempPath }\n}\n\nasync function readScriptFromStdin(): Promise<string> {\n  return process.stdin.isTTY ? '' : stdin()\n}\n\nasync function readScriptFromHttp(remote: string): Promise<string> {\n  const res = await fetch(remote)\n  if (!res.ok) {\n    console.error(`Error: Can't get ${remote}`)\n    process.exitCode = 1\n    throw new Fail(`Failed to fetch remote script: ${remote} (${res.status})`)\n  }\n  return res.text()\n}\n\nexport function injectGlobalRequire(origin: string): void {\n  const __filename = path.resolve(origin)\n  const __dirname = path.dirname(__filename)\n  const require = createRequire(origin)\n  Object.assign(globalThis, { __filename, __dirname, require })\n}\n\nexport function isMain(\n  meta: ImportMeta['url'] | ImportMeta = import.meta.url,\n  scriptpath: string = process.argv[1]\n): boolean {\n  if (typeof meta === 'string') {\n    if (meta.startsWith('file:')) {\n      const modulePath = url.fileURLToPath(meta).replace(/\\.\\w+$/, '')","sourceCodeStart":238,"sourceCodeEnd":274,"githubUrl":"https://github.com/google/zx/blob/00a2c484e219c2e84bfc3a199febf7fbce2cfbf4/src/cli.ts#L238-L274","documentation":"Thrown by readScriptFromHttp() when `zx <http(s) url>` gets a non-2xx response. zx fetches the URL with the global fetch() and rejects on !res.ok, embedding the HTTP status code in the message and setting exitCode to 1.","triggerScenarios":"`zx https://example.com/script.mjs` where the server returns 404/403/500; a gist URL that is not the raw endpoint (HTML page, non-2xx); a private repo/gist requiring auth; corporate proxy returning a block page (403).","commonSituations":"Wrong or mistyped URL; deleted/moved remote script; auth required; corporate proxy/VPN interfering; transient server outage.","solutions":["Verify the URL independently: `curl -iL <url>` and check the status.","Use the raw URL for gists/repos (e.g. `https://raw.githubusercontent.com/...`).","Add authentication (token in the URL or a custom fetch via a wrapper) if the resource is private.","Download the file and run it locally instead: `curl -o s.mjs <url> && zx s.mjs`.","Retry; if flaky, wrap the zx invocation in a retry or check connectivity/proxy."],"exampleFix":"// before: gist HTML page is not the script\n$ zx https://gist.github.com/user/abc123\n// after: use the raw endpoint\n$ zx https://raw.githubusercontent.com/gist/abc123/raw/script.mjs","handlingStrategy":"retry","validationCode":"async function headOk(url: string): Promise<boolean> {\n  const res = await fetch(url, { method: 'HEAD' })\n  return res.ok\n}\n\nif (!(await headOk(scriptUrl))) {\n  throw new Error(`remote script unreachable: ${scriptUrl}`)\n}","typeGuard":null,"tryCatchPattern":"try {\n  await runRemote(scriptUrl)\n} catch (e) {\n  if (e instanceof Fail && /Failed to fetch remote script/.test(e.message)) {\n    // fall back: download then run locally\n    await $`curl -fsSL ${scriptUrl} -o /tmp/s.mjs`\n    await $`zx /tmp/s.mjs`\n  } else throw e\n}","preventionTips":["Verify remote URLs with curl -iL before wiring them into zx invocations.","Pin to raw content URLs (raw.githubusercontent.com) for gists and repo files.","Cache remote scripts locally for offline/retry resilience instead of fetching on every run."],"tags":["network","http","fetch","cli","remote"],"backgroundTag":null,"analyzedSha":"00a2c484e219c2e84bfc3a199febf7fbce2cfbf4","analyzedAt":"2026-08-13T02:11:06.305Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}