@bongos/core 1.19.341 → 1.19.342
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/.bongos-core.json +20 -10
- package/package-lock.json +2 -2
- package/package.json +1 -1
- package/scripts/gds/push-path-brief.js +94 -0
- package/src/module-api.js +3 -1
- package/tests/push_path_brief.mjs +90 -0
package/.bongos-core.json
CHANGED
|
@@ -2,22 +2,22 @@
|
|
|
2
2
|
"artifact": "bongos-core",
|
|
3
3
|
"manifest_schema": 1,
|
|
4
4
|
"generator": "scripts/gds/package-core.js",
|
|
5
|
-
"core_version": "1.19.
|
|
6
|
-
"core_contract": "1.19.
|
|
7
|
-
"source_commit": "
|
|
5
|
+
"core_version": "1.19.342",
|
|
6
|
+
"core_contract": "1.19.342",
|
|
7
|
+
"source_commit": "8762dcc095daf67a6ebc7d8f67bee76335f6d718",
|
|
8
8
|
"source_ref": "HEAD",
|
|
9
|
-
"built_at": "2026-08-25T01:
|
|
9
|
+
"built_at": "2026-08-25T01:51:12.583Z",
|
|
10
10
|
"redaction": {
|
|
11
11
|
"model": "docs-redacted+functional-verbatim",
|
|
12
12
|
"docs_redacted": 326,
|
|
13
13
|
"agent_docs_stubbed": 22,
|
|
14
|
-
"functional_verbatim":
|
|
14
|
+
"functional_verbatim": 1487,
|
|
15
15
|
"rules": 3,
|
|
16
16
|
"gate_literals": 3,
|
|
17
17
|
"gate": "passed"
|
|
18
18
|
},
|
|
19
|
-
"file_count":
|
|
20
|
-
"tree_sha256": "
|
|
19
|
+
"file_count": 1835,
|
|
20
|
+
"tree_sha256": "77392f5c78b2253320505f4775d1f72a1dfe9c6c07fb3120ca3cbb91c9a8727d",
|
|
21
21
|
"files": [
|
|
22
22
|
{
|
|
23
23
|
"path": ".claude/skills/blocker-review/SKILL.md",
|
|
@@ -4732,12 +4732,12 @@
|
|
|
4732
4732
|
{
|
|
4733
4733
|
"path": "package-lock.json",
|
|
4734
4734
|
"mode": "0000644",
|
|
4735
|
-
"sha256": "
|
|
4735
|
+
"sha256": "c98fa68956d00010ef831bab66ad73939ee7b86b61a95c2512d4c98b2d284823"
|
|
4736
4736
|
},
|
|
4737
4737
|
{
|
|
4738
4738
|
"path": "package.json",
|
|
4739
4739
|
"mode": "0000644",
|
|
4740
|
-
"sha256": "
|
|
4740
|
+
"sha256": "6cd5475e1b29d9ba180f44e88c824eb38291945b3122ae22ff948e481333e513"
|
|
4741
4741
|
},
|
|
4742
4742
|
{
|
|
4743
4743
|
"path": "public-docs/index.html",
|
|
@@ -5759,6 +5759,11 @@
|
|
|
5759
5759
|
"mode": "0000644",
|
|
5760
5760
|
"sha256": "23c61159820e8b796bb3c84b399c4d8d9f2b1fc5665be5672ec72a354bcedc2e"
|
|
5761
5761
|
},
|
|
5762
|
+
{
|
|
5763
|
+
"path": "scripts/gds/push-path-brief.js",
|
|
5764
|
+
"mode": "0000644",
|
|
5765
|
+
"sha256": "cd173e293b1053a4070d2f1c3d51ad28d19d978cd3489efe312dc45e38739553"
|
|
5766
|
+
},
|
|
5762
5767
|
{
|
|
5763
5768
|
"path": "scripts/gds/read-session-export.js",
|
|
5764
5769
|
"mode": "0000644",
|
|
@@ -6567,7 +6572,7 @@
|
|
|
6567
6572
|
{
|
|
6568
6573
|
"path": "src/module-api.js",
|
|
6569
6574
|
"mode": "0000644",
|
|
6570
|
-
"sha256": "
|
|
6575
|
+
"sha256": "f26225c679194161265e5994e72566604610a0e41a4a2270579cfa6fbce3d0a2"
|
|
6571
6576
|
},
|
|
6572
6577
|
{
|
|
6573
6578
|
"path": "src/module-loader/catalog.js",
|
|
@@ -8534,6 +8539,11 @@
|
|
|
8534
8539
|
"mode": "0000644",
|
|
8535
8540
|
"sha256": "5a9ea0bf7b4d776a6f9036b8bd060fef76335533274ed748e9b9d742da6960d3"
|
|
8536
8541
|
},
|
|
8542
|
+
{
|
|
8543
|
+
"path": "tests/push_path_brief.mjs",
|
|
8544
|
+
"mode": "0000644",
|
|
8545
|
+
"sha256": "aea6f9ec053bd9477288025b58ed76c166c2d59a24d7ea3481edadba90113887"
|
|
8546
|
+
},
|
|
8537
8547
|
{
|
|
8538
8548
|
"path": "tests/rank_gate.mjs",
|
|
8539
8549
|
"mode": "0000644",
|
package/package-lock.json
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bongos/core",
|
|
3
|
-
"version": "1.19.
|
|
3
|
+
"version": "1.19.342",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "@bongos/core",
|
|
9
|
-
"version": "1.19.
|
|
9
|
+
"version": "1.19.342",
|
|
10
10
|
"license": "AGPL-3.0-or-later",
|
|
11
11
|
"dependencies": {
|
|
12
12
|
"express": "^4.21.2",
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bongos/core",
|
|
3
|
-
"version": "1.19.
|
|
3
|
+
"version": "1.19.342",
|
|
4
4
|
"description": "Cloud Bongos — the AI-first build platform core (GDS + platform surfaces + module system), installed as a versioned dependency (ADR 0108).",
|
|
5
5
|
"license": "AGPL-3.0-or-later",
|
|
6
6
|
"main": "src/platform-server.js",
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
'use strict';
|
|
3
|
+
//
|
|
4
|
+
// scripts/gds/push-path-brief.js — say out loud, at session start, that this machine
|
|
5
|
+
// cannot push (task 1003259 / idea 1000838).
|
|
6
|
+
//
|
|
7
|
+
// THE GAP. On 2026-08-24 a dev-box agent hit auth failures on every raw git probe,
|
|
8
|
+
// concluded "no push credential exists", and asked the owner to mint a fine-grained
|
|
9
|
+
// PAT and store it in ~/.git-credentials on the box — the exact anti-pattern the
|
|
10
|
+
// server-mediated publish path (ADR 0055) exists to avoid. The agent was not being
|
|
11
|
+
// careless: from inside a box every direct GitHub probe fails BY DESIGN (the clone
|
|
12
|
+
// token is one-shot and scrubbed from .git/config after each fetch — ADR 0031 §6),
|
|
13
|
+
// so "missing credential" is the only story the local evidence supports, and the true
|
|
14
|
+
// state at the time (branch already pushed, PR open, CI red) was invisible to it.
|
|
15
|
+
// Nothing the box session loads says the model out loud. This says it out loud.
|
|
16
|
+
//
|
|
17
|
+
// SO: the third SessionStart truth-teller, beside deploy-divergence.js and
|
|
18
|
+
// strand-watch.js. On the server-publish path (pushVia() 'server' — no authenticated
|
|
19
|
+
// gh, i.e. a dev box or any credential-less checkout) it prints ONE line stating the
|
|
20
|
+
// credential model and where the truth about published work lives
|
|
21
|
+
// (GET /api/gds/tasks/:id/publish-status). On a laptop that pushes locally
|
|
22
|
+
// (pushVia() 'local') it prints NOTHING — a line that fires on every healthy laptop
|
|
23
|
+
// becomes wallpaper and the real one gets scrolled past (the strand-watch lesson).
|
|
24
|
+
//
|
|
25
|
+
// STATIC TEXT ONLY. Nothing builder-authored is interpolated, so this adds no
|
|
26
|
+
// prompt-injection surface (the same trust-boundary rule as strand-watch's
|
|
27
|
+
// no-titles) — the test pins the line to the exported constant.
|
|
28
|
+
//
|
|
29
|
+
// Usage:
|
|
30
|
+
// node scripts/gds/push-path-brief.js # human-readable: which path + why
|
|
31
|
+
// node scripts/gds/push-path-brief.js --line # ONE line or nothing; always exit 0
|
|
32
|
+
//
|
|
33
|
+
// Detection override (tests / forcing): OTB_PUSH_VIA_SERVER=1 (server) / =0 (local).
|
|
34
|
+
|
|
35
|
+
const { hasFlag } = require('./cli-lib');
|
|
36
|
+
|
|
37
|
+
// ---- pure core ---------------------------------------------------------------
|
|
38
|
+
|
|
39
|
+
const BRIEF = 'This machine holds NO GitHub push credential — BY DESIGN (ADR 0031 §6 / ADR 0055): '
|
|
40
|
+
+ 'git push / ls-remote / fetch against origin fail with auth errors here, and that is not a fault to fix. '
|
|
41
|
+
+ 'Landing is server-mediated — /builder-ship uploads a git bundle and the SERVER pushes, opens the PR, and lands it. '
|
|
42
|
+
+ 'NEVER ask the owner for a PAT or credential; that request is always wrong on this machine. '
|
|
43
|
+
+ 'To see whether work reached GitHub, use GET /api/gds/tasks/:id/publish-status — never raw git probes.';
|
|
44
|
+
|
|
45
|
+
// briefLine(via) — the unit-testable core: the SessionStart line for this publish
|
|
46
|
+
// path, or null. Null IS the silence (the laptop case, and the undetermined case —
|
|
47
|
+
// a detection failure must not manufacture a warning).
|
|
48
|
+
function briefLine(via) {
|
|
49
|
+
return via === 'server' ? BRIEF : null;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
// ---- detection ---------------------------------------------------------------
|
|
53
|
+
|
|
54
|
+
// Lazy require so a broken or partial checkout degrades to silence, not a stack
|
|
55
|
+
// trace injected into the session. pushVia() honors OTB_PUSH_VIA_SERVER, else
|
|
56
|
+
// probes for an authenticated gh (absent on every box → 'server' instantly).
|
|
57
|
+
function detectVia() {
|
|
58
|
+
return require('./ship-deploy-target.js').pushVia();
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
// ---- rendering ---------------------------------------------------------------
|
|
62
|
+
|
|
63
|
+
function report(via) {
|
|
64
|
+
console.log('');
|
|
65
|
+
console.log(' Publish path');
|
|
66
|
+
console.log(' ──────────────────────────────────────────────────────────');
|
|
67
|
+
if (via === 'server') {
|
|
68
|
+
console.log(' server-mediated (no authenticated gh — a dev box or credential-less checkout).');
|
|
69
|
+
console.log(` ${BRIEF}`);
|
|
70
|
+
} else if (via === 'local') {
|
|
71
|
+
console.log(' local — this machine pushes with its own git + gh credentials.');
|
|
72
|
+
} else {
|
|
73
|
+
console.log(' undetermined — could not probe the publish path on this machine.');
|
|
74
|
+
}
|
|
75
|
+
console.log('');
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
function main() {
|
|
79
|
+
let via = null;
|
|
80
|
+
try { via = detectVia(); } catch (_) { via = null; }
|
|
81
|
+
if (hasFlag('--line')) {
|
|
82
|
+
// FAIL-OPEN, like the other SessionStart lines: silence on 'local' and on any
|
|
83
|
+
// detection failure; never a nonzero exit on the path every session rides in on.
|
|
84
|
+
const l = briefLine(via);
|
|
85
|
+
if (l) console.log(l);
|
|
86
|
+
process.exitCode = 0;
|
|
87
|
+
return;
|
|
88
|
+
}
|
|
89
|
+
report(via);
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
module.exports = { briefLine, BRIEF };
|
|
93
|
+
|
|
94
|
+
if (require.main === module) main();
|
package/src/module-api.js
CHANGED
|
@@ -1112,8 +1112,10 @@ const { validateOrRespond, LIMITS, parseId, asyncHandler, corsPublicGet, parsePa
|
|
|
1112
1112
|
// landed since 1.19.339 with no explicit bump. run 32798342738. (task 1002620)
|
|
1113
1113
|
// 1.19.341 — CI auto-patch (publish-on-merge, ADR 0161): carrier for merges
|
|
1114
1114
|
// landed since 1.19.340 with no explicit bump. run 32798507686. (task 1002620)
|
|
1115
|
+
// 1.19.342 — CI auto-patch (publish-on-merge, ADR 0161): carrier for merges
|
|
1116
|
+
// landed since 1.19.341 with no explicit bump. run 32799103427. (task 1002620)
|
|
1115
1117
|
// ---------------------------------------------------------------------------
|
|
1116
|
-
const CORE_VERSION = '1.19.
|
|
1118
|
+
const CORE_VERSION = '1.19.342'; // CI auto-patch carrier (ADR 0161); see changelog above
|
|
1117
1119
|
|
|
1118
1120
|
// A namespaced logger so a module's log lines are attributable + consistent.
|
|
1119
1121
|
// Usage: const log = api.logger('dev-box'); log.info('mounted');
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
// tests/push_path_brief.mjs
|
|
2
|
+
//
|
|
3
|
+
// Task 1003259 / idea 1000838 — a dev-box agent, unable to see WHY its git probes were
|
|
4
|
+
// failing, asked the owner to mint a PAT and store it on the box. push-path-brief.js is
|
|
5
|
+
// the SessionStart line that states the credential model natively so that request never
|
|
6
|
+
// gets made again. These tests pin BOTH halves: the line fires on the server-publish
|
|
7
|
+
// path with the load-bearing phrases intact, and it is SILENT everywhere else — the
|
|
8
|
+
// silence is half the design (a line firing on every healthy laptop becomes wallpaper).
|
|
9
|
+
//
|
|
10
|
+
// DB-free + network-free: briefLine is pure, and the CLI cases force the path with
|
|
11
|
+
// OTB_PUSH_VIA_SERVER so pushVia() never spawns gh. Run: node tests/push_path_brief.mjs
|
|
12
|
+
|
|
13
|
+
import { strict as assert } from 'node:assert';
|
|
14
|
+
import { createRequire } from 'node:module';
|
|
15
|
+
import { spawnSync } from 'node:child_process';
|
|
16
|
+
import path from 'node:path';
|
|
17
|
+
import { fileURLToPath } from 'node:url';
|
|
18
|
+
|
|
19
|
+
const require = createRequire(import.meta.url);
|
|
20
|
+
const brief = require('../scripts/gds/push-path-brief.js');
|
|
21
|
+
|
|
22
|
+
let passed = 0, failed = 0;
|
|
23
|
+
function t(name, fn) {
|
|
24
|
+
try { fn(); passed++; console.log(` PASS ${name}`); }
|
|
25
|
+
catch (e) { failed++; console.log(` FAIL ${name}\n ${e.message}`); }
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
// ---- the pure core -----------------------------------------------------------
|
|
29
|
+
|
|
30
|
+
t('server path gets the brief, with every load-bearing phrase', () => {
|
|
31
|
+
const l = brief.briefLine('server');
|
|
32
|
+
assert.ok(typeof l === 'string' && l.length > 0, 'expected a line on the server path');
|
|
33
|
+
// Each phrase is one of the three facts the 2026-08-24 incident showed an agent
|
|
34
|
+
// cannot infer from inside a box. Losing any of them re-opens the gap.
|
|
35
|
+
for (const must of [
|
|
36
|
+
'NO GitHub push credential',
|
|
37
|
+
'BY DESIGN',
|
|
38
|
+
'/builder-ship',
|
|
39
|
+
'NEVER ask the owner for a PAT',
|
|
40
|
+
'publish-status',
|
|
41
|
+
]) {
|
|
42
|
+
assert.ok(l.includes(must), `line must state: ${must}`);
|
|
43
|
+
}
|
|
44
|
+
});
|
|
45
|
+
|
|
46
|
+
t('local path is SILENT — null, not an empty string', () => {
|
|
47
|
+
assert.equal(brief.briefLine('local'), null);
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
t('undetermined path stays silent (fail-open, exact vocabulary only)', () => {
|
|
51
|
+
assert.equal(brief.briefLine(null), null);
|
|
52
|
+
assert.equal(brief.briefLine(undefined), null);
|
|
53
|
+
assert.equal(brief.briefLine('SERVER'), null);
|
|
54
|
+
assert.equal(brief.briefLine('ci'), null);
|
|
55
|
+
});
|
|
56
|
+
|
|
57
|
+
t('the line is the exported static constant — nothing is interpolated', () => {
|
|
58
|
+
// Trust boundary: this string is injected into every box session's context. Pinning
|
|
59
|
+
// it to the constant proves no builder-authored text can ever ride along.
|
|
60
|
+
assert.equal(brief.briefLine('server'), brief.BRIEF);
|
|
61
|
+
});
|
|
62
|
+
|
|
63
|
+
// ---- the CLI, end-to-end through the pushVia() override -----------------------
|
|
64
|
+
|
|
65
|
+
const script = path.join(
|
|
66
|
+
path.dirname(fileURLToPath(import.meta.url)),
|
|
67
|
+
'..', 'scripts', 'gds', 'push-path-brief.js',
|
|
68
|
+
);
|
|
69
|
+
function runCli(env) {
|
|
70
|
+
return spawnSync(process.execPath, [script, '--line'], {
|
|
71
|
+
env: { ...process.env, ...env },
|
|
72
|
+
encoding: 'utf8',
|
|
73
|
+
timeout: 15000,
|
|
74
|
+
});
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
t('--line on the forced server path prints the brief and exits 0', () => {
|
|
78
|
+
const r = runCli({ OTB_PUSH_VIA_SERVER: '1' });
|
|
79
|
+
assert.equal(r.status, 0, `expected exit 0, got ${r.status} (stderr: ${r.stderr})`);
|
|
80
|
+
assert.ok(r.stdout.includes('publish-status'), 'expected the brief on stdout');
|
|
81
|
+
});
|
|
82
|
+
|
|
83
|
+
t('--line on the forced local path prints NOTHING and still exits 0', () => {
|
|
84
|
+
const r = runCli({ OTB_PUSH_VIA_SERVER: '0' });
|
|
85
|
+
assert.equal(r.status, 0, `expected exit 0, got ${r.status} (stderr: ${r.stderr})`);
|
|
86
|
+
assert.equal(r.stdout.trim(), '', 'the laptop case must be silent');
|
|
87
|
+
});
|
|
88
|
+
|
|
89
|
+
console.log(`\npush_path_brief: ${passed} passed, ${failed} failed`);
|
|
90
|
+
process.exit(failed ? 1 : 0);
|