@blamejs/core 0.14.5 → 0.14.7
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 +4 -0
- package/README.md +4 -2
- package/lib/agent-event-bus.js +4 -4
- package/lib/agent-idempotency.js +6 -6
- package/lib/agent-orchestrator.js +9 -9
- package/lib/agent-posture-chain.js +10 -10
- package/lib/agent-saga.js +6 -7
- package/lib/agent-snapshot.js +8 -8
- package/lib/agent-stream.js +3 -3
- package/lib/agent-tenant.js +4 -4
- package/lib/agent-trace.js +5 -5
- package/lib/ai-disclosure.js +3 -3
- package/lib/app.js +2 -2
- package/lib/archive-read.js +1 -1
- package/lib/archive-tar-read.js +1 -1
- package/lib/archive-wrap.js +5 -5
- package/lib/audit-tools.js +65 -5
- package/lib/audit.js +2 -2
- package/lib/auth/ciba.js +1 -1
- package/lib/auth/dpop.js +1 -1
- package/lib/auth/fal.js +1 -1
- package/lib/auth/fido-mds3.js +2 -3
- package/lib/auth/jwt-external.js +2 -2
- package/lib/auth/oauth.js +9 -9
- package/lib/auth/oid4vci.js +7 -7
- package/lib/auth/oid4vp.js +1 -1
- package/lib/auth/openid-federation.js +5 -5
- package/lib/auth/passkey.js +6 -6
- package/lib/auth/saml.js +1 -1
- package/lib/auth/sd-jwt-vc.js +3 -6
- package/lib/backup/index.js +18 -18
- package/lib/cache.js +4 -4
- package/lib/calendar.js +5 -5
- package/lib/circuit-breaker.js +1 -1
- package/lib/cms-codec.js +2 -2
- package/lib/compliance.js +14 -14
- package/lib/cra-report.js +3 -3
- package/lib/crypto-field.js +58 -21
- package/lib/crypto.js +5 -6
- package/lib/db-query.js +131 -9
- package/lib/db.js +106 -22
- package/lib/external-db.js +64 -16
- package/lib/framework-schema.js +4 -4
- package/lib/guard-list-id.js +2 -2
- package/lib/guard-list-unsubscribe.js +1 -2
- package/lib/incident-report.js +150 -0
- package/lib/mail-crypto-smime.js +1 -1
- package/lib/mail-deploy.js +3 -3
- package/lib/mail-server-managesieve.js +2 -2
- package/lib/mail-server-pop3.js +2 -2
- package/lib/mail-store.js +1 -1
- package/lib/metrics.js +8 -8
- package/lib/middleware/age-gate.js +20 -7
- package/lib/middleware/bearer-auth.js +36 -35
- package/lib/middleware/bot-guard.js +17 -5
- package/lib/middleware/cors.js +28 -12
- package/lib/middleware/csrf-protect.js +23 -15
- package/lib/middleware/daily-byte-quota.js +27 -13
- package/lib/middleware/deny-response.js +140 -0
- package/lib/middleware/dpop.js +37 -24
- package/lib/middleware/fetch-metadata.js +21 -12
- package/lib/middleware/host-allowlist.js +19 -8
- package/lib/middleware/idempotency-key.js +21 -22
- package/lib/middleware/index.js +3 -0
- package/lib/middleware/network-allowlist.js +24 -10
- package/lib/middleware/protected-resource-metadata.js +2 -2
- package/lib/middleware/rate-limit.js +22 -5
- package/lib/middleware/require-aal.js +25 -10
- package/lib/middleware/require-auth.js +32 -16
- package/lib/middleware/require-bound-key.js +49 -18
- package/lib/middleware/require-content-type.js +19 -8
- package/lib/middleware/require-methods.js +17 -7
- package/lib/middleware/require-mtls.js +27 -14
- package/lib/network-dns-resolver.js +2 -2
- package/lib/network-dns.js +1 -2
- package/lib/network-tls.js +0 -1
- package/lib/network.js +4 -4
- package/lib/outbox.js +1 -1
- package/lib/pqc-agent.js +1 -1
- package/lib/retention.js +1 -1
- package/lib/retry.js +1 -1
- package/lib/safe-archive.js +2 -2
- package/lib/safe-ical.js +2 -2
- package/lib/safe-mime.js +1 -1
- package/lib/self-update-standalone-verifier.js +1 -1
- package/lib/self-update.js +2 -2
- package/lib/static.js +1 -1
- package/lib/subject.js +2 -2
- package/lib/vault/index.js +64 -1
- package/lib/vault/rotate.js +19 -0
- package/lib/vendor-data.js +1 -1
- package/package.json +1 -1
- package/sbom.cdx.json +6 -6
package/lib/network.js
CHANGED
|
@@ -108,8 +108,8 @@ function _socketDefaults() {
|
|
|
108
108
|
}
|
|
109
109
|
|
|
110
110
|
/**
|
|
111
|
-
* @primitive b.network.applyToSocket
|
|
112
|
-
* @signature b.network.applyToSocket(socket)
|
|
111
|
+
* @primitive b.network.socket.applyToSocket
|
|
112
|
+
* @signature b.network.socket.applyToSocket(socket)
|
|
113
113
|
* @since 0.7.68
|
|
114
114
|
* @related b.network.bootFromEnv, b.network.snapshot
|
|
115
115
|
*
|
|
@@ -124,7 +124,7 @@ function _socketDefaults() {
|
|
|
124
124
|
* @example
|
|
125
125
|
* var net = require("net");
|
|
126
126
|
* var s = new net.Socket();
|
|
127
|
-
* var ret = b.network.applyToSocket(s);
|
|
127
|
+
* var ret = b.network.socket.applyToSocket(s);
|
|
128
128
|
* ret === s;
|
|
129
129
|
* // → true
|
|
130
130
|
* s.destroy();
|
|
@@ -164,7 +164,7 @@ var ntpFacade = {
|
|
|
164
164
|
* @primitive b.network.bootFromEnv
|
|
165
165
|
* @signature b.network.bootFromEnv(opts)
|
|
166
166
|
* @since 0.7.68
|
|
167
|
-
* @related b.network.snapshot, b.network.applyToSocket
|
|
167
|
+
* @related b.network.snapshot, b.network.socket.applyToSocket
|
|
168
168
|
*
|
|
169
169
|
* Read `BLAMEJS_*` environment variables once and apply the union to
|
|
170
170
|
* the live network facade. Recognised keys cover NTP servers /
|
package/lib/outbox.js
CHANGED
|
@@ -342,7 +342,7 @@ function create(opts) {
|
|
|
342
342
|
var stopping = false;
|
|
343
343
|
var inFlight = null;
|
|
344
344
|
|
|
345
|
-
//
|
|
345
|
+
// `FOR UPDATE SKIP LOCKED` is Postgres / MySQL 8+ only.
|
|
346
346
|
// SQLite (single-writer at the DB level, but WAL mode lets multiple
|
|
347
347
|
// processes share the file with concurrent SELECTs) doesn't support
|
|
348
348
|
// SKIP LOCKED — feeding it Postgres syntax silently double-publishes
|
package/lib/pqc-agent.js
CHANGED
|
@@ -322,7 +322,7 @@ function _getDefaultAgent() {
|
|
|
322
322
|
* logger.info("pqc-agent reloaded", res);
|
|
323
323
|
*/
|
|
324
324
|
function reload() {
|
|
325
|
-
//
|
|
325
|
+
// Null the cached agent BEFORE calling destroy. The
|
|
326
326
|
// previous order let a concurrent _getDefaultAgent() see the
|
|
327
327
|
// destroyed-not-null agent and hand it to a caller; the caller
|
|
328
328
|
// then tries to issue a request through a torn-down keep-alive
|
package/lib/retention.js
CHANGED
|
@@ -569,7 +569,7 @@ function complianceFloor(posture, candidateTtlMs) {
|
|
|
569
569
|
return candidateTtlMs > floor ? candidateTtlMs : floor;
|
|
570
570
|
}
|
|
571
571
|
|
|
572
|
-
// applyPosture —
|
|
572
|
+
// applyPosture — cascade hook. b.compliance.set(posture)
|
|
573
573
|
// calls this to merge posture defaults into retention's state. The
|
|
574
574
|
// retention module itself doesn't carry per-instance global defaults;
|
|
575
575
|
// the cascade's job here is to surface the posture's audit-log
|
package/lib/retry.js
CHANGED
|
@@ -275,7 +275,7 @@ function backoffDelay(attempt, opts) {
|
|
|
275
275
|
opts = opts || DEFAULT_RETRY;
|
|
276
276
|
var base = opts.baseDelayMs * Math.pow(2, attempt - 1);
|
|
277
277
|
var capped = Math.min(base, opts.maxDelayMs);
|
|
278
|
-
//
|
|
278
|
+
// Jitter exists to spread retry storms across the
|
|
279
279
|
// millisecond window so N peer clients waking from the same
|
|
280
280
|
// upstream outage don't all hit the recovering service at the same
|
|
281
281
|
// tick. The value is observable to every client by construction
|
package/lib/safe-archive.js
CHANGED
|
@@ -225,7 +225,7 @@ async function extract(opts) {
|
|
|
225
225
|
}
|
|
226
226
|
inner = await archiveWrap().unwrapWithPassphrase(sealedBytes, { passphrase: opts.passphrase });
|
|
227
227
|
}
|
|
228
|
-
//
|
|
228
|
+
// Close the original source
|
|
229
229
|
// adapter BEFORE replacing it. When opts.source was a string
|
|
230
230
|
// path, the fs adapter opened a file descriptor; overwriting
|
|
231
231
|
// `source` loses the close reference and the descriptor
|
|
@@ -236,7 +236,7 @@ async function extract(opts) {
|
|
|
236
236
|
if (typeof source.close === "function" && typeof opts.source === "string") {
|
|
237
237
|
try { source.close(); } catch (_e) { /* drop-silent */ }
|
|
238
238
|
}
|
|
239
|
-
//
|
|
239
|
+
// Forward opts.signal to the
|
|
240
240
|
// inner buffer adapter so abort propagation stays intact
|
|
241
241
|
// across the unwrap boundary. Without it, an abort raised
|
|
242
242
|
// after unwrapping would no longer cancel inner range()
|
package/lib/safe-ical.js
CHANGED
|
@@ -251,9 +251,9 @@ function parse(text, opts) {
|
|
|
251
251
|
var vcal = consumed.component;
|
|
252
252
|
// RFC 5545 §3.4 — a stream may carry multiple VCALENDAR objects.
|
|
253
253
|
// Walk the remainder so trailing objects are validated under the
|
|
254
|
-
// same caps + control-char + property allowlist
|
|
254
|
+
// same caps + control-char + property allowlist; without
|
|
255
255
|
// this, CalDAV ingest can pass validation on the first object while
|
|
256
|
-
// trailing malformed objects ride through untouched
|
|
256
|
+
// trailing malformed objects ride through untouched.
|
|
257
257
|
var vcalendars = [_shapeVcalendar(vcal)];
|
|
258
258
|
var cursor = consumed.nextIdx;
|
|
259
259
|
while (cursor < lines.length) {
|
package/lib/safe-mime.js
CHANGED
|
@@ -549,7 +549,7 @@ function _splitMultipart(buf, boundary) {
|
|
|
549
549
|
// Per RFC 2046 §5.1.1 a boundary delimiter is `--<value>` preceded
|
|
550
550
|
// by CRLF (or LF) — OR at the very start of the body. A boundary-
|
|
551
551
|
// shaped sequence elsewhere in a part's body MUST NOT be treated
|
|
552
|
-
// as a delimiter.
|
|
552
|
+
// as a delimiter.
|
|
553
553
|
var idx = _findBoundaryAtLineStart(buf, delimiter, pos);
|
|
554
554
|
if (idx < 0) break;
|
|
555
555
|
if (buf[idx + delimiter.length] === 0x2D && buf[idx + delimiter.length + 1] === 0x2D) {
|
|
@@ -208,7 +208,7 @@ function verify(assetPath, signaturePath, pubkeyPem) {
|
|
|
208
208
|
// produces. 64 KiB chunks match the framework's hash-while-streaming
|
|
209
209
|
// convention elsewhere.
|
|
210
210
|
//
|
|
211
|
-
//
|
|
211
|
+
// Hardening (v0.9.58): fstat the asset BEFORE the read loop
|
|
212
212
|
// for every alg path, clamp every readSync to (assetStat.size -
|
|
213
213
|
// fullOff), and reject if the final fullOff diverges from
|
|
214
214
|
// assetStat.size. A grow-during-read race (writer appends as we
|
package/lib/self-update.js
CHANGED
|
@@ -115,7 +115,7 @@ function _normalizeTag(tag) {
|
|
|
115
115
|
* Missing numeric components on either side are treated as `"0"` so
|
|
116
116
|
* `"1.0"` and `"1.0.0"` compare equal.
|
|
117
117
|
*
|
|
118
|
-
*
|
|
118
|
+
* Hardening (v0.9.58) — pre-v0.9.58 the pre-release segment fell back
|
|
119
119
|
* to lexicographic comparison, which silently misordered `"1.0.0-alpha.10"`
|
|
120
120
|
* (the strict-§11 LARGER pre-release) and `"1.0.0-alpha.9"`: as strings
|
|
121
121
|
* "10" < "9" so `alpha.10 < alpha.9`, and a downstream consumer polling
|
|
@@ -294,7 +294,7 @@ function _matchAsset(name, pattern, fallback) {
|
|
|
294
294
|
* timeoutMs: number, // request timeout (default 15s)
|
|
295
295
|
* headers: object, // additional request headers
|
|
296
296
|
* etag: string, // last-seen etag for If-None-Match
|
|
297
|
-
* // (
|
|
297
|
+
* // (etags are RFC 9110 §13.1.1
|
|
298
298
|
* // per-resource; an etag captured for
|
|
299
299
|
* // releasesUrl=A is meaningless against
|
|
300
300
|
* // releasesUrl=B. Operators rotating
|
package/lib/static.js
CHANGED
|
@@ -216,7 +216,7 @@ function _resolveSafe(root, requestedPath) {
|
|
|
216
216
|
// deposited disk content: shell-exec extensions (.exe / .bin / .so /
|
|
217
217
|
// legitimate `<name>.<hash>.js` bundler output) are valid here. The
|
|
218
218
|
// other balanced checks still reject the traversal + smuggling
|
|
219
|
-
// surface
|
|
219
|
+
// surface.
|
|
220
220
|
var fname = nodePath.basename(resolved);
|
|
221
221
|
var rv = guardFilename().validate(fname, {
|
|
222
222
|
profile: "balanced",
|
package/lib/subject.js
CHANGED
|
@@ -362,7 +362,7 @@ function erase(subjectId, opts) {
|
|
|
362
362
|
|
|
363
363
|
// ---- Crypto-shred erase (Art. 17 + WAL/replica residual closure) ----
|
|
364
364
|
//
|
|
365
|
-
//
|
|
365
|
+
// When a table opts into per-row keying via
|
|
366
366
|
// b.cryptoField.declarePerRowKey, this primitive deletes the
|
|
367
367
|
// per-row K_row entries from _blamejs_per_row_keys, leaving any
|
|
368
368
|
// residual ciphertext in WAL / replica / backup storage
|
|
@@ -477,7 +477,7 @@ function eraseHard(subjectId, opts) {
|
|
|
477
477
|
totalDeleted += deleted;
|
|
478
478
|
perTable[spec.name] = deleted;
|
|
479
479
|
// REINDEX the table so B-tree pages holding the deleted row's
|
|
480
|
-
// index entries are rebuilt — closes the
|
|
480
|
+
// index entries are rebuilt — closes the erase-vacuum residual class.
|
|
481
481
|
try { db().runSql('REINDEX "' + spec.name + '"'); } // table name comes from FRAMEWORK_SCHEMA
|
|
482
482
|
catch (_e) { /* cluster mode / unsupported dialect */ }
|
|
483
483
|
}
|
package/lib/vault/index.js
CHANGED
|
@@ -102,11 +102,12 @@ function resolvePaths(dataDir) {
|
|
|
102
102
|
plaintext: nodePath.join(dataDir, "vault.key"),
|
|
103
103
|
sealed: nodePath.join(dataDir, "vault.key.sealed"),
|
|
104
104
|
derivedHashSalt: nodePath.join(dataDir, "vault.derived-hash-salt"),
|
|
105
|
+
derivedHashMacKey: nodePath.join(dataDir, "vault.derived-hash-mac.sealed"),
|
|
105
106
|
};
|
|
106
107
|
}
|
|
107
108
|
|
|
108
109
|
// derivedHashSalt — per-deployment salt for crypto-field
|
|
109
|
-
// derivedHashes
|
|
110
|
+
// derivedHashes. Pre-v0.8.42 the deterministic
|
|
110
111
|
// sha3(namespace + plaintext) shape allowed cross-deployment
|
|
111
112
|
// rainbow + cross-table correlation; binding a 32-byte
|
|
112
113
|
// per-deployment salt closes that class without breaking
|
|
@@ -175,6 +176,66 @@ function getDerivedHashSalt() {
|
|
|
175
176
|
return _cachedDerivedHashSalt;
|
|
176
177
|
}
|
|
177
178
|
|
|
179
|
+
// derivedHashMacKey — per-deployment SECRET key for crypto-field's
|
|
180
|
+
// keyed (hmac-shake256) derived-hash mode. Unlike the salt, this is
|
|
181
|
+
// SEALED at rest (vault.derived-hash-mac.sealed), so an attacker with
|
|
182
|
+
// disk access alone cannot recompute the keyed digest and correlate
|
|
183
|
+
// low-entropy plaintexts. Like the salt, it is keypair-bound and
|
|
184
|
+
// survives a passphrase-only rotation; an ENVELOPE rotation re-seals it
|
|
185
|
+
// because it is registered in rotate's additionalSealed sweep.
|
|
186
|
+
function _readOrCreateDerivedHashMacKey() {
|
|
187
|
+
if (!paths) {
|
|
188
|
+
throw new VaultError("vault/not-initialized",
|
|
189
|
+
"vault.getDerivedHashMacKey() requires init()");
|
|
190
|
+
}
|
|
191
|
+
if (nodeFs.existsSync(paths.derivedHashMacKey)) {
|
|
192
|
+
var sealed = atomicFile.readSync(paths.derivedHashMacKey, { encoding: "utf8" }).trim();
|
|
193
|
+
var b64 = unseal(sealed);
|
|
194
|
+
var key = Buffer.from(b64, "base64");
|
|
195
|
+
if (key.length !== 32) { // 32-byte (256-bit) MAC key
|
|
196
|
+
throw new VaultError("vault/derived-hash-mac-key-corrupted",
|
|
197
|
+
"vault.derived-hash-mac key must unseal to exactly 32 bytes; got " + key.length);
|
|
198
|
+
}
|
|
199
|
+
return key;
|
|
200
|
+
}
|
|
201
|
+
var nodeCrypto = require("node:crypto");
|
|
202
|
+
var raw = nodeCrypto.randomBytes(32); // 32-byte MAC key
|
|
203
|
+
atomicFile.writeSync(paths.derivedHashMacKey, seal(raw.toString("base64")), { fileMode: 0o600 });
|
|
204
|
+
log("generated per-deployment derivedHash MAC key at " + paths.derivedHashMacKey);
|
|
205
|
+
return raw;
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
var _cachedDerivedHashMacKey = null;
|
|
209
|
+
/**
|
|
210
|
+
* @primitive b.vault.getDerivedHashMacKey
|
|
211
|
+
* @signature b.vault.getDerivedHashMacKey()
|
|
212
|
+
* @since 0.14.7
|
|
213
|
+
* @related b.vault.getDerivedHashSalt, b.cryptoField.registerTable
|
|
214
|
+
*
|
|
215
|
+
* Returns the 32-byte per-deployment SECRET key that backs crypto-
|
|
216
|
+
* field's keyed (`hmac-shake256`) derived-hash mode. Generated once on
|
|
217
|
+
* first use, SEALED at rest (`vault.derived-hash-mac.sealed`, mode
|
|
218
|
+
* `0o600`) so disk access alone does not expose it, and re-sealed by an
|
|
219
|
+
* envelope vault rotation. Distinct from `getDerivedHashSalt`, which is
|
|
220
|
+
* a non-secret salt stored in plaintext.
|
|
221
|
+
*
|
|
222
|
+
* Throws `VaultError("vault/not-initialized")` before `init()`, or
|
|
223
|
+
* `vault/derived-hash-mac-key-corrupted` if the sealed file does not
|
|
224
|
+
* unseal to exactly 32 bytes.
|
|
225
|
+
*
|
|
226
|
+
* @example
|
|
227
|
+
* await b.vault.init({ dataDir: "/var/lib/blamejs", mode: "plaintext" });
|
|
228
|
+
* var k = b.vault.getDerivedHashMacKey();
|
|
229
|
+
* k.length; // → 32
|
|
230
|
+
* Buffer.isBuffer(k); // → true
|
|
231
|
+
*/
|
|
232
|
+
function getDerivedHashMacKey() {
|
|
233
|
+
if (_cachedDerivedHashMacKey === null) {
|
|
234
|
+
_cachedDerivedHashMacKey = _readOrCreateDerivedHashMacKey();
|
|
235
|
+
}
|
|
236
|
+
return _cachedDerivedHashMacKey;
|
|
237
|
+
}
|
|
238
|
+
|
|
178
239
|
// ---- Init dispatch ----
|
|
179
240
|
|
|
180
241
|
/**
|
|
@@ -620,6 +681,7 @@ module.exports = {
|
|
|
620
681
|
seal: seal,
|
|
621
682
|
unseal: unseal,
|
|
622
683
|
getDerivedHashSalt: getDerivedHashSalt,
|
|
684
|
+
getDerivedHashMacKey: getDerivedHashMacKey,
|
|
623
685
|
_zeroizeAndReplace: _zeroizeAndReplace,
|
|
624
686
|
aad: vaultAad,
|
|
625
687
|
getKeysJson: getKeysJson,
|
|
@@ -633,6 +695,7 @@ module.exports = {
|
|
|
633
695
|
_resetForTest: function () {
|
|
634
696
|
if (currentPassphrase) safeBuffer.secureZero(currentPassphrase);
|
|
635
697
|
keys = null; initialized = false; currentPassphrase = null; paths = null; currentMode = null;
|
|
698
|
+
_cachedDerivedHashSalt = null; _cachedDerivedHashMacKey = null;
|
|
636
699
|
},
|
|
637
700
|
_getKeysForTest: function () { return keys; },
|
|
638
701
|
_getPathsForTest: function () { return paths; },
|
package/lib/vault/rotate.js
CHANGED
|
@@ -651,6 +651,25 @@ async function rotate(opts) {
|
|
|
651
651
|
_reSealValue(current, oldKeys, newKeys), { mode: 0o600 });
|
|
652
652
|
}
|
|
653
653
|
|
|
654
|
+
// 3b. Framework-managed crypto-field derived-hash files — always
|
|
655
|
+
// rotated regardless of operator opts.paths, so the staging copy is
|
|
656
|
+
// complete. The plaintext salt is copied verbatim; the SEALED MAC key
|
|
657
|
+
// (keyed hmac-shake256 mode) is re-sealed under the new keypair so an
|
|
658
|
+
// envelope rotation doesn't orphan it (a passphrase-only rotation
|
|
659
|
+
// re-seals to the same value since the keypair is unchanged).
|
|
660
|
+
var saltSrc = nodePath.join(dataDir, "vault.derived-hash-salt");
|
|
661
|
+
if (nodeFs.existsSync(saltSrc)) {
|
|
662
|
+
nodeFs.copyFileSync(saltSrc, nodePath.join(stagingDir, "vault.derived-hash-salt"));
|
|
663
|
+
}
|
|
664
|
+
var macSrc = nodePath.join(dataDir, "vault.derived-hash-mac.sealed");
|
|
665
|
+
if (nodeFs.existsSync(macSrc)) {
|
|
666
|
+
var macCurrent = nodeFs.readFileSync(macSrc, "utf8").trim();
|
|
667
|
+
if (macCurrent.indexOf(C.VAULT_PREFIX) === 0) {
|
|
668
|
+
nodeFs.writeFileSync(nodePath.join(stagingDir, "vault.derived-hash-mac.sealed"),
|
|
669
|
+
_reSealValue(macCurrent, oldKeys, newKeys), { mode: 0o600 });
|
|
670
|
+
}
|
|
671
|
+
}
|
|
672
|
+
|
|
654
673
|
// 4. decrypt + rotate + re-encrypt db.enc
|
|
655
674
|
_emit(progress, { phase: "rotate_db" });
|
|
656
675
|
var encDbPath = nodePath.join(dataDir, paths.encryptedDb);
|
package/lib/vendor-data.js
CHANGED
|
@@ -306,7 +306,7 @@ function _loadAndVerify(name) {
|
|
|
306
306
|
// Memoized — "sha256:" + sha256(pemToRaw(PUBKEY_PEM)). Matches the
|
|
307
307
|
// canonical fingerprint shape `scripts/vendor-data-gen.js` writes into
|
|
308
308
|
// each .data.js's `metadata.publicKeyFingerprint`. Computed lazily on
|
|
309
|
-
// first verify (also lazily by verifyAll at boot).
|
|
309
|
+
// first verify (also lazily by verifyAll at boot). Every
|
|
310
310
|
// per-entry verify cross-checks this against the entry's declared
|
|
311
311
|
// `meta.publicKeyFingerprint` so a pubkey-swap attack fails before
|
|
312
312
|
// signature verify even runs.
|
package/package.json
CHANGED
package/sbom.cdx.json
CHANGED
|
@@ -2,10 +2,10 @@
|
|
|
2
2
|
"$schema": "http://cyclonedx.org/schema/bom-1.5.schema.json",
|
|
3
3
|
"bomFormat": "CycloneDX",
|
|
4
4
|
"specVersion": "1.5",
|
|
5
|
-
"serialNumber": "urn:uuid:
|
|
5
|
+
"serialNumber": "urn:uuid:5777b851-3edb-4e73-9a6a-0538d8e52a91",
|
|
6
6
|
"version": 1,
|
|
7
7
|
"metadata": {
|
|
8
|
-
"timestamp": "2026-05-
|
|
8
|
+
"timestamp": "2026-05-30T21:03:08.883Z",
|
|
9
9
|
"lifecycles": [
|
|
10
10
|
{
|
|
11
11
|
"phase": "build"
|
|
@@ -19,14 +19,14 @@
|
|
|
19
19
|
}
|
|
20
20
|
],
|
|
21
21
|
"component": {
|
|
22
|
-
"bom-ref": "@blamejs/core@0.14.
|
|
22
|
+
"bom-ref": "@blamejs/core@0.14.7",
|
|
23
23
|
"type": "application",
|
|
24
24
|
"name": "blamejs",
|
|
25
|
-
"version": "0.14.
|
|
25
|
+
"version": "0.14.7",
|
|
26
26
|
"scope": "required",
|
|
27
27
|
"author": "blamejs contributors",
|
|
28
28
|
"description": "The Node framework that owns its stack.",
|
|
29
|
-
"purl": "pkg:npm/%40blamejs/core@0.14.
|
|
29
|
+
"purl": "pkg:npm/%40blamejs/core@0.14.7",
|
|
30
30
|
"properties": [],
|
|
31
31
|
"externalReferences": [
|
|
32
32
|
{
|
|
@@ -54,7 +54,7 @@
|
|
|
54
54
|
"components": [],
|
|
55
55
|
"dependencies": [
|
|
56
56
|
{
|
|
57
|
-
"ref": "@blamejs/core@0.14.
|
|
57
|
+
"ref": "@blamejs/core@0.14.7",
|
|
58
58
|
"dependsOn": []
|
|
59
59
|
}
|
|
60
60
|
]
|