Writing a real scanner against the kit before six repos get cut from it, rather
than after. It is the lutris pilot (M5/WP5.1) — the smallest of the six and the
one that exercises the POSIX local-art path end to end.
It earned its keep immediately: withReadOnlyDb / openReadOnly were never exported
from the parsers barrel, so the single most distinctive thing the lutris plugin
needs was unreachable from @punktfunk/plugin-kit/library. Nothing caught that,
because nothing had consumed the public surface yet.
It also caught a vacuous green in this package: tsconfig's include was
["src","test"], so anything under examples/ type-checked as a no-op. `examples`
is now in the check scope; tsconfig.build.json still narrows to src and
package.json still ships only dist + README, so nothing new is published (verified
against the built dist).
The example carries two deliberate departures from the Rust original, both
documented inline: art is emitted as file:// URLs instead of inlined data: URLs
(the host proxies the bytes, so the payload stays small — inlining covers is what
blew the 2 MB body limit at 49 titles during the playnite work, and is exactly
why the POSIX art path exists), and the untrusted-slug guard is carried over
verbatim, since the slug comes from Lutris's own database and is interpolated
into a path the host will later be asked to serve.
What it demonstrates, which is the reason one-repo-per-plugin is safe: everything
below `scan` is store-specific parsing, and everything else — store claim, sync
engine, launcher entries, __config, console registration, and the CLI verbs
including the parity gate — comes from defineLibraryPlugin.
plugin-kit: tsc clean (now including examples), 56 tests pass, build clean.
Two spikes validating the riskiest seams of the plugin-kit design before
implementation:
- HttpApi (effect/unstable/httpapi) served on Bun behind the SDK's
servePluginUi using ONLY effect-core layers (Etag.layerWeak, Path.layer,
HttpPlatform.layer + FileSystem.layerNoop) — no platform package. Auth,
schema validation, and static fallthrough all verified end-to-end.
- Browser client prefix strategy for the console proxy: both
transformClient+prependUrl AND baseUrl preserve the /plugin-ui/<id>
path prefix. Nested Schema.withDecodingDefaultKey defaults confirmed
(Effect-valued defaults; encodingStrategy "omit" restores raw shape
on encode).
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>