Cache/API implementation (#36), phase 3.
Depends on the download-plumbing and streaming-decrypt units. New module.
Goal
Three independent bounded request pools inside the library so metadata, content,
and thumbnail traffic are limited and prioritised separately (owner ruling 7).
Scope
Three queues, each with a max in-flight count, defaulted and overridable via open() options: metadata 10 (metadataConcurrency), content 5
(contentConcurrency), thumbnails 25 (thumbnailConcurrency).
Each request is assigned by what it fetches: metadata = /collections/v2, /collections/v2/diff, /files/data/fetch; content =
original streams; thumbnails = thumbnail streams.
Within a pool, on-demand work runs before background/precache work (a simple
priority ordering, e.g. visible > ahead > background). The same fileID
requested twice is fetched once (in-flight dedup). An idle pool does not lend
slots to another.
The retry policy is unchanged and runs inside a slot (a third attempt still
holds one slot). Pools wrap calls into Client; do not change ApiClient.
Definition of done
Concurrency caps enforced per pool (tested with a controllable fake task that
counts concurrent starts).
Priority ordering and in-flight dedup tested.
make check green.
Grounding
New src/library/ module (a small generic bounded queue + three instances).
Depends on the download units (so content/thumbnail work has something to wrap).
Dispatch notes: TDD; no scripted edits; no interactive questions; plain language.
Squash subject ends (closes #<this issue>). End every message with Model: opus-4-8.
Model: opus-4-8
Cache/API implementation (https://git.eeqj.de/sneak/quak/issues/36), phase 3.
Depends on the download-plumbing and streaming-decrypt units. New module.
## Goal
Three independent bounded request pools inside the library so metadata, content,
and thumbnail traffic are limited and prioritised separately (owner ruling 7).
## Scope
- Three queues, each with a max in-flight count, defaulted and overridable via
`open()` options: metadata 10 (`metadataConcurrency`), content 5
(`contentConcurrency`), thumbnails 25 (`thumbnailConcurrency`).
- Each request is assigned by what it fetches: metadata =
`/collections/v2`, `/collections/v2/diff`, `/files/data/fetch`; content =
original streams; thumbnails = thumbnail streams.
- Within a pool, on-demand work runs before background/precache work (a simple
priority ordering, e.g. `visible` > `ahead` > `background`). The same `fileID`
requested twice is fetched once (in-flight dedup). An idle pool does not lend
slots to another.
- The retry policy is unchanged and runs inside a slot (a third attempt still
holds one slot). Pools wrap calls into `Client`; do not change `ApiClient`.
## Definition of done
- Concurrency caps enforced per pool (tested with a controllable fake task that
counts concurrent starts).
- Priority ordering and in-flight dedup tested.
- `make check` green.
## Grounding
New `src/library/` module (a small generic bounded queue + three instances).
Depends on the download units (so content/thumbnail work has something to wrap).
Dispatch notes: TDD; no scripted edits; no interactive questions; plain language.
Squash subject ends ` (closes #<this issue>)`. End every message with
`Model: opus-4-8`.
Model: opus-4-8
Implemented as #63 (branch issue-45-request-pools, base next).
New self-contained src/library/pools.ts: a generic BoundedPool concurrency limiter plus a RequestPools bundle of three at the caps this issue sets — metadata 10, content 5, thumbnails 25, each overridable via constructor options. Within a pool, on-demand work is served before background/precache work, first-come-first-served within a priority; a task submitted under a key already in flight is shared rather than fetched twice, and the key frees the moment that task settles. A task's slot is held for its whole lifetime, so a request that retries internally stays counted against the cap between attempts.
Kept strictly to the pools module and its test (test/library/pools.test.ts, TDD): Library and ApiClient are untouched, since wiring the pools into the cache is the later unit (#46). Tests cover the concurrency cap under a controllable fake task, priority ordering, in-flight dedup, the retry-holds-a-slot property, and that an idle pool lends no slots. make check green.
Judgement call: a request that dedups onto an already-queued task inherits the first submitter's priority rather than promoting the queued entry — kept simple and disclosed in the PR.
Model: opus-4-8
Implemented as https://git.eeqj.de/sneak/quak/pulls/63 (branch `issue-45-request-pools`, base `next`).
New self-contained `src/library/pools.ts`: a generic `BoundedPool` concurrency limiter plus a `RequestPools` bundle of three at the caps this issue sets — metadata 10, content 5, thumbnails 25, each overridable via constructor options. Within a pool, on-demand work is served before background/precache work, first-come-first-served within a priority; a task submitted under a `key` already in flight is shared rather than fetched twice, and the key frees the moment that task settles. A task's slot is held for its whole lifetime, so a request that retries internally stays counted against the cap between attempts.
Kept strictly to the pools module and its test (`test/library/pools.test.ts`, TDD): `Library` and `ApiClient` are untouched, since wiring the pools into the cache is the later unit (https://git.eeqj.de/sneak/quak/issues/46). Tests cover the concurrency cap under a controllable fake task, priority ordering, in-flight dedup, the retry-holds-a-slot property, and that an idle pool lends no slots. `make check` green.
Judgement call: a request that dedups onto an already-queued task inherits the first submitter's priority rather than promoting the queued entry — kept simple and disclosed in the PR.
Model: opus-4-8
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Cache/API implementation (#36), phase 3.
Depends on the download-plumbing and streaming-decrypt units. New module.
Goal
Three independent bounded request pools inside the library so metadata, content,
and thumbnail traffic are limited and prioritised separately (owner ruling 7).
Scope
open()options: metadata 10 (metadataConcurrency), content 5(
contentConcurrency), thumbnails 25 (thumbnailConcurrency)./collections/v2,/collections/v2/diff,/files/data/fetch; content =original streams; thumbnails = thumbnail streams.
priority ordering, e.g.
visible>ahead>background). The samefileIDrequested twice is fetched once (in-flight dedup). An idle pool does not lend
slots to another.
holds one slot). Pools wrap calls into
Client; do not changeApiClient.Definition of done
counts concurrent starts).
make checkgreen.Grounding
New
src/library/module (a small generic bounded queue + three instances).Depends on the download units (so content/thumbnail work has something to wrap).
Dispatch notes: TDD; no scripted edits; no interactive questions; plain language.
Squash subject ends
(closes #<this issue>). End every message withModel: opus-4-8.Model: opus-4-8
Implemented as #63 (branch
issue-45-request-pools, basenext).New self-contained
src/library/pools.ts: a genericBoundedPoolconcurrency limiter plus aRequestPoolsbundle of three at the caps this issue sets — metadata 10, content 5, thumbnails 25, each overridable via constructor options. Within a pool, on-demand work is served before background/precache work, first-come-first-served within a priority; a task submitted under akeyalready in flight is shared rather than fetched twice, and the key frees the moment that task settles. A task's slot is held for its whole lifetime, so a request that retries internally stays counted against the cap between attempts.Kept strictly to the pools module and its test (
test/library/pools.test.ts, TDD):LibraryandApiClientare untouched, since wiring the pools into the cache is the later unit (#46). Tests cover the concurrency cap under a controllable fake task, priority ordering, in-flight dedup, the retry-holds-a-slot property, and that an idle pool lends no slots.make checkgreen.Judgement call: a request that dedups onto an already-queued task inherits the first submitter's priority rather than promoting the queued entry — kept simple and disclosed in the PR.
Model: opus-4-8