You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
scripts/gittensor-impact-card.mjs renders the README "Gittensor impact" SVG card by fetching data from api.gittensor.io and gittensor.io at build/CI time. Two of its network calls have no timeout:
fetchJson(url) (lines 50-56) calls fetch(url, { headers: {...} }) with no signal at all — used for
both https://api.gittensor.io/repos/${encoded}/impact and .../prs (lines 214-216).
The gt-logo fetch at line 217: fetch("https://gittensor.io/gt-logo.svg").then((r) => r.text()) — also no signal.
Every other outbound fetch() call already exercised by this script family sets an explicit timeout via AbortSignal.timeout(...):
This is the same "no timeout on an external call, unlike every sibling fetcher" class of bug already fixed
across the repo (#7070qdrant-vectorize.ts, #7071fetchRepoFocusManifestFile, #7072fetchShotContentBlock, #7014 three release/observability scripts, #7007 the extension's sync fetch, #6988oauth-device-flow.js) — scripts/gittensor-impact-card.mjs was missed by that sweep. Without a timeout, a hung api.gittensor.io or gittensor.io response hangs the README-card regeneration job indefinitely instead of failing fast.
Requirements
Add an explicit request timeout (AbortSignal.timeout(...)) to every fetch() call in scripts/gittensor-impact-card.mjs: the two calls inside fetchJson (both the impact and prs requests
route through it) and the standalone gt-logo.svg fetch at line 217.
Follow this repo's existing convention: a single named timeout constant (e.g. GITTENSOR_IMPACT_CARD_FETCH_TIMEOUT_MS) reused by all three call sites, matching how GITHUB_FETCH_TIMEOUT_MS / GITHUB_PUBLIC_FETCH_TIMEOUT_MS are defined once and reused in src/github/client.ts / src/github/public.ts.
On a timeout/abort, the script must still fail loudly (matching its current main().catch(...) -> process.exit(1) behavior) rather than hanging or swallowing the error.
Do not change the script's non-error-path output shape (the generated SVG) or its CLI usage
(node scripts/gittensor-impact-card.mjs <owner/repo> <out-file.svg>).
Deliverables
A shared timeout constant used by fetchJson's fetch call and the gt-logo.svg fetch.
Both call sites pass signal: AbortSignal.timeout(...) using that constant.
A regression test (or an addition to any existing test for this script) that stubs a hanging fetch
and asserts the call aborts within the configured timeout instead of hanging.
Test Coverage Requirements
scripts/** is explicitly excluded from the Codecov ignore: list in codecov.yml (- "scripts/**"), so codecov/patch does not gate this file — it is not unit-coverable via the Codecov patch gate. Add or
extend a vitest unit test that exercises fetchJson (and/or the module's exported pure helpers, if any are
extracted for testability) with a stubbed/injectable fetch that never resolves, and assert the call rejects
via the configured AbortSignal.timeout rather than hanging the test run. Run locally via npm run test:coverage per this repo's contributor workflow even though Codecov itself won't gate it.
Expected Outcome
scripts/gittensor-impact-card.mjs can no longer hang indefinitely on a slow/unresponsive api.gittensor.io or gittensor.io response — every outbound fetch in the script fails fast on a bounded
timeout, consistent with every other external-fetch script in this repo.
Context
scripts/gittensor-impact-card.mjsrenders the README "Gittensor impact" SVG card by fetching data fromapi.gittensor.ioandgittensor.ioat build/CI time. Two of its network calls have no timeout:fetchJson(url)(lines 50-56) callsfetch(url, { headers: {...} })with nosignalat all — used forboth
https://api.gittensor.io/repos/${encoded}/impactand.../prs(lines 214-216).fetch("https://gittensor.io/gt-logo.svg").then((r) => r.text())— also nosignal.Every other outbound
fetch()call already exercised by this script family sets an explicit timeout viaAbortSignal.timeout(...):scripts/smoke-observability-metrics.mjs(lines 51/57/64)scripts/smoke-observability-traces.mjs(lines 52/58)scripts/check-mcp-release-due.mjs(line 184,GITHUB_REQUEST_TIMEOUT_MS)scripts/smoke-production.mjs/scripts/load-test-worker.mjs(both use anAbortController+setTimeout)src/github/client.ts(GITHUB_FETCH_TIMEOUT_MS),src/github/public.ts(
GITHUB_PUBLIC_FETCH_TIMEOUT_MS),src/github/migration-tree.ts(GITHUB_FETCH_TIMEOUT_MS)This is the same "no timeout on an external call, unlike every sibling fetcher" class of bug already fixed
across the repo (#7070
qdrant-vectorize.ts, #7071fetchRepoFocusManifestFile, #7072fetchShotContentBlock,#7014 three release/observability scripts, #7007 the extension's sync fetch, #6988
oauth-device-flow.js) —scripts/gittensor-impact-card.mjswas missed by that sweep. Without a timeout, a hungapi.gittensor.ioorgittensor.ioresponse hangs the README-card regeneration job indefinitely instead of failing fast.Requirements
AbortSignal.timeout(...)) to everyfetch()call inscripts/gittensor-impact-card.mjs: the two calls insidefetchJson(both the impact and prs requestsroute through it) and the standalone
gt-logo.svgfetch at line 217.GITTENSOR_IMPACT_CARD_FETCH_TIMEOUT_MS) reused by all three call sites, matching howGITHUB_FETCH_TIMEOUT_MS/GITHUB_PUBLIC_FETCH_TIMEOUT_MSare defined once and reused insrc/github/client.ts/src/github/public.ts.main().catch(...)->process.exit(1)behavior) rather than hanging or swallowing the error.(
node scripts/gittensor-impact-card.mjs <owner/repo> <out-file.svg>).Deliverables
fetchJson's fetch call and thegt-logo.svgfetch.signal: AbortSignal.timeout(...)using that constant.fetchand asserts the call aborts within the configured timeout instead of hanging.
Test Coverage Requirements
scripts/**is explicitly excluded from the Codecovignore:list incodecov.yml(- "scripts/**"), socodecov/patchdoes not gate this file — it is not unit-coverable via the Codecov patch gate. Add orextend a
vitestunit test that exercisesfetchJson(and/or the module's exported pure helpers, if any areextracted for testability) with a stubbed/injectable
fetchthat never resolves, and assert the call rejectsvia the configured
AbortSignal.timeoutrather than hanging the test run. Run locally vianpm run test:coverageper this repo's contributor workflow even though Codecov itself won't gate it.Expected Outcome
scripts/gittensor-impact-card.mjscan no longer hang indefinitely on a slow/unresponsiveapi.gittensor.ioorgittensor.ioresponse — every outbound fetch in the script fails fast on a boundedtimeout, consistent with every other external-fetch script in this repo.
Links & Resources
scripts/gittensor-impact-card.mjs(lines 50-56, 213-218)src/github/client.ts(GITHUB_FETCH_TIMEOUT_MS),src/github/public.ts(
GITHUB_PUBLIC_FETCH_TIMEOUT_MS),src/github/migration-tree.ts(GITHUB_FETCH_TIMEOUT_MS)