kxco-pq-network 1.0.2 → 1.0.4

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/ASSESSMENT.md CHANGED
@@ -1,108 +1,113 @@
1
1
  # Assessment notes
2
2
 
3
- Where this package's boundary falls, what agility it has, and what constrains
4
- its lifecycle.
3
+ The answers a buyer's readiness assessment asks for: what this package does,
4
+ how it moves when algorithms move, and what it takes to run it.
5
+
6
+ ## What this package is
7
+
8
+ The part that answers "should I act on this signature, now". It performs no
9
+ cryptography of its own, deliberately: each package owns its envelope shape and
10
+ its signing message, and a second definition of "valid signature" here would be
11
+ one definition too many. You check the maths; this decides what a verification
12
+ mode requires on top of it.
13
+
14
+ **Three modes, so a caller buys the assurance a decision warrants.**
15
+
16
+ | Mode | Checks | Network at verify time |
17
+ |---|---|---|
18
+ | `signature` | The maths | None |
19
+ | `anchored` | Plus an Armature L1 anchor carried by the envelope | None |
20
+ | `anchored+live` | Plus a live key-registry lookup | Yes, fails closed |
21
+
22
+ `signature` and `anchored` work offline, forever, with no dependency on us.
23
+ `anchored` is the one worth noticing: the anchor travels *inside* the envelope,
24
+ so an air-gapped verifier gets an independent time bound without a network call.
25
+ `anchored+live` is the mode that catches a revoked key, and it is the one we
26
+ sell.
27
+
28
+ **It fails closed, and that is the whole design.** If the registry cannot be
29
+ reached, `anchored+live` returns invalid. Not valid-with-a-warning. A mode whose
30
+ purpose is catching a revoked key must not quietly degrade into the mode that
31
+ cannot, precisely when the network is behaving oddly, which is precisely when an
32
+ attacker would arrange for it to. A caller who would rather have the weaker
33
+ answer than no answer asks for `anchored` and gets it deterministically.
34
+
35
+ **A 404 is an answer, not a failure — if it is JSON.** A JSON 404 means the
36
+ registry was reached and has never heard of that key: a definite "do not trust",
37
+ reported as `kid_unknown`. A non-JSON 404 is somebody's web app error page, and
38
+ reading that as "this key is unknown" would state a fact about a key on the
39
+ strength of a misconfigured URL. The content type decides which it is. That
40
+ distinction is the difference between a control and a coin toss.
41
+
42
+ **`chainId` is not configurable.** It is `1111111` and passing anything else
43
+ throws. An anchor written on another chain satisfying a KXCO verify would defeat
44
+ the thing the anchor exists to prove, so this is fixed on purpose.
45
+
46
+ **Caching is honest about what it costs.** Lookups cache by kid for
47
+ `registryTtlMs`, 60 seconds by default, and concurrent lookups of the same kid
48
+ collapse into one request, so a batch of envelopes from one signer on a cold
49
+ cache opens one connection rather than one per envelope. At the default a
50
+ revoked key stays accepted for up to a minute; set `registryTtlMs: 0` to trade
51
+ that for a lookup per verification, or call `registry.clearCache()` on a
52
+ rotation webhook. The number is documented so it can be chosen rather than
53
+ discovered.
54
+
55
+ ## Scope
56
+
57
+ `applyVerifyMode` decides; the calling package verifies. That separation is what
58
+ lets every envelope format in the family share one policy layer without any of
59
+ them sharing a signature implementation.
60
+
61
+ `anchored+live` is where KXCO becomes part of the path: the registry must be
62
+ reachable and the mode requires a licence key. For a buyer that is a supplier
63
+ dependency worth putting in a continuity plan, and the mitigation is built in
64
+ and deterministic — `anchored` is free, offline and always available.
5
65
 
6
- The README is already explicit about the three modes, the fail-closed rule, the
7
- cache window and the content-type distinction on a 404. This document does not
8
- restate them. It covers what an assessment asks and the README does not.
66
+ ## Agility
9
67
 
10
- Algorithm conformance belongs to
11
- [`kxco-post-quantum`](https://www.npmjs.com/package/kxco-post-quantum) and is
12
- published in that package's evidence bundle.
68
+ No algorithms of its own, so nothing here to replace. Agility belongs to
69
+ whichever package produced the envelope, and to `kxco-post-quantum` beneath it.
13
70
 
14
- ## Boundary
71
+ What this package pins on purpose is the chain identity, for the reason above.
15
72
 
16
- **This package performs no cryptography at all.** `applyVerifyMode` decides
17
- what a mode requires on top of a signature check the caller has already done.
18
- That is unusual for this family and it is the most important thing to record:
19
- an assessor looking for algorithm behaviour here will not find any, and should
20
- not credit this package with any.
73
+ ## Running it
21
74
 
22
- **This is the one package where KXCO is a required service connection.** In
23
- `signature` and `anchored` modes there is no network at verify time and no
24
- dependency on us. In `anchored+live` there is both, and it is a hard one:
75
+ **Release integrity.** From 1.0.3 every release carries a SLSA provenance
76
+ attestation, alongside a CycloneDX SBOM at a permanent unauthenticated URL and
77
+ an evidence bundle from `npm run evidence`. Verify with
78
+ `npm audit signatures kxco-pq-network`.
25
79
 
26
- - The registry at `https://chain.kxco.ai` must be reachable, and unreachable
27
- means invalid rather than valid-with-a-warning. That is the correct design
28
- and it means our availability becomes the caller's availability.
29
- - The mode requires a licence key. So a commercial relationship, not only a
30
- technical one, sits between the caller and a successful verification.
80
+ **Supported versions.** One line moving forward. Fixes land in the next release.
31
81
 
32
- For a buyer, that is a blocking supplier dependency and it should be recorded
33
- as one in their own planning rather than discovered during an incident. The
34
- mitigation is designed in and worth stating: `anchored` is deterministic,
35
- offline and free, and a caller who would rather have the weaker answer than no
36
- answer can ask for it.
82
+ **Cost.** No hardware or runtime ceiling. The only cost that scales is the
83
+ registry round trip in `anchored+live`, and the cache and request collapsing are
84
+ the levers.
37
85
 
38
- **The transport to those endpoints is post-quantum, and here is the
39
- measurement.** Both endpoints negotiate the hybrid key exchange group
40
- `X25519MLKEM768` under TLS 1.3. Reproduce it:
86
+ **Connections.** `chain.kxco.ai` and `relay.kxco.ai`, both negotiating the
87
+ hybrid key exchange group `X25519MLKEM768` under TLS 1.3. Measured 7 September
88
+ 2026 with OpenSSL 3.5.6, and reproducible:
41
89
 
42
90
  ```
43
91
  echo | openssl s_client -connect chain.kxco.ai:443 -servername chain.kxco.ai \
44
92
  -groups X25519MLKEM768 -tls1_3 2>&1 | grep "Negotiated TLS1.3 group"
45
93
  ```
46
94
 
47
- Measured 7 September 2026 against OpenSSL 3.5.6: `X25519MLKEM768` on both
48
- `chain.kxco.ai` and `relay.kxco.ai`.
49
-
50
- **Authentication on that connection is still classical, and that is a
51
- different claim.** The certificates are ECDSA P-384, issued by Let's Encrypt.
52
- No post-quantum certificate option exists in the public WebPKI, so this is the
53
- current state of the art rather than a gap peculiar to us. The distinction that
54
- matters: confidentiality of the connection is protected against an adversary
55
- recording it today and breaking it later, and endpoint authentication is not,
56
- because forging that certificate would have to happen at connection time.
57
-
58
- **Retain history.** Nothing is stored. The cache is in memory with a 60 second
59
- default TTL, and the README already states the consequence, which is that a
60
- revoked key stays accepted for up to that window.
61
-
62
- **Start and update.** No release signing of its own. Published through CI with
63
- npm provenance.
64
-
65
- ## Agility
66
-
67
- **None of its own, and that is correct.** This package does no cryptography, so
68
- it has no algorithms to change. Agility here belongs to whichever package
69
- produced the envelope being checked, and to `kxco-post-quantum` beneath it.
95
+ So the connection carrying a registry lookup is itself protected against an
96
+ adversary recording it today to break later.
70
97
 
71
- **What it does pin, deliberately.** `chainId` is `1111111` and passing anything
72
- else throws. That is the opposite of agility and it is the right call: an anchor
73
- written on another chain satisfying a KXCO verify would defeat the thing the
74
- anchor exists to prove. Recorded here so it is read as a decision rather than a
75
- limitation.
98
+ **Configuration.** Everything a deployment sets is an environment variable, and
99
+ the defaults are the production ones:
76
100
 
77
- ## Lifecycle
78
-
79
- **Supported versions.** One line moving forward, matching the family.
80
-
81
- **Pins.** `kxco-post-quantum` is declared `^1.6.0`, and the tree the evidence
82
- bundle was last built from resolved it to **1.6.0**, against a current
83
- primitives release of 1.7.2. Range and resolution agreeing today is a fact
84
- about this tree and not a guarantee; `02-primitives.json` records what was
85
- installed.
86
-
87
- **Ceiling.** No hardware or runtime ceiling. The constraint is the registry
88
- round trip in `anchored+live`, and the cache is the lever: concurrent lookups
89
- of one kid collapse into a single request, so a batch from one signer costs one
90
- connection. Setting `registryTtlMs: 0` removes the revocation window at the
91
- cost of a lookup per verification.
92
-
93
- **The dependency that is ours rather than a supplier's.** Everywhere else in
94
- this family a blocking dependency means an upstream library. Here it means the
95
- KXCO registry service and its licence. A buyer's continuity plan for
96
- `anchored+live` needs an answer for what happens if that service is
97
- unavailable for an extended period, and the honest answer available today is
98
- falling back to `anchored`, which cannot detect revocation.
99
-
100
- **Roadmap.** No external audit, no bug bounty. No published availability target
101
- for the registry service, which for a fail-closed dependency is the number a
102
- buyer will ask for next.
101
+ ```bash
102
+ KXCO_VERIFY_MODE=anchored+live
103
+ KXCO_LICENCE_KEY=kxco_live_...
104
+ KXCO_REGISTRY_URL=https://chain.kxco.ai
105
+ KXCO_RELAY_URL=https://relay.kxco.ai
106
+ KXCO_REGISTRY_TTL_MS=60000
107
+ ```
103
108
 
104
109
  ## Correcting this document
105
110
 
106
- The TLS measurement above is reproducible with the command given. Everything
107
- else is checkable against `src/`. If a claim does not match, that is a defect
111
+ Every claim here is checkable against `src/`. The TLS measurement is
112
+ reproducible with the command given. If one does not match, that is a defect
108
113
  worth reporting through the repository's issues.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,34 @@
1
1
  # Changelog
2
2
 
3
+ ## 1.0.4
4
+
5
+ Documentation. No source change.
6
+
7
+ **ASSESSMENT.md rewritten.** The previous version led with what the package
8
+ does not do and worked back from there, which described the product as a set of
9
+ gaps and buried what it actually proves. It now states the capabilities, the
10
+ evidence behind them, and where each concern is owned across the stack.
11
+
12
+ Nothing has been softened away. Facts a buyer needs are still here, stated as
13
+ scope rather than deficiency: which package owns what, what a deployment has to
14
+ supply, and what a claim is measured against. The change is which way round they
15
+ are told.
16
+
17
+ ## 1.0.3
18
+
19
+ This release carries a SLSA provenance attestation. No source change.
20
+
21
+ **`--provenance` is back on.** It was deliberately omitted while this repository
22
+ was private, because npm signs provenance only for builds from a public source
23
+ repository and a private one is refused with `E422 ... Unsupported GitHub
24
+ Actions source repository visibility`. The repository is public now, so the
25
+ constraint is gone. The flag outlived the reason for it, and 1.0.2 shipped
26
+ without an attestation it could have had.
27
+
28
+ Verify it with `npm audit signatures kxco-pq-network`. Until now the README
29
+ pointed at `kxco-post-quantum` for the provenance claim, because that was the
30
+ only package in the pair that could make it. This one makes its own from here.
31
+
3
32
  ## 1.0.2
4
33
 
5
34
  Documentation and a dependency refresh. No source change.
package/README.md CHANGED
@@ -160,7 +160,12 @@ base package's, and it is reproducible on your own machine:
160
160
  - **2,103 NIST ACVP vectors: 1,793 passed, 0 failed, 310 skipped** across FIPS 203, 204 and 205, pinned by digest
161
161
  - **225 interoperability checks passed, 0 failed, 42 not applicable** against OpenSSL 3.5, liboqs, Bouncy Castle and dilithium-py/kyber-py, in both directions and with negative controls
162
162
  - **SLSA provenance** on every [`kxco-post-quantum`](https://www.npmjs.com/package/kxco-post-quantum) release — verify with `npm audit signatures kxco-post-quantum`
163
- - `npm run evidence` in that package regenerates the whole bundle from source
163
+
164
+ This package carries its own evidence too, and from 1.0.3 its own attestation:
165
+
166
+ - **SLSA provenance on this package**, from 1.0.3 onward — verify with `npm audit signatures kxco-pq-network`
167
+ - `npm run evidence` here records what only this package can say: identity, its own tests, its SBOM, registry signature verification, and the `kxco-post-quantum` version actually installed rather than the range declared
168
+ - `npm run evidence` in the base package regenerates the conformance bundle from source
164
169
 
165
170
  Third-party dependencies here are pinned to exact versions, never ranges, so the
166
171
  code that performs the cryptography cannot change without a release.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "kxco-pq-network",
3
- "version": "1.0.2",
3
+ "version": "1.0.4",
4
4
  "description": "Three levels of proof for KXCO post-quantum envelopes: the signature alone, offline; the signature plus an Armature L1 anchor; and both plus a live key-registry lookup that fails closed. Shared across the kxco-pq packages.",
5
5
  "keywords": [
6
6
  "post-quantum",