@cosyte/cli 0.0.1 → 0.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -9,11 +9,81 @@ this file is maintained by hand (Changesets handles the version bump and publish
9
9
 
10
10
  ## [Unreleased]
11
11
 
12
- The first pre-alpha release (`0.0.1`) will ship the initial public API surface. The package begins
13
- its public history at `0.0.x`, per the cosyte version ladder (`0.0.x` until first alpha).
12
+ ### Fixed
13
+
14
+ - **The public surface now states that `0.0.1` is published and uninstallable (ASSETS-P8).** `0.0.1`
15
+ published on 2026-07-29 with all ten `file:vendor/*.tgz` dependency specifiers intact. `vendor/` is
16
+ not in `files` and there is no `bundledDependencies`, so every install route (`npm i`, `npm i -g`,
17
+ `npx`) fails with `ENOENT` on `node_modules/@cosyte/cli/vendor/cosyte-fhir-0.0.0.tgz`. Reproduced
18
+ in a clean directory. A published version is immutable (ADR 0001), so `0.0.1` stays broken and the
19
+ fix must ship as a later version.
20
+ - `README.md` gains a **"Known issue"** section stating what fails, the exact error, why, and that
21
+ a source checkout is the only workaround. `docs-content/installation.md` gains the same under
22
+ **"Installing fails today"**. Both copies of the broken `npx`-based MCP registration snippet are
23
+ annotated (`README.md` and `docs-content/mcp.md`).
24
+ - **Four false claims corrected.** (1) `README.md` said "not yet published to npm"; it is
25
+ published. (2) It described swapping the vendored sibling deps for real `@cosyte/*` npm ranges as
26
+ a step still to come "at that flip"; the flip already happened without the swap, which is the
27
+ defect. (3) The same "not yet published" claim appeared in **three** `docs-content/` pages. (4)
28
+ The `redact`/`deid` terminal diagnostic, the `--help` text, three JSDoc blocks that compile into
29
+ `dist/*.d.ts`, and **five** docs pages said `@cosyte/deid` was unpublished, unshipped, or unbuilt;
30
+ it is published at `0.0.2`, and the accurate statement is that the CLI does not wire it yet. Every
31
+ count here was re-derived by census of the base tree, not estimated.
32
+ - **The "all eight formats" claim was checked and is correct**: `CosyteFormat` and `OP_SUPPORT` both
33
+ enumerate exactly eight.
34
+ - `RELEASING.md` records that the documented dependency-swap step was skipped, that a green
35
+ `npm publish --dry-run` cannot catch this (it packs a tarball but never resolves its deps from a
36
+ registry), and adds a checklist step to install the published version from outside the repo.
37
+ - **The route to an installable release, recorded in `RELEASING.md` and verified against the
38
+ registry.** `@cosyte/hl7` (`0.0.3`), `@cosyte/terminology` (`0.0.4`) and all six breadth parsers
39
+ would swap to real ranges today. `@cosyte/fhir` is unpublished (`FHIR-NPM-NAME`, an npm E403
40
+ name-similarity rejection) and `@cosyte/transform@0.0.2` fails `E404` on its `@cosyte/fhir` peer,
41
+ so neither can. An installable release is nonetheless reachable before that unblocks, because npm
42
+ tolerates an `optionalDependency` that fails to resolve (measured). It needs a code change first:
43
+ `@cosyte/fhir` and `@cosyte/transform` are imported with a raw `await import()`, so they must be
44
+ routed through a guarded loader to degrade to `CLI_PARSER_UNAVAILABLE` (exit `69`) rather than
45
+ crash. `loadOptional()` cannot be reused unchanged: it takes a `CosyteFormat`, and `"transform"` is
46
+ not one, and its diagnostic hardcodes the word "parser". Not undertaken here.
14
47
 
15
48
  ### Added
16
49
 
50
+ - **`README.md` now opens with the shared Cosyte lockup in a `<picture>` block, above the H1.** The
51
+ dark-ground tile (`cosyte-lockup-tile-on-dark-1200x300.png`) sits behind a
52
+ `prefers-color-scheme: dark` media query and the light-ground tile
53
+ (`cosyte-lockup-tile-on-light-1200x300.png`) is the inner `<img>` fallback, so the mark is read on
54
+ a ground that matches the page it is read on. The `# @cosyte/cli` heading and the blockquote under
55
+ it are unchanged: the artwork reads "Cosyte" and the heading names the package, so nothing on the
56
+ page is duplicated. Both URLs were re-checked immediately before the push and returned
57
+ `200 image/png` (10513 bytes dark, 10455 light). The block was copied byte for byte out of
58
+ `@cosyte/hl7`'s `README.md` rather than retyped and diffed against it, because a transcription
59
+ error in one of these URLs is a broken image on a public package page.
60
+
61
+ **This replaces the per-package banner added earlier in the same unreleased window, and the reason
62
+ it replaces it is recorded rather than dropped.** That banner was a plain markdown image, chosen
63
+ over `<img>` or `<picture>` on the stated ground that whether npm's markdown sanitizer preserves a
64
+ `<picture>` element was unverified. That was an accurate account of what was known when it was
65
+ written, and it has since been measured: **GitHub honours the `prefers-color-scheme` switch**
66
+ (observed on `@cosyte/astm` in dark mode, where the rendered image's `currentSrc` resolves to the
67
+ on-dark tile and its parent element is `PICTURE`), and **on the npm package page the `<img>` is
68
+ hoisted out of its `<picture>` by the anchor wrapper** rather than the element being stripped, so
69
+ the light cut renders, which is the correct one there because npmjs.com has no dark mode. Those two
70
+ measurements were taken on `astm` and reported into this repo rather than re-taken here; what was
71
+ re-checked directly for `cli` is that both tile URLs return `200 image/png`. The failure mode is
72
+ safe either way: a renderer that strips `<source>` renders the inner `<img>`, so the worst case is
73
+ a light-ground mark on a dark page, never a missing or broken image.
74
+
75
+ **Why this is corrected rather than annotated in place.** `0.0.1` published on 2026-07-29, a day
76
+ before the banner landed, so no `@cosyte/cli` tarball has ever carried the banner or the sentence
77
+ announcing it. Annotating an entry no consumer received would publish an addition and its
78
+ replacement as two changes when only one was ever visible, so the banner entry is removed from this
79
+ release and its reasoning is carried here instead of being silently reversed.
80
+
81
+ The alt text describes the artwork, a plus mark set in two overlapping rounded squares beside the
82
+ Cosyte wordmark, rather than the package. It is what a screen reader on the npm page reads out and
83
+ what a reader gets when the image fails to load, so repeating the `@cosyte/cli` heading below it
84
+ would be a wasted line. The wording is the one eight sibling packages already carry, confirmed
85
+ against both rendered PNGs here rather than copied on trust.
86
+
17
87
  - **Phase 7: release hardening (the final roadmap phase; the CLI is feature-complete).** No new
18
88
  runtime command surface: this phase is publish-readiness.
19
89
  - **Fuzz gate over the two input boundaries.** `test/fuzz.property.test.ts` fuzzes the terminal
package/README.md CHANGED
@@ -1,3 +1,8 @@
1
+ <picture>
2
+ <source media="(prefers-color-scheme: dark)" srcset="https://cosyte.com/tile/cosyte-lockup-tile-on-dark-1200x300.png">
3
+ <img alt="Cosyte: a plus mark set in two overlapping rounded squares, one solid and one outlined, beside the Cosyte wordmark" src="https://cosyte.com/tile/cosyte-lockup-tile-on-light-1200x300.png">
4
+ </picture>
5
+
1
6
  # @cosyte/cli
2
7
 
3
8
  > The **cosyte CLI**: a PHI-safe developer front door over the `@cosyte/*` healthcare parsers.
@@ -17,7 +22,37 @@ It is a thin, honest skin over libraries that already own correctness ([`@cosyte
17
22
  and owns two disciplines of its own: a documented **exit-code contract** and a **value-free
18
23
  diagnostic** posture.
19
24
 
20
- > **Status:** pre-alpha (`0.0.x`), **not yet published to npm**. The `cosyte` command wraps **all eight
25
+ ## Known issue: `0.0.1` is published but cannot be installed
26
+
27
+ **`@cosyte/cli@0.0.1` is on npm and `npm install @cosyte/cli` fails.** It ends in an `ENOENT`, like
28
+ this:
29
+
30
+ ```
31
+ npm error code ENOENT
32
+ npm error path node_modules/@cosyte/cli/vendor/cosyte-fhir-0.0.0.tgz
33
+ npm error enoent ENOENT: no such file or directory
34
+ ```
35
+
36
+ `npx @cosyte/cli …` and `npm install -g @cosyte/cli` fail the same way, and so does the `npx`-based
37
+ MCP server registration below. There is no workaround from the consumer side. **Nothing is wrong with
38
+ your setup, and re-running it will not help.**
39
+
40
+ **Why.** The published manifest declares its ten `@cosyte/*` sibling packages as local file paths
41
+ (`file:vendor/*.tgz`) rather than as npm version ranges. Those tarballs live in the git repository and
42
+ are deliberately not part of the published package, so npm resolves the paths against a directory that
43
+ does not exist in your `node_modules` and stops at the first one. It is a packaging defect in that
44
+ release, not a fault in any command.
45
+
46
+ **A published version is immutable, so `0.0.1` will stay broken.** The fix has to arrive as a later
47
+ version, and it is blocked on something outside this package: `@cosyte/fhir` is not on npm yet (its
48
+ name was rejected by the registry as too similar to an existing package, which is a naming problem
49
+ rather than missing work), and `@cosyte/transform` is on npm but currently fails to install for the
50
+ same reason, because it peer-depends on `@cosyte/fhir`. `@cosyte/hl7` and `@cosyte/terminology` are
51
+ published and would swap over today. Until the naming issue is resolved, run the CLI from a source
52
+ checkout (`pnpm install && pnpm build`, then invoke `dist/bin/cosyte.mjs`).
53
+
54
+ > **Status:** pre-alpha (`0.0.x`), published to npm at `0.0.1`, which **cannot be installed** (see
55
+ > above). The `cosyte` command wraps **all eight
21
56
  > cosyte formats** (**HL7 v2**, **FHIR R4**, **X12**, **ASTM**, **NCPDP SCRIPT**, **C-CDA**, **DICOM**,
22
57
  > and **MLLP**) plus the `@cosyte/transform` and `@cosyte/terminology` higher-layer libraries, with
23
58
  > conservative content-format autodetection and a documented exit-code contract:
@@ -34,8 +69,8 @@ diagnostic** posture.
34
69
  > free issues on stderr, and a non-zero exit on an error-severity conversion issue.
35
70
  > - **`map-codes`**: translate a code through a BYO FHIR ConceptMap via `@cosyte/terminology`; the
36
71
  > target coding(s) on stdout, or a value-free unmapped signal + exit `1`.
37
- > - **`redact` / `deid`**: gated to an honest `CLI_NOT_IMPLEMENTED` (exit `69`) until `@cosyte/deid`
38
- > ships; it never reads the input and never emits a partial scrub dressed up as de-identified.
72
+ > - **`redact` / `deid`**: gated to an honest `CLI_NOT_IMPLEMENTED` (exit `69`) until the CLI wires
73
+ > `@cosyte/deid`; it never reads the input and never emits a partial scrub dressed up as de-identified.
39
74
  > - **`completion <bash|zsh|fish>`**: print a static shell completion script.
40
75
  >
41
76
  > **Support is honest per (format, operation)**: not every parser faithfully supports every command, so
@@ -45,16 +80,20 @@ diagnostic** posture.
45
80
  > as the single door to a value on a secondary surface, and never a temp file with PHI. An **MCP server**
46
81
  > (`cosyte-mcp`) exposes the same core to an LLM/agent as callable tools.
47
82
  >
48
- > The CLI is **feature-complete and release-hardened**: an argv+stdin+MCP fuzz
49
- > gate, an exit-code golden matrix, a built-package smoke of both bins, and a clean `npm publish`
50
- > dry-run. What remains is the two standing founder stops (flipping the repo public and the real
51
- > `npm publish`) plus swapping the vendored sibling deps for real `@cosyte/*` npm ranges at that flip.
52
- > See [RELEASING.md](./RELEASING.md).
83
+ > The CLI is **feature-complete**: an argv+stdin+MCP fuzz gate, an exit-code golden matrix, a
84
+ > built-package smoke of both bins, and a clean `npm publish` dry-run. Those gates cover the code, and
85
+ > the code is not what is broken. The one release step they do not cover is the dependency swap
86
+ > described above, which is why `0.0.1` published green and still cannot be installed: a dry-run
87
+ > builds the tarball but never resolves it from a registry. **The swap is blocked, not scheduled**,
88
+ > and it stays blocked until `@cosyte/fhir` can be published under a name npm accepts, which also
89
+ > unblocks `@cosyte/transform`. See [RELEASING.md](./RELEASING.md).
53
90
 
54
91
  ## Run it
55
92
 
56
- > Not on npm yet. The commands below are how you'll install and run it **once it's published**.
57
- > Until then, run it from a local checkout (`pnpm build`, then invoke `dist/bin/cosyte.mjs`).
93
+ > **None of the commands in this section work today.** `@cosyte/cli` is on npm, but every install
94
+ > route fails with the `ENOENT` described in [the known issue](#known-issue-001-is-published-but-cannot-be-installed)
95
+ > above. They are recorded here as the shape install will take once a fixed version can ship. Until
96
+ > then, run it from a local checkout (`pnpm install && pnpm build`, then invoke `dist/bin/cosyte.mjs`).
58
97
 
59
98
  ```bash
60
99
  npx @cosyte/cli parse message.hl7 # no install; format autodetected → HL7 v2
@@ -207,13 +246,14 @@ cosyte parse broken.hl7 --format hl7 --unsafe-show-values # appends a bounded i
207
246
  ## `cosyte redact` / `cosyte deid`
208
247
 
209
248
  De-identification is the one operation whose _job_ is to strip PHI. It is **not implemented yet, on
210
- purpose.** It belongs to [`@cosyte/deid`](https://github.com/cosyte/deid), which is not published, and
211
- the wrapped parsers expose no de-identification API. A built-in "minimal Safe-Harbor" pass over only
249
+ purpose.** It belongs to [`@cosyte/deid`](https://github.com/cosyte/deid). That package is now
250
+ published, but the CLI does not wire it yet, and the wrapped parsers expose no de-identification API of
251
+ their own. A built-in "minimal Safe-Harbor" pass over only
212
252
  the obvious fields would leave PHI behind and _look_ de-identified while silently under-redacting: the
213
253
  exact false-safety hazard `redact` exists to avoid. So `cosyte redact <file>` is an honest, typed
214
254
  `CLI_NOT_IMPLEMENTED` (exit `69`, `EX_UNAVAILABLE`) that **never reads your input** and **never emits a
215
- partial scrub dressed up as safe**. It will produce a real de-identified copy once `@cosyte/deid`
216
- ships and is vetted.
255
+ partial scrub dressed up as safe**. It will produce a real de-identified copy once the CLI wires
256
+ `@cosyte/deid` and that integration is vetted.
217
257
 
218
258
  ## `cosyte completion`
219
259
 
@@ -239,6 +279,11 @@ subprocess**, not a hosted endpoint. Register it in an MCP client's config:
239
279
  }
240
280
  ```
241
281
 
282
+ > This registration **does not work yet**: `npx` has to install the package first, and that install
283
+ > fails with the `ENOENT` described in
284
+ > [the known issue](#known-issue-001-is-published-but-cannot-be-installed) above. To run the MCP
285
+ > server today, point `command` at a built local checkout's `dist/bin/cosyte-mcp.mjs` instead.
286
+
242
287
  `cosyte mcp` and the standalone `cosyte-mcp` bin both start the stdio server. It exposes four tools
243
288
  (`parse`, `validate`, `inspect`, `convert`), each calling the same command the terminal runs, so the CLI
244
289
  and the agent get identical results. The PHI posture is inherited and hardened: there is **no
@@ -23,7 +23,7 @@ var EXIT = {
23
23
  DATAERR: 65,
24
24
  /** No input: the named file does not exist or is unreadable (`EX_NOINPUT`). */
25
25
  NOINPUT: 66,
26
- /** Unavailable: a required capability is not yet built (e.g. `redact` before `@cosyte/deid`), a
26
+ /** Unavailable: a required capability is not yet wired (e.g. `redact` before `@cosyte/deid`), a
27
27
  * distinct non-zero signal that is never a fake success (`EX_UNAVAILABLE`). */
28
28
  UNAVAILABLE: 69,
29
29
  /** Internal error: an unexpected exception (a bug), distinct from a handled bad input (`EX_SOFTWARE`). */
@@ -51,8 +51,8 @@ var CLI_CODES = {
51
51
  CLI_PARSER_UNAVAILABLE: "CLI_PARSER_UNAVAILABLE",
52
52
  /** The wrapped parser rejected the input. Positional context only, never the offending bytes. Exit `65`. */
53
53
  CLI_PARSE_FAILED: "CLI_PARSE_FAILED",
54
- /** A command whose ground-layer library is not yet built (e.g. `redact` before `@cosyte/deid`
55
- * ships). Never a fake success: a distinct, value-free "unavailable" signal. Exit `69`. */
54
+ /** A command whose ground-layer library is not yet wired (e.g. `redact` before `@cosyte/deid` is
55
+ * wired). Never a fake success: a distinct, value-free "unavailable" signal. Exit `69`. */
56
56
  CLI_NOT_IMPLEMENTED: "CLI_NOT_IMPLEMENTED",
57
57
  /** An unexpected internal error (a bug). Exit `70`. */
58
58
  CLI_INTERNAL: "CLI_INTERNAL"