first commit
This commit is contained in:
@@ -0,0 +1,86 @@
|
||||
# manager-stream
|
||||
|
||||
## Purpose
|
||||
|
||||
Free-function implementation of `PackedResourceManager.loadStream`,
|
||||
factored out of `manager.ts` so the class stays under the CLAUDE.md
|
||||
§3 300-line hard cap. The function drives the loader's streaming
|
||||
iterator, inserts each decoded entry into the manager's cache, and
|
||||
emits a `load` event before yielding the entry to the caller — so
|
||||
streaming consumers see exactly the same cache-priming behaviour as
|
||||
batch consumers.
|
||||
|
||||
## Features
|
||||
|
||||
- Threads the manager's default `MessageResolver` and feature-flag
|
||||
provider through every loader call via `buildLoaderOptions`.
|
||||
- Inserts each yielded entry into the cache **before** yielding so a
|
||||
consumer that calls `manager.load(inputUrl)` immediately after
|
||||
receiving an entry hits the cache (no second fetch).
|
||||
- `AbortSignal` propagation is honoured at entry time (via
|
||||
`manager._checkAbortedExt`) and re-honoured by the underlying
|
||||
`loader.loadStream` iterator at each yield.
|
||||
- Per-entry options (`StreamLoadEntry.options`) override the manager-
|
||||
level options, so a single stream can mix `verifyKey`s, keyrings,
|
||||
and mime allow-lists.
|
||||
|
||||
## Usage: Basic Example
|
||||
|
||||
```ts
|
||||
import { createPackedResourceManager } from "@suaveplan/packer-browser";
|
||||
|
||||
const manager = createPackedResourceManager();
|
||||
for await (const entry of manager.loadStream([
|
||||
"/asset-a.packed",
|
||||
"/asset-b.packed",
|
||||
])) {
|
||||
console.info("decoded", entry.inputUrl, "→", entry.url);
|
||||
}
|
||||
```
|
||||
|
||||
## Usage: Advanced Example
|
||||
|
||||
```ts
|
||||
import {
|
||||
createPackedResourceManager,
|
||||
MemoryKeyring,
|
||||
} from "@suaveplan/packer-browser";
|
||||
|
||||
const manager = createPackedResourceManager();
|
||||
const keyring = new MemoryKeyring({ "v1": new Uint8Array(32).fill(7) });
|
||||
const ac = new AbortController();
|
||||
|
||||
for await (const entry of manager.loadStream(
|
||||
[
|
||||
{ url: "/plain.packed" },
|
||||
{ url: "/encrypted.packed", options: { keyring } },
|
||||
],
|
||||
{ signal: ac.signal }
|
||||
)) {
|
||||
if (entry.inputUrl === "/plain.packed") ac.abort();
|
||||
process(entry);
|
||||
}
|
||||
```
|
||||
|
||||
## API Reference
|
||||
|
||||
- `managerLoadStream(manager, opts, inputs)` — internal entrypoint
|
||||
used by `PackedResourceManager.loadStream`. Not part of the package
|
||||
barrel.
|
||||
- `ManagerStreamedEntry` — `{ url, inputUrl, metadata }`.
|
||||
|
||||
## Implementation Notes
|
||||
|
||||
- The function takes the `inputs` array as the trailing parameter so
|
||||
the manager can pass `opts` early; this keeps the method signature
|
||||
in `manager.ts` to a single line and avoids type-juggling in the
|
||||
delegation.
|
||||
- `_streamInsert`, `_getDefaultResolver`, and `_checkAbortedExt` on the
|
||||
manager are intentionally `_`-prefixed: they exist only to give this
|
||||
free function access to the manager's internals without exposing
|
||||
cache/resolver/abort plumbing on the public surface. They are not in
|
||||
the package barrel.
|
||||
- The manager's `cacheHit` / `cacheMiss` events are NOT emitted from
|
||||
the streaming path — every streamed entry is, by definition, a
|
||||
fresh load. Consumers that need pre-stream cache lookups should
|
||||
combine `cache.has(...)` with a batch `load`.
|
||||
Reference in New Issue
Block a user