@jmanuelcorral/openteam 0.16.0 → 0.16.1
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/README.es.md +1 -1
- package/README.md +1 -1
- package/dist/cli/graphOperator.d.ts +3 -3
- package/dist/cli/graphOperator.d.ts.map +1 -1
- package/dist/cli/opencodeVersion.d.ts +44 -0
- package/dist/cli/opencodeVersion.d.ts.map +1 -0
- package/dist/cli.js +1987 -995
- package/dist/commands/dispatch.d.ts +23 -1
- package/dist/commands/dispatch.d.ts.map +1 -1
- package/dist/commands/doctor.d.ts +19 -0
- package/dist/commands/doctor.d.ts.map +1 -1
- package/dist/commands/graph.d.ts +40 -2
- package/dist/commands/graph.d.ts.map +1 -1
- package/dist/contract/opencode.d.ts +49 -3
- package/dist/contract/opencode.d.ts.map +1 -1
- package/dist/graph/certificate.d.ts.map +1 -1
- package/dist/index.d.ts +28 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +139 -23
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -2450,6 +2450,10 @@ function splitVirtualPath(path) {
|
|
|
2450
2450
|
|
|
2451
2451
|
// src/cli/graphOperator.ts
|
|
2452
2452
|
var ALLOWED_GATE = { allowed: true, violations: [] };
|
|
2453
|
+
var ALLOWED_EVALUATION = {
|
|
2454
|
+
kind: "evaluated",
|
|
2455
|
+
gate: ALLOWED_GATE
|
|
2456
|
+
};
|
|
2453
2457
|
function journalRoot(config) {
|
|
2454
2458
|
return config.graph?.journalRoot ?? DEFAULT_GRAPH_JOURNAL_ROOT;
|
|
2455
2459
|
}
|
|
@@ -2539,7 +2543,7 @@ async function listWorktreeObservations(config, options) {
|
|
|
2539
2543
|
})));
|
|
2540
2544
|
}
|
|
2541
2545
|
function createGraphOperator(options) {
|
|
2542
|
-
const evaluateCutoverGate = options.evaluateCutoverGate ?? (async () =>
|
|
2546
|
+
const evaluateCutoverGate = options.evaluateCutoverGate ?? (async () => ALLOWED_EVALUATION);
|
|
2543
2547
|
const worktreeOptions = options.exec === undefined ? undefined : {
|
|
2544
2548
|
exec: options.exec,
|
|
2545
2549
|
repoRoot: options.repoRoot ?? process.cwd(),
|
|
@@ -4298,6 +4302,36 @@ var SUPPORTED_OPENCODE_VERSIONS = [
|
|
|
4298
4302
|
"1.18.18",
|
|
4299
4303
|
"1.18.19"
|
|
4300
4304
|
];
|
|
4305
|
+
var SEMVER_RE = /^(\d+)\.(\d+)\.(\d+)/;
|
|
4306
|
+
function parseSemver(version) {
|
|
4307
|
+
const normalized = version.trim().replace(/^[=^~v]+/, "");
|
|
4308
|
+
const match = SEMVER_RE.exec(normalized);
|
|
4309
|
+
if (match === null) {
|
|
4310
|
+
throw new Error(`invalid semver: "${version}"`);
|
|
4311
|
+
}
|
|
4312
|
+
return {
|
|
4313
|
+
major: Number(match[1]),
|
|
4314
|
+
minor: Number(match[2]),
|
|
4315
|
+
patch: Number(match[3])
|
|
4316
|
+
};
|
|
4317
|
+
}
|
|
4318
|
+
function isCertificateVersionCompatible(certifiedVersion, liveVersion) {
|
|
4319
|
+
if (certifiedVersion === liveVersion) {
|
|
4320
|
+
return true;
|
|
4321
|
+
}
|
|
4322
|
+
let certified;
|
|
4323
|
+
let live;
|
|
4324
|
+
try {
|
|
4325
|
+
certified = parseSemver(certifiedVersion);
|
|
4326
|
+
live = parseSemver(liveVersion);
|
|
4327
|
+
} catch {
|
|
4328
|
+
return false;
|
|
4329
|
+
}
|
|
4330
|
+
if (certified.major !== live.major || certified.minor !== live.minor) {
|
|
4331
|
+
return false;
|
|
4332
|
+
}
|
|
4333
|
+
return live.patch >= certified.patch;
|
|
4334
|
+
}
|
|
4301
4335
|
|
|
4302
4336
|
// src/graph/soakLedger.ts
|
|
4303
4337
|
import { z as z15 } from "zod";
|
|
@@ -4556,8 +4590,8 @@ function parseShadowCertificate(value, opencodeVersion) {
|
|
|
4556
4590
|
if (sha256Hex(canonicalCertificate(unsigned)) !== digest) {
|
|
4557
4591
|
throw new ShadowCertificateError("digest-mismatch", "certificate digest does not cover the presented evidence");
|
|
4558
4592
|
}
|
|
4559
|
-
if (certificate.opencodeVersion
|
|
4560
|
-
throw new ShadowCertificateError("opencode-mismatch", `certified for "${certificate.opencodeVersion}",
|
|
4593
|
+
if (!isCertificateVersionCompatible(certificate.opencodeVersion, opencodeVersion)) {
|
|
4594
|
+
throw new ShadowCertificateError("opencode-mismatch", `certified for "${certificate.opencodeVersion}", running "${opencodeVersion}" — evidence is accepted only on ${certificate.opencodeVersion} or a newer patch of the same minor line`);
|
|
4561
4595
|
}
|
|
4562
4596
|
return certificate;
|
|
4563
4597
|
}
|
|
@@ -4741,8 +4775,8 @@ function parseReleaseCertificate(value, opencodeVersion, expectedShadowDigest) {
|
|
|
4741
4775
|
if (sha256Hex(canonicalReleaseCertificate(unsigned)) !== digest) {
|
|
4742
4776
|
throw new ReleaseCertificateError("digest-mismatch", "certificate digest does not cover the presented evidence");
|
|
4743
4777
|
}
|
|
4744
|
-
if (certificate.opencodeVersion
|
|
4745
|
-
throw new ReleaseCertificateError("opencode-mismatch", `certified for "${certificate.opencodeVersion}",
|
|
4778
|
+
if (!isCertificateVersionCompatible(certificate.opencodeVersion, opencodeVersion)) {
|
|
4779
|
+
throw new ReleaseCertificateError("opencode-mismatch", `certified for "${certificate.opencodeVersion}", running "${opencodeVersion}" — evidence is accepted only on ${certificate.opencodeVersion} or a newer patch of the same minor line`);
|
|
4746
4780
|
}
|
|
4747
4781
|
return certificate;
|
|
4748
4782
|
}
|
|
@@ -8344,7 +8378,7 @@ function legacyRosterFindings(audit) {
|
|
|
8344
8378
|
}
|
|
8345
8379
|
return findings;
|
|
8346
8380
|
}
|
|
8347
|
-
function rosterHealthSection(audit, loadError, rosterRoleCount) {
|
|
8381
|
+
function rosterHealthSection(audit, loadError, rosterRoleCount, rosterMissing) {
|
|
8348
8382
|
const auditFindings = audit?.findings ?? legacyRosterFindings(audit ?? {});
|
|
8349
8383
|
const unparseable = auditFindings.find((finding) => finding.kind === "unparseable-roster");
|
|
8350
8384
|
const unparseableMessage = loadError ?? unparseable?.message;
|
|
@@ -8357,6 +8391,14 @@ function rosterHealthSection(audit, loadError, rosterRoleCount) {
|
|
|
8357
8391
|
];
|
|
8358
8392
|
}
|
|
8359
8393
|
if (audit === undefined) {
|
|
8394
|
+
if (rosterMissing === true) {
|
|
8395
|
+
return [
|
|
8396
|
+
" roster health:",
|
|
8397
|
+
` ✗ ${OPENTEAM_ROSTER_PATH} does not exist — no team roster has been cast.`,
|
|
8398
|
+
" consequence: without a roster openteam cannot distribute work across roles, so every request is handled by a single agent and no work splitting happens.",
|
|
8399
|
+
` remedy: run \`openteam setup\` to cast a team and write the roster (${OPENTEAM_ROSTER_PATH}), then re-run \`openteam doctor\`.`
|
|
8400
|
+
];
|
|
8401
|
+
}
|
|
8360
8402
|
return [];
|
|
8361
8403
|
}
|
|
8362
8404
|
const missing = auditFindings.filter((finding) => finding.kind === "missing-guaranteed-role").map((finding) => finding.roleID);
|
|
@@ -8392,6 +8434,14 @@ function rosterHealthSection(audit, loadError, rosterRoleCount) {
|
|
|
8392
8434
|
}
|
|
8393
8435
|
return lines;
|
|
8394
8436
|
}
|
|
8437
|
+
function orchestratorAgentSection() {
|
|
8438
|
+
return [
|
|
8439
|
+
" orchestrator agent:",
|
|
8440
|
+
` ✗ ${ORCHESTRATOR_AGENT_PATH} does not exist — opencode has no openteam coordinator agent.`,
|
|
8441
|
+
" consequence: this is the primary agent that reads the roster and calls `openteam-orchestrate` to fan work out across roles; without it opencode has no openteam coordinator, so every request is handled by a single agent and no work splitting happens.",
|
|
8442
|
+
` remedy: run \`openteam setup\` to generate ${ORCHESTRATOR_AGENT_PATH}, then re-run \`openteam doctor\`.`
|
|
8443
|
+
];
|
|
8444
|
+
}
|
|
8395
8445
|
function gitignoreSection(gitignore) {
|
|
8396
8446
|
if (gitignore.missingRules.length === 0) {
|
|
8397
8447
|
return [
|
|
@@ -8455,7 +8505,10 @@ function renderDoctor(input) {
|
|
|
8455
8505
|
if (input.diagnostics !== undefined) {
|
|
8456
8506
|
lines.push(...diagnosticsSection(input.diagnostics));
|
|
8457
8507
|
}
|
|
8458
|
-
lines.push(...rosterHealthSection(input.rosterAudit, input.rosterLoadError, input.rosterRoleCount));
|
|
8508
|
+
lines.push(...rosterHealthSection(input.rosterAudit, input.rosterLoadError, input.rosterRoleCount, input.rosterMissing));
|
|
8509
|
+
if (input.orchestratorAgentMissing === true) {
|
|
8510
|
+
lines.push(...orchestratorAgentSection());
|
|
8511
|
+
}
|
|
8459
8512
|
if (input.gitignore !== undefined) {
|
|
8460
8513
|
lines.push(...gitignoreSection(input.gitignore));
|
|
8461
8514
|
}
|
|
@@ -8539,14 +8592,31 @@ function leaseLine(lease) {
|
|
|
8539
8592
|
const state = lease.released ? "released" : "active";
|
|
8540
8593
|
return ` lease: ${lease.holder} → ${lease.runID} (${state})`;
|
|
8541
8594
|
}
|
|
8542
|
-
function
|
|
8595
|
+
function appendEffectiveLines(lines, gate) {
|
|
8596
|
+
switch (gate.kind) {
|
|
8597
|
+
case "not-applicable":
|
|
8598
|
+
return;
|
|
8599
|
+
case "passed":
|
|
8600
|
+
lines.push(" effective: active");
|
|
8601
|
+
return;
|
|
8602
|
+
case "unevaluable":
|
|
8603
|
+
lines.push(" effective: unknown — could not evaluate the cutover gate");
|
|
8604
|
+
lines.push(` ${gate.reason}`);
|
|
8605
|
+
return;
|
|
8606
|
+
case "denied":
|
|
8607
|
+
lines.push(" effective: off — cutover gate denied");
|
|
8608
|
+
for (const violation of gate.violations) {
|
|
8609
|
+
lines.push(` • ${violation.code}: ${violation.detail}`);
|
|
8610
|
+
}
|
|
8611
|
+
}
|
|
8612
|
+
}
|
|
8613
|
+
function renderGraphStatus(snapshot, gate = { kind: "not-applicable" }) {
|
|
8543
8614
|
const lines = [
|
|
8544
8615
|
"openteam graph status:",
|
|
8545
|
-
` config: ${snapshot.effectiveMode} (source: ${snapshot.source})
|
|
8546
|
-
leaseLine(snapshot.lease),
|
|
8547
|
-
` journal: ${snapshot.journal}`,
|
|
8548
|
-
` effects: ${snapshot.pendingEffects} pending, ${snapshot.unknownEffects} unknown`
|
|
8616
|
+
` config: ${snapshot.effectiveMode} (source: ${snapshot.source})`
|
|
8549
8617
|
];
|
|
8618
|
+
appendEffectiveLines(lines, gate);
|
|
8619
|
+
lines.push(leaseLine(snapshot.lease), ` journal: ${snapshot.journal}`, ` effects: ${snapshot.pendingEffects} pending, ${snapshot.unknownEffects} unknown`);
|
|
8550
8620
|
const needsReconciliation = isRecoveryRequired(snapshot.journal, snapshot.unknownEffects);
|
|
8551
8621
|
if (needsReconciliation) {
|
|
8552
8622
|
lines.push(" ⚠ Reconciliation required: journal or effects in an uncertain state.");
|
|
@@ -9990,8 +10060,7 @@ async function runAgents(deps, configPath, opencodeConfigPaths, configResolution
|
|
|
9990
10060
|
async function runGraph(positionals, deps, configPath, configResolution) {
|
|
9991
10061
|
const sub = positionals[1];
|
|
9992
10062
|
if (sub === "status") {
|
|
9993
|
-
|
|
9994
|
-
return { exitCode: 0, stdout: renderGraphStatus(snapshot) };
|
|
10063
|
+
return runGraphStatus(deps, configPath, configResolution);
|
|
9995
10064
|
}
|
|
9996
10065
|
if (sub === "cancel") {
|
|
9997
10066
|
return runGraphCancel(positionals, deps, configPath, configResolution);
|
|
@@ -10046,7 +10115,9 @@ function renderGraphOutcome(outcome) {
|
|
|
10046
10115
|
async function resolveOperatorGraphPolicy(config, operator) {
|
|
10047
10116
|
let graph = resolveGraphConfig(config, "file");
|
|
10048
10117
|
if (isGateApplicable(graph.effectiveMode)) {
|
|
10049
|
-
|
|
10118
|
+
const evaluation = await operator.evaluateCutoverGate(config);
|
|
10119
|
+
const gate = evaluation.kind === "evaluated" ? evaluation.gate : { allowed: false, violations: [] };
|
|
10120
|
+
graph = applyGraphGate(graph, gate);
|
|
10050
10121
|
}
|
|
10051
10122
|
return {
|
|
10052
10123
|
graph,
|
|
@@ -10064,6 +10135,32 @@ function checkOperatorGate(policy) {
|
|
|
10064
10135
|
stdout: renderLegacyGraphReason(decision2)
|
|
10065
10136
|
};
|
|
10066
10137
|
}
|
|
10138
|
+
async function runGraphStatus(deps, configPath, configResolution) {
|
|
10139
|
+
const snapshot = await deps.readGraphSnapshot(configPath, configResolution);
|
|
10140
|
+
if (!isGateApplicable(snapshot.effectiveMode)) {
|
|
10141
|
+
return { exitCode: 0, stdout: renderGraphStatus(snapshot) };
|
|
10142
|
+
}
|
|
10143
|
+
const operator = deps.graphOperator;
|
|
10144
|
+
if (operator === undefined) {
|
|
10145
|
+
const gate2 = {
|
|
10146
|
+
kind: "unevaluable",
|
|
10147
|
+
reason: "graph operator ports are not configured"
|
|
10148
|
+
};
|
|
10149
|
+
return { exitCode: 0, stdout: renderGraphStatus(snapshot, gate2) };
|
|
10150
|
+
}
|
|
10151
|
+
const config = await deps.loadConfig(configPath, configResolution);
|
|
10152
|
+
const evaluation = await operator.evaluateCutoverGate(config);
|
|
10153
|
+
if (evaluation.kind === "unevaluable") {
|
|
10154
|
+
const gate2 = {
|
|
10155
|
+
kind: "unevaluable",
|
|
10156
|
+
reason: evaluation.reason
|
|
10157
|
+
};
|
|
10158
|
+
return { exitCode: 0, stdout: renderGraphStatus(snapshot, gate2) };
|
|
10159
|
+
}
|
|
10160
|
+
const resolved = applyGraphGate(resolveGraphConfig(config, "file"), evaluation.gate);
|
|
10161
|
+
const gate = resolved.gateDenied === true ? { kind: "denied", violations: resolved.gateViolations ?? [] } : { kind: "passed" };
|
|
10162
|
+
return { exitCode: 0, stdout: renderGraphStatus(snapshot, gate) };
|
|
10163
|
+
}
|
|
10067
10164
|
async function runGraphCancel(positionals, deps, configPath, configResolution) {
|
|
10068
10165
|
const runID = positionals[2];
|
|
10069
10166
|
if (runID === undefined || runID.trim() === "") {
|
|
@@ -10510,6 +10607,9 @@ async function runCli(argv, deps) {
|
|
|
10510
10607
|
const summary = summarizeQueueWaits(queueEvents);
|
|
10511
10608
|
queueWait = summary !== undefined ? { summary } : {};
|
|
10512
10609
|
}
|
|
10610
|
+
const rosterMissing = deps.loadRosterForDoctor !== undefined && roster === undefined && rosterLoadError === undefined;
|
|
10611
|
+
const orchestratorAgentName = ORCHESTRATOR_AGENT_PATH.slice(ORCHESTRATOR_AGENT_PATH.lastIndexOf("/") + 1).replace(/\.md$/, "");
|
|
10612
|
+
const orchestratorAgentMissing = !agentFiles.some((file) => file.name === orchestratorAgentName);
|
|
10513
10613
|
return {
|
|
10514
10614
|
exitCode: 0,
|
|
10515
10615
|
stdout: renderDoctor({
|
|
@@ -10523,6 +10623,8 @@ async function runCli(argv, deps) {
|
|
|
10523
10623
|
...rosterAudit !== undefined ? { rosterAudit } : {},
|
|
10524
10624
|
...rosterRoleCount !== undefined ? { rosterRoleCount } : {},
|
|
10525
10625
|
...rosterLoadError !== undefined ? { rosterLoadError } : {},
|
|
10626
|
+
...rosterMissing ? { rosterMissing } : {},
|
|
10627
|
+
...orchestratorAgentMissing ? { orchestratorAgentMissing } : {},
|
|
10526
10628
|
...diagnostics !== undefined && diagnostics.length > 0 ? { diagnostics } : {},
|
|
10527
10629
|
...opencodeConfigError !== undefined ? { opencodeConfigError } : {},
|
|
10528
10630
|
...cacheEntries !== undefined ? { cacheEntries, cliVersion: deps.version } : {},
|
|
@@ -13387,7 +13489,7 @@ var createOtlpSpanExporter = (connection, config) => {
|
|
|
13387
13489
|
// package.json
|
|
13388
13490
|
var package_default = {
|
|
13389
13491
|
name: "@jmanuelcorral/openteam",
|
|
13390
|
-
version: "0.16.
|
|
13492
|
+
version: "0.16.1",
|
|
13391
13493
|
packageManager: "bun@1.3.14",
|
|
13392
13494
|
description: "Cost-aware, local-first routing plugin for opencode with cheapest-capable frontier fallback and multi-agent orchestration.",
|
|
13393
13495
|
license: "MIT",
|
|
@@ -13751,6 +13853,14 @@ async function buildGateInput(config, storage, opencodeVersion, warn) {
|
|
|
13751
13853
|
const operatorApproval = config.graph?.operatorApproval ?? false;
|
|
13752
13854
|
return { shadow, release, soak, migration, operatorApproval };
|
|
13753
13855
|
}
|
|
13856
|
+
var OPENCODE_VERSION_UNRESOLVED_REASON = "the opencode version is not determinable outside a running opencode session, " + "so the cutover gate cannot be verified here — the running plugin logs the " + "authoritative gate result and warns loudly on a real denial";
|
|
13857
|
+
async function evaluateCutoverGateForBoundary(config, storage, version) {
|
|
13858
|
+
if (version === undefined) {
|
|
13859
|
+
return { kind: "unevaluable", reason: OPENCODE_VERSION_UNRESOLVED_REASON };
|
|
13860
|
+
}
|
|
13861
|
+
const gateInput = await buildGateInput(config, storage, version, () => {});
|
|
13862
|
+
return { kind: "evaluated", gate: evaluateGraphGate(gateInput) };
|
|
13863
|
+
}
|
|
13754
13864
|
function recorderPortsFromStorage(storage) {
|
|
13755
13865
|
return {
|
|
13756
13866
|
fs: {
|
|
@@ -13838,7 +13948,7 @@ async function readStoredRosterForDoctor(storage) {
|
|
|
13838
13948
|
}
|
|
13839
13949
|
}
|
|
13840
13950
|
var auditStoredRosterForDoctor = (roster, configuredRoles) => typeof roster === "string" ? auditRoster(roster, configuredRoles) : auditRoster(roster, configuredRoles);
|
|
13841
|
-
function createCliDeps(config, registry, telemetryPath, sessionsDir = DEFAULT_SESSIONS_DIR, storage = createFsStorageProvider(process.cwd()), fallbackSource = "options", rawOptions) {
|
|
13951
|
+
function createCliDeps(config, registry, telemetryPath, sessionsDir = DEFAULT_SESSIONS_DIR, storage = createFsStorageProvider(process.cwd()), fallbackSource = "options", rawOptions, resolveOpencodeVersion) {
|
|
13842
13952
|
return {
|
|
13843
13953
|
loadConfig: async (path4, resolution = { explicit: false }) => {
|
|
13844
13954
|
const content = await readCliConfigFromStorage(storage, path4, resolution);
|
|
@@ -13912,7 +14022,8 @@ function createCliDeps(config, registry, telemetryPath, sessionsDir = DEFAULT_SE
|
|
|
13912
14022
|
}),
|
|
13913
14023
|
graphOperator: createGraphOperator({
|
|
13914
14024
|
storage,
|
|
13915
|
-
holder: "openteam-cli"
|
|
14025
|
+
holder: "openteam-cli",
|
|
14026
|
+
evaluateCutoverGate: async (gateConfig) => evaluateCutoverGateForBoundary(gateConfig, storage, resolveOpencodeVersion === undefined ? undefined : await resolveOpencodeVersion())
|
|
13916
14027
|
}),
|
|
13917
14028
|
configPath: DEFAULT_CONFIG_PATH,
|
|
13918
14029
|
telemetryPath,
|
|
@@ -14042,7 +14153,14 @@ var server = async (ctx, rawOptions) => {
|
|
|
14042
14153
|
injectMemory,
|
|
14043
14154
|
onRoute: (sid, model) => sessionTracker.trackRoutedModel(sid, model)
|
|
14044
14155
|
});
|
|
14045
|
-
const
|
|
14156
|
+
const getOpencodeVersion = createLazyOpencodeVersionReader(ctx.serverUrl, {
|
|
14157
|
+
client: ctx.client,
|
|
14158
|
+
onFailure: createOpencodeVersionReadFailureLogger(MAX_LOGGED_OPENCODE_VERSION_FAILURE_CAUSES, diagnostics.warn("opencode-version-read-failed", { toast: false }))
|
|
14159
|
+
});
|
|
14160
|
+
const cliDeps = createCliDeps(config, registry, telemetryPath, sessionsDir, storage, runtimeConfig.source, rawOptions, async () => {
|
|
14161
|
+
const version = await getOpencodeVersion();
|
|
14162
|
+
return version === "unknown" ? undefined : version;
|
|
14163
|
+
});
|
|
14046
14164
|
const toolcalls = createToolcallTracker({ sink });
|
|
14047
14165
|
const announcedSessions = new Set;
|
|
14048
14166
|
const announceEndpoint = (sessionID) => {
|
|
@@ -14065,10 +14183,6 @@ var server = async (ctx, rawOptions) => {
|
|
|
14065
14183
|
if (config.privacyMode === "forceLocalOnSensitive" && localDefault(config) === null) {
|
|
14066
14184
|
warnInertPrivacySetting(runtimeConfig.searchedPaths, diagnostics.warn("privacy-inert"));
|
|
14067
14185
|
}
|
|
14068
|
-
const getOpencodeVersion = createLazyOpencodeVersionReader(ctx.serverUrl, {
|
|
14069
|
-
client: ctx.client,
|
|
14070
|
-
onFailure: createOpencodeVersionReadFailureLogger(MAX_LOGGED_OPENCODE_VERSION_FAILURE_CAUSES, diagnostics.warn("opencode-version-read-failed", { toast: false }))
|
|
14071
|
-
});
|
|
14072
14186
|
if (isGateApplicable(graphConfig.effectiveMode)) {
|
|
14073
14187
|
const opencodeVersion = await getOpencodeVersion();
|
|
14074
14188
|
const gateInput = await buildGateInput(config, storage, opencodeVersion, diagnostics.warn("soak-evidence-rejected", { toast: false }));
|
|
@@ -14233,6 +14347,7 @@ export {
|
|
|
14233
14347
|
logOpencodeServerUrl,
|
|
14234
14348
|
logAvailabilityRefreshError,
|
|
14235
14349
|
isMissingFile,
|
|
14350
|
+
evaluateCutoverGateForBoundary,
|
|
14236
14351
|
src_default as default,
|
|
14237
14352
|
createOpencodeVersionReadFailureLogger,
|
|
14238
14353
|
createLazyOpencodeVersionReader,
|
|
@@ -14240,5 +14355,6 @@ export {
|
|
|
14240
14355
|
createCliDeps,
|
|
14241
14356
|
buildGateInput,
|
|
14242
14357
|
PACKAGE_VERSION,
|
|
14358
|
+
OPENCODE_VERSION_UNRESOLVED_REASON,
|
|
14243
14359
|
MAX_LOGGED_OPENCODE_VERSION_FAILURE_CAUSES
|
|
14244
14360
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jmanuelcorral/openteam",
|
|
3
|
-
"version": "0.16.
|
|
3
|
+
"version": "0.16.1",
|
|
4
4
|
"packageManager": "bun@1.3.14",
|
|
5
5
|
"description": "Cost-aware, local-first routing plugin for opencode with cheapest-capable frontier fallback and multi-agent orchestration.",
|
|
6
6
|
"license": "MIT",
|