Add serve-instrument-all package#1363
Conversation
Adds a dev server that serves every instrument in a directory tree of forms/ and interactive/ subdirectories, with an index page and a language switcher, extending the single-instrument serve-instrument package. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
|
Important Review skippedAuto reviews are disabled on base/target branches other than the default branch. Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Repository UI Review profile: CHILL Plan: Pro Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Pull request overview
Adds a new workspace package, @opendatacapture/serve-instrument-all, providing a dev server that discovers and serves all instruments under forms/ and interactive/, with an index page and per-instrument rendering/bundling.
Changes:
- Introduces the
serve-instrument-allCLI + HTTP server to enumerate instruments and serve an index plus per-instrument pages. - Adds a small React client/root app including an en/fr language switcher and instrument rendering via
ScalarInstrumentRenderer. - Adds build tooling (esbuild + Tailwind CSS extraction) and wires the new package into the pnpm workspace lockfile.
Reviewed changes
Copilot reviewed 7 out of 8 changed files in this pull request and generated 9 comments.
Show a summary per file
| File | Description |
|---|---|
| pnpm-lock.yaml | Adds the new workspace importer for packages/serve-instrument-all. |
| packages/serve-instrument-all/package.json | Defines the new package, bin entry, and dependencies for the CLI/dev server. |
| packages/serve-instrument-all/tsconfig.json | TypeScript config matching existing dev-server conventions (DOM libs, runtime path mapping). |
| packages/serve-instrument-all/scripts/build.js | Builds the Node CLI and browser client bundles (plus inlined Tailwind styles). |
| packages/serve-instrument-all/src/cli.ts | CLI argument parsing/validation and server startup (--port, --verbose). |
| packages/serve-instrument-all/src/server.tsx | HTTP server, instrument discovery, bundling/watch logic, and runtime asset serving. |
| packages/serve-instrument-all/src/root.tsx | React UI: index page + instrument page with language switcher. |
| packages/serve-instrument-all/src/client.tsx | Client hydration entrypoint for the server-rendered HTML. |
Files not reviewed (1)
- pnpm-lock.yaml: Language not supported
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| const [, type, name] = instrumentMatch; | ||
| const decodedName = decodeURIComponent(name!); | ||
| const encodedBundle = await this.loaderMap.getEncodedBundle(type!, decodedName); |
| const clientBundle = await fs.promises | ||
| .readFile(path.resolve(import.meta.dirname, 'client.js'), 'utf-8') | ||
| .then((text) => `const __ROOT_PROPS__ = ${JSON.stringify(props)}; ${text}`); | ||
|
|
| fs.watch(target, { recursive: false }, () => { | ||
| log(chalk.yellow('↺') + chalk.dim(` [${this.label}] File changed, rebuilding...`)); | ||
| void this.updateEncodedBundle(); | ||
| }); |
| const [, type, name] = instrumentMatch; | ||
| const decodedName = decodeURIComponent(name!); | ||
| const encodedBundle = await this.loaderMap.getEncodedBundle(type!, decodedName); |
| const clientBundle = await fs.promises | ||
| .readFile(path.resolve(import.meta.dirname, 'client.js'), 'utf-8') | ||
| .then((text) => `const __ROOT_PROPS__ = ${JSON.stringify(props)}; ${text}`); | ||
|
|
| fs.watch(target, { recursive: false }, () => { | ||
| log(chalk.yellow('↺') + chalk.dim(` [${this.label}] File changed, rebuilding...`)); | ||
| void this.updateEncodedBundle(); | ||
| }); |
| const [, type, name] = instrumentMatch; | ||
| const decodedName = decodeURIComponent(name!); | ||
| const encodedBundle = await this.loaderMap.getEncodedBundle(type!, decodedName); |
| const clientBundle = await fs.promises | ||
| .readFile(path.resolve(import.meta.dirname, 'client.js'), 'utf-8') | ||
| .then((text) => `const __ROOT_PROPS__ = ${JSON.stringify(props)}; ${text}`); | ||
|
|
| fs.watch(target, { recursive: false }, () => { | ||
| log(chalk.yellow('↺') + chalk.dim(` [${this.label}] File changed, rebuilding...`)); | ||
| void this.updateEncodedBundle(); | ||
| }); |
Summary
Adds
@opendatacapture/serve-instrument-all, a dev server that serves every instrument in a directory tree, extending the single-instrumentserve-instrumentpackage.Given a target directory containing
forms/and/orinteractive/subdirectories, it:forms/<name>/,interactive/<name>/) and serves an index page linking to all of themScalarInstrumentRenderer, rebuilding its bundle on file change (fs.watch)/runtime/*--portand--verbose(the latter now also emits per-request logs)The implementation closely mirrors
serve-instrument(same build setup, esbuild config, and conventions).Notes
pnpm-lock.yamlchange is a single additive importer block; transitive dependency drift from regeneration was stripped so the diff stays minimal.pnpm install --frozen-lockfilepasses.tsc,eslint, andbuildall pass for the new package.Known limitations (follow-ups, not blockers)
404rather than distinguishing a compile error.🤖 Generated with Claude Code