{"_id":"@antiphony/capture-kit","name":"@antiphony/capture-kit","dist-tags":{"latest":"0.1.0"},"versions":{"0.1.0":{"name":"@antiphony/capture-kit","version":"0.1.0","description":"Headless browser audio primitives for Antiphony clients — a microphone recorder, a playback hook, and client-side waveform peaks. Renders nothing, styles nothing, uploads nothing.","license":"MIT","homepage":"https://docs.antiphony.dev","repository":{"type":"git","url":"git+https://github.com/bbthorson/antiphony.git","directory":"packages/capture-kit"},"bugs":{"url":"https://github.com/bbthorson/antiphony/issues"},"type":"module","sideEffects":false,"main":"./dist/cjs/index.cjs","module":"./dist/esm/index.js","types":"./dist/cjs/index.d.cts","exports":{".":{"import":{"types":"./dist/esm/index.d.ts","default":"./dist/esm/index.js"},"require":{"types":"./dist/cjs/index.d.cts","default":"./dist/cjs/index.cjs"}},"./waveform":{"import":{"types":"./dist/esm/waveform.d.ts","default":"./dist/esm/waveform.js"},"require":{"types":"./dist/cjs/waveform.d.cts","default":"./dist/cjs/waveform.cjs"}},"./mime":{"import":{"types":"./dist/esm/mime.d.ts","default":"./dist/esm/mime.js"},"require":{"types":"./dist/cjs/mime.d.cts","default":"./dist/cjs/mime.cjs"}},"./package.json":"./package.json"},"keywords":["audio","recorder","mediarecorder","waveform","headless","react","antiphony"],"scripts":{"build":"node ./scripts/clean.mjs && tsup","//prepare":"Same reason as @antiphony/shared: every export resolves into dist/, so a cold `git clone && npm ci && npm run typecheck` has nothing to typecheck against until this has run. npm runs prepare for workspace packages on install.","prepare":"npm run build","typecheck":"tsc --noEmit","lint":"eslint . --max-warnings=0","test":"vitest run"},"//peerDependencies":"React is a peer, not a dependency, so a consumer's own React is the one the hooks run on. Two React copies in one tree means two dispatchers and 'invalid hook call' at runtime — the standard failure mode for a hooks library that gets this wrong. The range matches what apps/reference and the Vox Pop clients are on.","peerDependencies":{"react":"^18 || ^19"},"devDependencies":{"@eslint/js":"^9.39.2","@testing-library/dom":"^10.4.0","@testing-library/react":"^16.1.0","@types/react":"^19.0.7","eslint":"^9.16.0","jsdom":"^25.0.1","react":"^19.0.0","react-dom":"^19.0.0","tsup":"^8.5.1","typescript":"^5.7.2","typescript-eslint":"^8.18.0","vitest":"^4.1.9"},"publishConfig":{"access":"public"},"gitHead":"7e21a2e79fe2d706cbd51eb60bd9c3da29654b32","_id":"@antiphony/capture-kit@0.1.0","_nodeVersion":"22.22.3","_npmVersion":"12.0.2","dist":{"integrity":"sha512-+lceWg135OLg2nrgWrKzgP8tvrhNiz27ElL+d/oYqXISct4YA3tmftrVyduEaBPLWR0u3uRvwsPdixCxOe4v/g==","shasum":"b77b034635f1797135466a074021c5c53713b8cf","tarball":"https://registry.npmjs.org/@antiphony/capture-kit/-/capture-kit-0.1.0.tgz","fileCount":17,"unpackedSize":52733,"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEQCIC94rgK5PFGjs83fhfATWwZWcsxNqj2kZf9n4s8D8r21AiASuqmTT70UNiILOBfIeh1SDweM9DcWjs8eG14V5VMYMw=="}]},"_npmUser":{"name":"bbthorson","email":"bbthorson@gmail.com"},"directories":{},"maintainers":[{"name":"bbthorson","email":"bbthorson@gmail.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/capture-kit_0.1.0_1788639707010_0.189734950672791"},"_hasShrinkwrap":false}},"time":{"created":"2026-09-05T20:21:46.828Z","0.1.0":"2026-09-05T20:21:47.149Z","modified":"2026-09-05T20:21:47.374Z"},"maintainers":[{"name":"bbthorson","email":"bbthorson@gmail.com"}],"description":"Headless browser audio primitives for Antiphony clients — a microphone recorder, a playback hook, and client-side waveform peaks. Renders nothing, styles nothing, uploads nothing.","homepage":"https://docs.antiphony.dev","keywords":["audio","recorder","mediarecorder","waveform","headless","react","antiphony"],"repository":{"type":"git","url":"git+https://github.com/bbthorson/antiphony.git","directory":"packages/capture-kit"},"bugs":{"url":"https://github.com/bbthorson/antiphony/issues"},"license":"MIT","readme":"# @antiphony/capture-kit\n\nHeadless browser audio primitives for [Antiphony](https://docs.antiphony.dev) clients: a microphone recorder, a playback hook, and the waveform helper that produces the peaks `dev.antiphony.embed.audio` carries.\n\n```bash\nnpm install @antiphony/capture-kit\n```\n\nReact `^18 || ^19` is a peer dependency, so the hooks run on your React.\n\n```tsx\nimport { useAudioRecorder, useAudioPlayer, computeWaveform } from '@antiphony/capture-kit';\n```\n\n## Headless, and what that excludes\n\nThe hooks render nothing and style nothing. They return state and handlers; what you draw is yours.\n\nThe kit stops where product judgement starts. It does **not** upload — `useAudioRecorder` hands back a `Blob` and is finished, because the endpoint, the credential and the idempotency story are app-layer concerns. It does **not** know what a session is. And it carries no design language: `AudioPlayer` is a worked example so the reference app has something to render, not a component to theme.\n\nThat boundary is the same one the platform draws everywhere else. Antiphony owns the bytes and the services that derive facts about them; the app connecting to it owns what any of that means to a user. Recording audio is a fact about bytes — every client needs the identical state machine — so it lives here.\n\n## Exports\n\n| | |\n|---|---|\n| `useAudioRecorder(options?)` | MediaRecorder as a state machine. `{ status, recording, elapsedMs, error, errorKind, analyser, start, stop, reset }`. `maxDurationMs` auto-stops; `analyser: true` opts into a live `AnalyserNode`; the mic is released on unmount. |\n| `useAudioPlayer({ url, durationMs?, crossOrigin? })` | Playback without an `<audio>` element in your tree. `{ status, currentTimeMs, durationMs, progress, error, play, pause, toggle, seek, seekToProgress }`. |\n| `computeWaveform(blob, buckets?)` | 0–100 integer peaks, lexicon-shaped. Also at `@antiphony/capture-kit/waveform`, which imports **no React**. |\n| `AudioPlayer` | A minimal transport UI built from `useAudioPlayer`. A demonstration, not a design system. |\n| `pickMimeType()` | What MediaRecorder will actually give this browser, if you need to know before recording. |\n| `normalizeAudioMimeType(type, filename, fallback?)` | Any audio blob's type → a bare, uploadable MIME. Strips codec parameters; falls back to the filename when the blob claims none. Both also at `@antiphony/capture-kit/mime`, which imports **no React**. |\n\nFull walkthrough: **<https://docs.antiphony.dev/build-your-own/capture-kit/>**\n\n## License\n\nMIT — see [LICENSE](./LICENSE).\n","readmeFilename":"README.md","_rev":"1-3fec531ff99751c172f2bf5762dbd15b"}