@pmelab/gtd 27.4.0 → 27.5.0
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/.claude-plugin/plugin.json +1 -1
- package/README.md +8 -0
- package/dist/chunks/{Schema-CyImoHTj.mjs → Schema-DO5ttJaI.mjs} +1 -1
- package/dist/chunks/{reserved-BPdVZkgv.mjs → reserved-DM5W_LAt.mjs} +64 -3
- package/dist/chunks/{tail-iLAMoigl.mjs → tail-6gvLXXcg.mjs} +1 -1
- package/dist/flows.mjs +4 -2
- package/dist/gtd.bundle.mjs +44 -9
- package/dist/testkit.mjs +43 -10
- package/dist/workflows/cleanup.mjs +2 -2
- package/dist/workflows/feature.mjs +140 -64
- package/dist/workflows/fix.mjs +2 -2
- package/dist/workflows/review.mjs +2 -2
- package/dist/workflows/rollout.mjs +1 -1
- package/dist/workflows.mjs +346 -107
- package/package.json +1 -1
- package/src/cli/Cli.test.ts +49 -1
- package/src/cli/Cli.ts +20 -3
- package/src/edge/Edge.test.ts +45 -1
- package/src/edge/Edge.ts +15 -4
- package/src/flags/index.test.ts +14 -1
- package/src/flags/index.ts +14 -3
- package/src/flows/helpers.ts +7 -3
- package/src/replay/judgeDiffShape.test.ts +43 -0
- package/src/step/planStart.ts +3 -2
- package/src/testkit/TestRepo.ts +3 -0
- package/src/testkit/steps.ts +18 -0
- package/src/workflow/index.ts +8 -1
- package/src/workflow/vars.test.ts +23 -1
- package/src/workflow/vars.ts +24 -0
- package/src/workflows/feature/feature.ts +9 -2
- package/src/workflows/feature/index.ts +1 -0
- package/src/workflows/feature/seam-pin.feature +52 -0
- package/src/workflows/feature/seam.feature +387 -0
- package/src/workflows/feature/seam.test.ts +88 -0
- package/src/workflows/feature/seam.ts +110 -0
- package/src/workflows/index.ts +1 -0
- package/src/workflows/shared/options.test.ts +12 -1
- package/src/workflows/shared/options.ts +1 -0
- package/src/workflows/shared/skills.test.ts +20 -2
- package/src/workflows/shared/skills.ts +6 -0
- package/src/workflows/shared/text.test.ts +59 -0
- package/src/workflows/shared/text.ts +86 -0
- package/src/workflows/shared/vars.ts +4 -0
- package/src/workflows/shared/workflows.steps.ts +39 -1
package/README.md
CHANGED
|
@@ -552,6 +552,14 @@ unknown key. `gtd.config.ts` is the only repository config: gtd 23 removed the
|
|
|
552
552
|
home directory — fails every command until you delete it. See
|
|
553
553
|
[Migrating from `.gtdrc`](https://github.com/pmelab/gtd/blob/main/docs/configuration.md#migrating-from-gtdrc).
|
|
554
554
|
|
|
555
|
+
**Naive pass (flag `GTD_FLAG_NAIVE_PASS=1`, off by default).** Instead of an
|
|
556
|
+
architecture and package files, the agent first implements the requirements
|
|
557
|
+
directly. A judge checks whether it changed anything outside the expected set
|
|
558
|
+
(tests, steering files; see `seamAllow`). Incidental changes land; a needed seam
|
|
559
|
+
change goes to you for approval and is refactored first; a wrong approach is
|
|
560
|
+
retried twice, then rests for you to steer or overrule it. Details in
|
|
561
|
+
[the naive-pass path](docs/configuration.md#the-naive-pass-path).
|
|
562
|
+
|
|
555
563
|
### Rolling out and cleaning up release flags
|
|
556
564
|
|
|
557
565
|
Two more bundled workflows retire a release flag:
|
|
@@ -25449,4 +25449,4 @@ Struct({
|
|
|
25449
25449
|
description: "Represents an issue returned by the ArrayFormatter formatter"
|
|
25450
25450
|
});
|
|
25451
25451
|
//#endregion
|
|
25452
|
-
export { logWarning as $,
|
|
25452
|
+
export { logWarning as $, NodeInspectSymbol as $i, map$4 as $n, make$20 as $r, provide$1 as $t, catchIf as A, add$2 as Ai, scopeMake as An, flatMap$3 as Ar, suspend$1 as At, flatMap$1 as B, getOrElse as Bi, get as Bn, sync$1 as Br, unsafeMakeLatch as Bt, all as C, toArray$1 as Ci, isInterrupted as Cn, exitFail as Cr, sandbox as Ct, async as D, GenericTag as Di, squash as Dn, exitZipRight as Dr, scopedWith as Dt, asVoid as E, unsafeHead as Ei, reduceWithContext as En, exitVoid$1 as Er, scoped as Et, ensuring as F, fromIterable$6 as Fi, join as Fn, map$5 as Fr, tryMap as Ft, forkIn as G, none$4 as Gi, TypeId$4 as Gn, whenEffect as Gr, zipLeft as Gt, fnUntraced as H, isSome as Hi, modify as Hn, uninterruptible$1 as Hr, when as Ht, exit as I, splitAt as Ii, sequential$1 as In, onInterrupt as Ir, tryPromise as It, ignore as J, left as Ji, all$2 as Jn, DeferredTypeId as Jr, spaced as Jt, forkScoped as K, some as Ki, Class as Kn, withFiberRuntime$1 as Kr, zipRight as Kt, fail$1 as L, filter$3 as Li, bind as Ln, scopeClose as Lr, try_ as Lt, die as M, getOption as Mi, _await as Mn, interruptAsFiber as Mr, tap as Mt, dieMessage as N, omit$1 as Ni, inheritAll as Nn, interruptFiber as Nr, tapErrorCause as Nt, catchAll as O, Reference as Oi, ensuring$1 as On, fiberId as Or, serviceOption as Ot, either as P, empty$22 as Pi, interruptAllAs as Pn, interruptible$2 as Pr, timeout as Pt, isEffect as Q, BaseProto as Qi, isFailure as Qn, ids as Qr, mergeAll as Qt, failCause as R, flatMap$6 as Ri, bindTo as Rn, succeed$5 as Rr, uninterruptible as Rt, addFinalizer as S, takeRight as Si, isDieType as Sn, exitAs as Sr, runtime as St, as as T, unsafeGet as Ti, map$3 as Tn, exitSucceed$1 as Tr, scopeWith as Tt, forEach as U, map$11 as Ui, set as Un, uninterruptibleMask$2 as Ur, withFiberRuntime as Ut, flatten as V, isNone as Vi, make$12 as Vn, tap$1 as Vr, unsafeMakeSemaphore as Vt, forkDaemon as W, match$6 as Wi, update$1 as Wn, void_$2 as Wr, zip as Wt, interruptible as X, right as Xi, fail$4 as Xn, combine$5 as Xr, tagged as Xt, interrupt as Y, match$7 as Yi, die$2 as Yn, empty$15 as Yr, TaggedError$1 as Yt, intoDeferred as Z, pipeArguments as Zi, failCause$2 as Zn, combineAll as Zr, fromEffect as Zt, decodeSync as _, of$1 as _i, fail$2 as _n, deferredIsDone as _r, raceWith as _t, Literal as a, constTrue as aa, size$2 as ai, updateContext as an, zipRight$1 as ar, matchCause as at, acquireRelease as b, reverse$1 as bi, interrupt$1 as bn, deferredUnsafeDone as br, runPromise as bt, String$ as c, dual as ca, append as ci, Scope as cn, asyncInterrupt as cr, negate as ct, Union as d, empty$19 as di, close as dn, deferredAwait as dr, orElse$1 as dt, format$4 as ea, none$2 as ei, provideMerge as en, mapBoth$2 as er, makeSemaphore as et, between as f, filter$1 as fi, extend$1 as fn, deferredComplete as fr, orElseSucceed as ft, standardSchemaV1 as g, map$9 as gi, die$1 as gn, deferredInterruptWith as gr, race as gt, optionalWith as h, isEmpty$5 as hi, NoSuchElementException as hn, deferredInterrupt as hr, provideService as ht, Defect as i, constFalse as ia, has$1 as ii, unsafeRunPromiseExit as in, zip$1 as ir, match as it, catchTag as j, get$7 as ji, scopeTag as jn, interrupt$2 as jr, sync as jt, catchAllCause as k, Tag as ki, forEachConcurrentDiscard as kn, fiberRefLocally as kr, succeed$1 as kt, Struct as l, identity as la, appendAll$1 as li, addFinalizer$1 as ln, catchAll$1 as lr, onError as lt, optional as m, isChunk as mi, make$2 as mn, deferredFailCause as mr, provide as mt, Boolean$ as n, equals$2 as na, make$22 as ni, succeed$2 as nn, succeed$4 as nr, mapBoth$1 as nt, Never as o, constUndefined as oa, decode as oi, forkIn$1 as on, as$1 as or, matchCauseEffect as ot, decodeUnknown as p, fromIterable$5 as pi, fork as pn, deferredFail as pr, promise as pt, gen as q, isLeft as qi, spanTag as qn, zipRight$2 as qr, zipWith as qt, Cause as r, hasProperty as ra, set$3 as ri, unsafeFork as rn, void_$1 as rr, mapError$1 as rt, Number$ as s, constVoid as sa, isFinite as si, unsafeMakeSemaphore$1 as sn, asVoid$1 as sr, matchEffect as st, Array$ as t, toJSON as ta, get$4 as ti, scoped$1 as tn, match$3 as tr, map$1 as tt, TaggedError as u, pipe as ua, drop as ui, addFinalizerExit as un, currentContext as ur, orDie as ut, encodeSync as v, prepend$1 as vi, failureOrCause as vn, deferredMake as vr, repeat as vt, annotateLogs as w, unsafeFromArray as wi, isInterruptedOnly as wn, exitFailCause$1 as wr, scope as wt, acquireUseRelease as x, take as xi, interruptors as xn, deferredUnsafeMake as xr, runPromiseExit as xt, _void as y, reduce$6 as yi, flipCauseOption as yn, deferredSucceed as yr, retry as yt, fiberIdWith as z, fromNullable as zi, sleep as zn, suspend$3 as zr, uninterruptibleMask as zt };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { accessFor, agent, answered, changesSince, check, codeThreads, defineWorkflow, env, head, human, judge, numeric, quote, skillsFor, start, vars } from "../flows.mjs";
|
|
1
|
+
import { accessFor, agent, answered, changesSince, check, codeThreads, defineWorkflow, displayPath, env, head, human, judge, numeric, quote, skillsFor, start, vars } from "../flows.mjs";
|
|
2
2
|
import { escalation as escalation$1, gate as gate$1, healthy as healthy$1, lensScopes, lensesOf, removedAssertions } from "../workflow-kit.mjs";
|
|
3
|
-
import { c as String$, g as standardSchemaV1, h as optionalWith, l as Struct } from "./Schema-
|
|
3
|
+
import { c as String$, g as standardSchemaV1, h as optionalWith, l as Struct } from "./Schema-DO5ttJaI.mjs";
|
|
4
4
|
//#region src/workflows/shared/prose.ts
|
|
5
5
|
const skillsPreamble = `- Load whatever's listed here that your harness actually has installed,
|
|
6
6
|
skip anything it doesn't — silently, never stopping or asking about a
|
|
@@ -1071,6 +1071,60 @@ ${it.processCostByModel.map((m) => `- ${m.model}: ${m.cost}\n`).join("")}
|
|
|
1071
1071
|
Print the closing message and stop — this writes nothing itself.
|
|
1072
1072
|
`;
|
|
1073
1073
|
};
|
|
1074
|
+
const listed = (paths, unreadable = []) => paths.map((path) => ` - \`${displayPath(path)}\`${unreadable.includes(path) ? " (unreadable)" : ""}`).join("\n");
|
|
1075
|
+
const naivePassPrompt = (rejection) => `${stateFileRules}
|
|
1076
|
+
- Read \`.gtd/REQUIREMENTS.md\`: the settled requirements for this change
|
|
1077
|
+
- Implement them the quickest way that works — the naive version. Do not
|
|
1078
|
+
restructure, abstract or refactor around the change; a later step judges
|
|
1079
|
+
the shape of your diff and a reviewer makes it fit
|
|
1080
|
+
- Add tests as you go, and leave \`.gtd/\` untouched
|
|
1081
|
+
- Leave everything uncommitted and finish your turn — do not commit
|
|
1082
|
+
${rejection === void 0 ? "" : `
|
|
1083
|
+
Your previous attempt was rejected: the judge answered \`reject\` (p=${rejection.p}),
|
|
1084
|
+
meaning the naive pass solved the task the wrong way — discard it and
|
|
1085
|
+
re-implement. It changed these files outside the expected set:
|
|
1086
|
+
${listed(rejection.strays)}
|
|
1087
|
+
Start over and choose a different approach; do not rebuild the same diff.
|
|
1088
|
+
`}`;
|
|
1089
|
+
const implementBuildingPrompt = (reference) => `${stateFileRules}
|
|
1090
|
+
- Read \`.gtd/REQUIREMENTS.md\`: the settled requirements for this change
|
|
1091
|
+
- Implement them properly, fitting the codebase's seams and conventions
|
|
1092
|
+
- Reference only: \`git show ${reference}\` shows an earlier naive attempt.
|
|
1093
|
+
Read it for ideas; never apply, cherry-pick or check it out — write
|
|
1094
|
+
the change fresh
|
|
1095
|
+
- Put the new behaviour behind a new release flag, following the
|
|
1096
|
+
repository's flag conventions
|
|
1097
|
+
- Write the tests first, then the code that makes them pass
|
|
1098
|
+
- Leave \`.gtd/REQUIREMENTS.md\` in place and everything uncommitted, then
|
|
1099
|
+
finish your turn
|
|
1100
|
+
`;
|
|
1101
|
+
const implementFixPrompt = () => `${stateFileRules}
|
|
1102
|
+
${fixFeedbackPrompt}
|
|
1103
|
+
- Leave everything uncommitted and finish your turn — do not commit
|
|
1104
|
+
`;
|
|
1105
|
+
const seamSteerMessage = (rejection) => `The naive pass was rejected three times and the retries are spent.
|
|
1106
|
+
The last attempt changed these files outside the expected set:
|
|
1107
|
+
${listed(rejection.strays)}
|
|
1108
|
+
|
|
1109
|
+
Two ways forward (then run \`gtd land\`):
|
|
1110
|
+
- **Steer** — edit \`.gtd/REQUIREMENTS.md\` to redirect the change; the naive
|
|
1111
|
+
pass runs again with a fresh retry budget
|
|
1112
|
+
- **Overrule** — land a clean tree to accept the last attempt's approach:
|
|
1113
|
+
the implementation is built against it as reference, with no seam gate
|
|
1114
|
+
and no refactor. Risk: this ships the seam the judge objected to,
|
|
1115
|
+
unaddressed — the choice is recorded in history.
|
|
1116
|
+
|
|
1117
|
+
An edit together with an approval counts as steer. Only
|
|
1118
|
+
\`.gtd/REQUIREMENTS.md\` is meant to change here: any other edit lands on the
|
|
1119
|
+
branch unjudged.
|
|
1120
|
+
`;
|
|
1121
|
+
const seamByHandMessage = (strays, unreadable, reference) => `The judge could not read some of these files, so the diff was never
|
|
1122
|
+
fully judged and no refactor runs. Unreadable ones are marked:
|
|
1123
|
+
${listed(strays, unreadable)}
|
|
1124
|
+
|
|
1125
|
+
See them with \`git show ${reference} -- <path>\` and review by hand. Land a
|
|
1126
|
+
clean tree to go on to the implementation, which runs next.
|
|
1127
|
+
`;
|
|
1074
1128
|
//#endregion
|
|
1075
1129
|
//#region src/workflows/shared/steps.ts
|
|
1076
1130
|
const FEEDBACK = ".gtd/FEEDBACK.md";
|
|
@@ -1257,6 +1311,8 @@ const defaults = {
|
|
|
1257
1311
|
reviewNoteActionable: "0.7",
|
|
1258
1312
|
reviewSeverityMinP: "0.7",
|
|
1259
1313
|
refactorFlagPattern: "\\bGTD_FLAG_\\w+",
|
|
1314
|
+
seamAllow: "**/*.test.*, **/*.spec.*, **/*.feature, **/tests/**, **/test/**, **/__tests__/**, .gtd/**",
|
|
1315
|
+
flag_naive_pass: "0",
|
|
1260
1316
|
qualityReviews: "correctness, owasp-security, ponytail-review, test-audit, conventions, spec-challenge"
|
|
1261
1317
|
};
|
|
1262
1318
|
/** Environment settings. */
|
|
@@ -1275,6 +1331,7 @@ const ShippedOptions = Struct({
|
|
|
1275
1331
|
reviewNoteActionable: setting,
|
|
1276
1332
|
reviewSeverityMinP: setting,
|
|
1277
1333
|
refactorFlagPattern: setting,
|
|
1334
|
+
seamAllow: setting,
|
|
1278
1335
|
qualityReviews: setting,
|
|
1279
1336
|
testCommand: setting,
|
|
1280
1337
|
plannerModel: setting,
|
|
@@ -1339,6 +1396,10 @@ const skills = (vars) => ({
|
|
|
1339
1396
|
refactor: ["ponytail"],
|
|
1340
1397
|
"refactor.fix.suite": ["ponytail", "debugging-and-error-recovery"],
|
|
1341
1398
|
"refactor.health": ["ponytail", "debugging-and-error-recovery"],
|
|
1399
|
+
seam: ["incremental-implementation"],
|
|
1400
|
+
implement: ["test-driven-development", "incremental-implementation"],
|
|
1401
|
+
"implement.fix.suite": ["debugging-and-error-recovery"],
|
|
1402
|
+
"implement.health": ["debugging-and-error-recovery"],
|
|
1342
1403
|
...lensScopes("build.quality", lensesOf(vars.qualityReviews ?? ""), (lens) => builtInLenses[lens]?.skills ?? [lens])
|
|
1343
1404
|
});
|
|
1344
1405
|
//#endregion
|
|
@@ -1362,4 +1423,4 @@ const steering = {
|
|
|
1362
1423
|
[REVIEW]: "review"
|
|
1363
1424
|
};
|
|
1364
1425
|
//#endregion
|
|
1365
|
-
export {
|
|
1426
|
+
export { refactorFixPrompt as $, architectureAuthorPrompt as A, designGateAnswerMessage as B, fixRisks as C, reviewing as D, reviewQuality as E, buildReviewCollectingPrompt as F, handOffAwaitReviewMessage as G, designTriagePrompt as H, buildReviewFixNitsPrompt as I, implementFixPrompt as J, idleMessage as K, buildReviewTriageMessage as L, architectureGateAnswerMessage as M, buildReviewAnswerQuestionsPrompt as N, agentWithSkills as O, buildReviewAwaitAfterDeferMessage as P, refactorBuildingPrompt as Q, builderSystem as R, fixQuality as S, reviewMissing as T, finisherSystem as U, designSystem as V, fixReviewNotesPrompt as W, packagesItemBuildingPrompt as X, naivePassPrompt as Y, packagesItemFixSuitePrompt as Z, REQUIREMENTS as _, flagShipped as a, seamByHandMessage as at, coder as b, envDefaults as c, unwindFailedMessage as ct, gate as d, reviewEditNotesCapture as et, guarded as f, QUALITY as g, FEEDBACK as h, skills as i, reviewerSystem as it, architectureDecomposePrompt as j, architectSystem as k, baseline as l, unwindFailure as lt, ARCHITECTURE as m, summary as n, reviewGateBlockedMessage as nt, shipped as o, seamSteerMessage as ot, healthy as p, implementBuildingPrompt as q, access as r, reviewNotesCapture as rt, defaults as s, startGateBlockedMessage as st, steering as t, reviewEditsCapture as tt, escalation as u, REVIEW as v, planner as w, fixCheck as x, awaitReview as y, deferNotesScript as z };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { read, refuse, removeScript, run, scope, showScript, vars } from "../flows.mjs";
|
|
2
2
|
import { fixFindings, lensesOf, qualityLap as qualityLap$1, reviewToHandOff } from "../workflow-kit.mjs";
|
|
3
|
-
import { C as fixRisks, D as reviewing, E as reviewQuality, G as handOffAwaitReviewMessage, S as fixQuality, T as reviewMissing, f as guarded, g as QUALITY, p as healthy, u as escalation, v as REVIEW, x as fixCheck, y as awaitReview } from "./reserved-
|
|
3
|
+
import { C as fixRisks, D as reviewing, E as reviewQuality, G as handOffAwaitReviewMessage, S as fixQuality, T as reviewMissing, f as guarded, g as QUALITY, p as healthy, u as escalation, v as REVIEW, x as fixCheck, y as awaitReview } from "./reserved-DM5W_LAt.mjs";
|
|
4
4
|
//#region src/workflows/shared/tail.ts
|
|
5
5
|
/** The reviewer's own `.gtd/REVIEW.md`, kept beside the human's notes so `fix` can tell them apart. */
|
|
6
6
|
const REVIEW_ORIG = ".gtd/REVIEW.orig.md";
|
package/dist/flows.mjs
CHANGED
|
@@ -354,7 +354,8 @@ const strayContent = (strays) => strays.map((c) => [
|
|
|
354
354
|
*/
|
|
355
355
|
const judgeDiffShape = async (name, options) => {
|
|
356
356
|
const { changes: all, allow } = options;
|
|
357
|
-
const
|
|
357
|
+
const exempt = options.exempt ?? [];
|
|
358
|
+
const isStray = (c) => !exempt.includes(c.path) && !allow.some((pattern) => matches(c.path, pattern));
|
|
358
359
|
const strayChanges = all.filter(isStray).sort((a, b) => a.path < b.path ? -1 : a.path > b.path ? 1 : 0).map(({ path, status, before, after }) => ({
|
|
359
360
|
path,
|
|
360
361
|
status,
|
|
@@ -600,6 +601,7 @@ var flows_exports = /* @__PURE__ */ __exportAll({
|
|
|
600
601
|
configure: () => configure,
|
|
601
602
|
defineConfig: () => defineConfig,
|
|
602
603
|
defineWorkflow: () => defineWorkflow,
|
|
604
|
+
displayPath: () => displayPath,
|
|
603
605
|
env: () => env,
|
|
604
606
|
glob: () => glob,
|
|
605
607
|
hasThreadFor: () => hasThreadFor,
|
|
@@ -640,4 +642,4 @@ var flows_exports = /* @__PURE__ */ __exportAll({
|
|
|
640
642
|
wrote: () => wrote
|
|
641
643
|
});
|
|
642
644
|
//#endregion
|
|
643
|
-
export { FLOWS_PROTOCOL, FlowsProtocolError, accessFor, agent, answered, changes, changesSince, check, checkScript, codeChanges, codeThreads, configProblems, configure, defineConfig, defineWorkflow, env, glob, hasThreadFor, head, human, installContext, isFactoryWorkflow, judge, judgeDiffShape, kept, matches, moveScript, numeric, openQuestions, protocolMismatch, quote, read, refuse, removeScript, requireAnswers, requireProgress, requireReplies, requireRevert, requireThreadsClosed, restart, restoreScript, revertScript, run, scope, seamGate, sectionBodies, sections, showScript, skillsFor, start, flows_exports as t, threads, vars, wrote };
|
|
645
|
+
export { FLOWS_PROTOCOL, FlowsProtocolError, accessFor, agent, answered, changes, changesSince, check, checkScript, codeChanges, codeThreads, configProblems, configure, defineConfig, defineWorkflow, displayPath, env, glob, hasThreadFor, head, human, installContext, isFactoryWorkflow, judge, judgeDiffShape, kept, matches, moveScript, numeric, openQuestions, protocolMismatch, quote, read, refuse, removeScript, requireAnswers, requireProgress, requireReplies, requireRevert, requireThreadsClosed, restart, restoreScript, revertScript, run, scope, seamGate, sectionBodies, sections, showScript, skillsFor, start, flows_exports as t, threads, vars, wrote };
|
package/dist/gtd.bundle.mjs
CHANGED
|
@@ -20970,13 +20970,23 @@ const restorability = (git, headHash, tipHash) => gen(function* () {
|
|
|
20970
20970
|
});
|
|
20971
20971
|
//#endregion
|
|
20972
20972
|
//#region src/flags/index.ts
|
|
20973
|
-
const FLAGS$1 = [
|
|
20973
|
+
const FLAGS$1 = [{
|
|
20974
|
+
name: "naive_pass",
|
|
20975
|
+
owner: "pmelab",
|
|
20976
|
+
expiry: "2027-01-15",
|
|
20977
|
+
kind: "release"
|
|
20978
|
+
}];
|
|
20974
20979
|
const BOOL = {
|
|
20975
20980
|
"0": false,
|
|
20976
20981
|
false: false,
|
|
20977
20982
|
"1": true,
|
|
20978
20983
|
true: true
|
|
20979
20984
|
};
|
|
20985
|
+
/** A `flag_<name>` setting's value as the pinned `"1"`/`"0"`, or undefined when garbled. */
|
|
20986
|
+
const flagSettingValue = (raw) => {
|
|
20987
|
+
const key = raw.toLowerCase();
|
|
20988
|
+
return Object.hasOwn(BOOL, key) ? BOOL[key] ? "1" : "0" : void 0;
|
|
20989
|
+
};
|
|
20980
20990
|
const resolveFlags = (env, registry = FLAGS$1) => {
|
|
20981
20991
|
const out = {};
|
|
20982
20992
|
for (const { name, defaultOn } of registry) {
|
|
@@ -20991,6 +21001,7 @@ const resolveFlags = (env, registry = FLAGS$1) => {
|
|
|
20991
21001
|
}
|
|
20992
21002
|
return out;
|
|
20993
21003
|
};
|
|
21004
|
+
const flagSettings = (flags) => Object.fromEntries(Object.entries(flags).map(([name, on]) => [`flag_${name}`, on ? "1" : "0"]));
|
|
20994
21005
|
//#endregion
|
|
20995
21006
|
//#region src/install/Version.ts
|
|
20996
21007
|
const _require = createRequire(import.meta.url);
|
|
@@ -21976,7 +21987,8 @@ const strayContent = (strays) => strays.map((c) => [
|
|
|
21976
21987
|
*/
|
|
21977
21988
|
const judgeDiffShape = async (name, options) => {
|
|
21978
21989
|
const { changes: all, allow } = options;
|
|
21979
|
-
const
|
|
21990
|
+
const exempt = options.exempt ?? [];
|
|
21991
|
+
const isStray = (c) => !exempt.includes(c.path) && !allow.some((pattern) => matches(c.path, pattern));
|
|
21980
21992
|
const strayChanges = all.filter(isStray).sort((a, b) => a.path < b.path ? -1 : a.path > b.path ? 1 : 0).map(({ path, status, before, after }) => ({
|
|
21981
21993
|
path,
|
|
21982
21994
|
status,
|
|
@@ -22222,6 +22234,7 @@ var flows_exports = /* @__PURE__ */ __exportAll({
|
|
|
22222
22234
|
configure: () => configure$1,
|
|
22223
22235
|
defineConfig: () => defineConfig,
|
|
22224
22236
|
defineWorkflow: () => defineWorkflow,
|
|
22237
|
+
displayPath: () => displayPath,
|
|
22225
22238
|
env: () => env,
|
|
22226
22239
|
glob: () => glob,
|
|
22227
22240
|
hasThreadFor: () => hasThreadFor,
|
|
@@ -38368,7 +38381,10 @@ const compileConfig = (value, origin) => {
|
|
|
38368
38381
|
};
|
|
38369
38382
|
//#endregion
|
|
38370
38383
|
//#region src/workflow/vars.ts
|
|
38384
|
+
init_esm();
|
|
38371
38385
|
const PREFIX = "GTD_";
|
|
38386
|
+
/** The live release flags as `flag_<name>` settings, provided by the CLI; absent means no flags. */
|
|
38387
|
+
var StartFlags = class extends Reference()("StartFlags", { defaultValue: () => ({}) }) {};
|
|
38372
38388
|
/**
|
|
38373
38389
|
* One kind of setting, later wins: the workflow's own defaults, `--var`
|
|
38374
38390
|
* overrides (process settings only; environment settings pass `{}`), then
|
|
@@ -38388,6 +38404,18 @@ const resolveVars = (workflowVars, entryVars, env) => {
|
|
|
38388
38404
|
}
|
|
38389
38405
|
return merged;
|
|
38390
38406
|
};
|
|
38407
|
+
/**
|
|
38408
|
+
* `resolveVars` for a process being STARTED: `flags` land between the workflow
|
|
38409
|
+
* defaults and `--var`, for already-declared names only. A running process never
|
|
38410
|
+
* calls this — it replays its pinned record.
|
|
38411
|
+
*/
|
|
38412
|
+
const resolveStartVars = (workflowVars, flags, entryVars, env) => {
|
|
38413
|
+
const declared = Object.fromEntries(Object.entries(flags).filter(([name]) => Object.hasOwn(workflowVars, name)));
|
|
38414
|
+
return resolveVars({
|
|
38415
|
+
...workflowVars,
|
|
38416
|
+
...declared
|
|
38417
|
+
}, entryVars, env);
|
|
38418
|
+
};
|
|
38391
38419
|
/** The first process setting whose value spans lines — a `Gtd-Var:` trailer cannot carry it. */
|
|
38392
38420
|
const multilineSetting = (vars) => Object.keys(vars).sort().find((name) => /[\r\n]/.test(vars[name]));
|
|
38393
38421
|
const SETTING_NAME = /^[A-Za-z_][A-Za-z0-9_]*$/;
|
|
@@ -39321,7 +39349,7 @@ const planStart = (current, actor, start) => gen(function* () {
|
|
|
39321
39349
|
const overrideRefusal = yield* checkOverrides(commandLabel, varOverrides, Object.keys(workflow.vars), Object.keys(workflow.env));
|
|
39322
39350
|
if (overrideRefusal !== void 0) return overrideRefusal;
|
|
39323
39351
|
const baseOf = workflow.def.base;
|
|
39324
|
-
const vars =
|
|
39352
|
+
const vars = resolveStartVars(workflow.vars, yield* StartFlags, varOverrides, (yield* Host).env);
|
|
39325
39353
|
const multiline = multilineSetting(vars);
|
|
39326
39354
|
if (multiline !== void 0) return refusal(`${commandLabel}: process setting "${multiline}" spans several lines — a process setting is pinned in a commit trailer and must be a single line`);
|
|
39327
39355
|
const template = yield* try_({
|
|
@@ -39673,9 +39701,9 @@ const pendingTree = (workspace, entries, rewrite) => {
|
|
|
39673
39701
|
* are always live. `startOverrides` are `--var` values, passed only while a
|
|
39674
39702
|
* process is being started.
|
|
39675
39703
|
*/
|
|
39676
|
-
const settingsFor = (workflow, pinnedVars, hostEnv, startOverrides = {}) => ({
|
|
39704
|
+
const settingsFor = (workflow, pinnedVars, hostEnv, startOverrides = {}, startFlags) => ({
|
|
39677
39705
|
vars: {
|
|
39678
|
-
...
|
|
39706
|
+
...resolveStartVars(workflow.vars, startFlags, startOverrides, hostEnv),
|
|
39679
39707
|
...pinnedVars
|
|
39680
39708
|
},
|
|
39681
39709
|
env: resolveVars(workflow.env, {}, hostEnv)
|
|
@@ -39849,7 +39877,8 @@ const costByModel = (entries) => {
|
|
|
39849
39877
|
const setupFor = (config, run, workspace, host, startOverrides = {}) => gen(function* () {
|
|
39850
39878
|
const resolved = yield* workflowOf(config, run);
|
|
39851
39879
|
const def = resolved.def;
|
|
39852
|
-
const
|
|
39880
|
+
const startFlags = run.trace.length === 0 ? yield* StartFlags : {};
|
|
39881
|
+
const { vars, env } = settingsFor(resolved, run.pinnedVars, host.env, startOverrides, startFlags);
|
|
39853
39882
|
const skills = yield* resolveScopeSkills(def, vars);
|
|
39854
39883
|
const access = yield* resolveScopeAccess(def, skills, vars);
|
|
39855
39884
|
const budget = yield* try_({
|
|
@@ -39959,7 +39988,7 @@ const currentRest = restAt(void 0);
|
|
|
39959
39988
|
*/
|
|
39960
39989
|
const startRefusal = (rest, resolved, startVars) => gen(function* () {
|
|
39961
39990
|
const host = yield* Host;
|
|
39962
|
-
const { vars, env } = settingsFor(resolved, {}, host.env, startVars);
|
|
39991
|
+
const { vars, env } = settingsFor(resolved, {}, host.env, startVars, yield* StartFlags);
|
|
39963
39992
|
const skills = yield* resolveScopeSkills(resolved.def, vars);
|
|
39964
39993
|
const access = yield* resolveScopeAccess(resolved.def, skills, vars);
|
|
39965
39994
|
const workspace = rest.setup.workspace;
|
|
@@ -40173,7 +40202,7 @@ const summaryFor = (run) => gen(function* () {
|
|
|
40173
40202
|
})),
|
|
40174
40203
|
processCost: run.costEntries.reduce((sum, entry) => sum + entry.cost, 0),
|
|
40175
40204
|
processCostByModel: costByModel(run.costEntries),
|
|
40176
|
-
...settingsFor(resolved, run.pinnedVars, host.env)
|
|
40205
|
+
...settingsFor(resolved, run.pinnedVars, host.env, {}, {})
|
|
40177
40206
|
});
|
|
40178
40207
|
});
|
|
40179
40208
|
/** Repository-relative paths of the config files today's config and the process's own record name; one outside the repository cannot be read at a ref, so it is left out. */
|
|
@@ -41651,6 +41680,12 @@ const FLAGS = [
|
|
|
41651
41680
|
if (/[\r\n]/.test(value)) return left(`gtd: --var ${name} must be a single-line value`);
|
|
41652
41681
|
if (seen.has(name)) return left(`gtd: --var ${name} specified more than once`);
|
|
41653
41682
|
seen.add(name);
|
|
41683
|
+
if (name.startsWith("flag_")) {
|
|
41684
|
+
const pinned = flagSettingValue(value);
|
|
41685
|
+
if (pinned === void 0) return left(`gtd: --var ${name} must be 1, 0, true or false`);
|
|
41686
|
+
vars[name] = pinned;
|
|
41687
|
+
continue;
|
|
41688
|
+
}
|
|
41654
41689
|
vars[name] = value;
|
|
41655
41690
|
}
|
|
41656
41691
|
return right(vars);
|
|
@@ -42488,7 +42523,7 @@ const runCli = (argv, io) => {
|
|
|
42488
42523
|
return flatMap$4(Host, ({ env }) => try_({
|
|
42489
42524
|
try: () => resolveFlags(env, io.flags),
|
|
42490
42525
|
catch: (e) => new GtdError(e.message)
|
|
42491
|
-
})).pipe(flatMap$4(() => runCommand(plan.command, plan.json, out)), map$4((code) => {
|
|
42526
|
+
})).pipe(flatMap$4((flags) => runCommand(plan.command, plan.json, out).pipe(provideService(StartFlags, flagSettings(flags)))), map$4((code) => {
|
|
42492
42527
|
out.flush();
|
|
42493
42528
|
io.exit(code);
|
|
42494
42529
|
}), provide$1(io.layers(plan.verbose)), sandbox, catchAll((cause) => isInterruptedOnly(cause) ? failCause$2(cause) : report(io, plan.json.kind !== "off")(cause)));
|
package/dist/testkit.mjs
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { checkScript, configProblems, configure, installContext, isFactoryWorkflow, moveScript, protocolMismatch, removeScript, restoreScript, revertScript, showScript, t as flows_exports } from "./flows.mjs";
|
|
2
2
|
import { E as ACCESS_REFUSAL, _ as demandOf, a as landFields, c as renderLandJson, d as renderBeatPlain, f as beatDocument, g as beatKindOf, i as judgeJson, k as renderFormat, l as renderLandPlain, m as statusOf, n as resolveSession, p as renderBeatJson, r as selectPath, s as noopText, t as globMatches } from "./chunks/wire-C12dahrH.mjs";
|
|
3
3
|
import { C as headingSections, S as headingSectionBodies, a as unansweredQuestions, b as parseThreadsWithFindings, n as openThreads, r as steeringFormatFor, s as parseCodeThreads, t as BUILT_IN_MODE_NAMES, w as formatFinding } from "./chunks/steering-DVILanVf.mjs";
|
|
4
|
-
import { $ as logWarning, $i as
|
|
4
|
+
import { $ as logWarning, $i as NodeInspectSymbol, $n as map$5, $r as make$19, $t as provide$1, A as catchIf, Ai as add, An as scopeMake, Ar as flatMap$3, At as suspend$5, B as flatMap$4, Bi as getOrElse, Bn as get$3, Br as sync$1, Bt as unsafeMakeLatch, C as all$1, Ci as toArray, Cn as isInterrupted, Cr as exitFail, Ct as sandbox, D as async, Di as GenericTag, Dn as squash, Dr as exitZipRight, Dt as scopedWith$1, E as asVoid$1, Ei as unsafeHead, En as reduceWithContext, Er as exitVoid, Et as scoped$4, F as ensuring$2, Fi as fromIterable, Fn as join$3, Fr as map$3, Ft as tryMap, G as forkIn, Gi as none, Gn as TypeId$10, Gr as whenEffect, Gt as zipLeft, H as fnUntraced, Hi as isSome, Hn as modify$1, Hr as uninterruptible, Ht as when, I as exit, Ii as splitAt, In as sequential, Ir as onInterrupt, It as tryPromise, J as ignore, Ji as left, Jn as all, Jr as DeferredTypeId$1, Jt as spaced$1, K as forkScoped, Ki as some, Kn as Class, Kr as withFiberRuntime, Kt as zipRight$3, L as fail$5, Li as filter$1, Ln as bind, Lr as scopeClose, Lt as try_, M as die$2, Mi as getOption, Mn as _await$2, Mr as interruptAsFiber, Mt as tap, N as dieMessage, Ni as omit, Nn as inheritAll$1, Nr as interruptFiber, Nt as tapErrorCause, O as catchAll$1, Oi as Reference, On as ensuring$3, Or as fiberId, Ot as serviceOption, P as either, Pi as empty$5, Pn as interruptAllAs$1, Pr as interruptible$1, Pt as timeout, Q as isEffect, Qi as BaseProto, Qn as isFailure, Qr as ids, Qt as mergeAll$2, R as failCause$4, Ri as flatMap$5, Rn as bindTo, Rr as succeed$4, Rt as uninterruptible$1, S as addFinalizer$1, Si as takeRight, Sn as isDieType, Sr as exitAs, St as runtime, T as as, Ti as unsafeGet, Tn as map$6, Tr as exitSucceed, Tt as scopeWith, U as forEach$2, Ui as map$8, Un as set$1, Ur as uninterruptibleMask$1, Ut as withFiberRuntime$1, V as flatten$4, Vi as isNone, Vn as make$16, Vr as tap$1, Vt as unsafeMakeSemaphore$1, W as forkDaemon, Wi as match$4, Wn as update$1, Wr as void_$2, Wt as zip$1, X as interruptible, Xi as right, Xn as fail$4, Xr as combine, Xt as tagged, Y as interrupt$4, Yi as match$2, Yn as die, Yr as empty$6, Yt as TaggedError$1, Z as intoDeferred, Zi as pipeArguments, Zn as failCause$3, Zr as combineAll, Zt as fromEffect$5, _ as decodeSync, _i as of, _n as fail$3, _r as deferredIsDone, _t as raceWith, a as Literal, aa as constTrue, ai as size$2, an as updateContext$1, ar as zipRight$2, at as matchCause, b as acquireRelease, bi as reverse, bn as interrupt$3, br as deferredUnsafeDone, bt as runPromise, c as String$, ca as dual, ci as append$1, cn as Scope, cr as asyncInterrupt, ct as negate, d as Union, di as empty$4, dn as close, dr as deferredAwait, dt as orElse, ea as format, ei as none$1, en as provideMerge$1, er as mapBoth, et as makeSemaphore, f as between, fi as filter, fn as extend, fr as deferredComplete, ft as orElseSucceed, gi as map$7, gn as die$1, gr as deferredInterruptWith, gt as race, hi as isEmpty$2, hn as NoSuchElementException, hr as deferredInterrupt, ht as provideService, i as Defect, ia as constFalse, ii as has, in as unsafeRunPromiseExit, ir as zip$2, it as match$5, j as catchTag, ji as get$5, jn as scopeTag, jr as interrupt$2, jt as sync$2, k as catchAllCause, ki as Tag, kn as forEachConcurrentDiscard, kr as fiberRefLocally, kt as succeed$6, l as Struct, la as identity, li as appendAll, ln as addFinalizer, lr as catchAll, lt as onError, m as optional$1, mi as isChunk, mn as make$18, mr as deferredFailCause, mt as provide$2, n as Boolean$, na as equals, ni as make$17, nn as succeed$3, nr as succeed$5, nt as mapBoth$1, o as Never, oa as constUndefined, oi as decode, on as forkIn$1, or as as$1, ot as matchCauseEffect, p as decodeUnknown, pi as fromIterable$1, pn as fork, pr as deferredFail, pt as promise, q as gen, qi as isLeft, qn as spanTag, qr as zipRight$1, qt as zipWith, r as Cause, ra as hasProperty, ri as set$2, rn as unsafeFork, rr as void_$3, rt as mapError, s as Number$, sa as constVoid, si as isFinite, sn as unsafeMakeSemaphore, sr as asVoid, st as matchEffect, t as Array$, ta as toJSON, ti as get$4, tn as scoped$3, tr as match$3, tt as map$4, u as TaggedError, ua as pipe, ui as drop, un as addFinalizerExit, ur as currentContext$1, ut as orDie, v as encodeSync, vi as prepend, vn as failureOrCause, vr as deferredMake, vt as repeat, w as annotateLogs, wi as unsafeFromArray, wn as isInterruptedOnly, wr as exitFailCause, wt as scope, x as acquireUseRelease$2, xi as take$2, xn as interruptors, xr as deferredUnsafeMake, xt as runPromiseExit$1, y as _void, yi as reduce, yn as flipCauseOption, yr as deferredSucceed, yt as retry, z as fiberIdWith, zi as fromNullable, zn as sleep, zr as suspend$4, zt as uninterruptibleMask } from "./chunks/Schema-DO5ttJaI.mjs";
|
|
5
5
|
import { createRequire } from "node:module";
|
|
6
6
|
import * as Crypto from "node:crypto";
|
|
7
7
|
import { createHash } from "node:crypto";
|
|
@@ -6097,13 +6097,23 @@ const restorability = (git, headHash, tipHash) => gen(function* () {
|
|
|
6097
6097
|
});
|
|
6098
6098
|
//#endregion
|
|
6099
6099
|
//#region src/flags/index.ts
|
|
6100
|
-
const FLAGS$1 = [
|
|
6100
|
+
const FLAGS$1 = [{
|
|
6101
|
+
name: "naive_pass",
|
|
6102
|
+
owner: "pmelab",
|
|
6103
|
+
expiry: "2027-01-15",
|
|
6104
|
+
kind: "release"
|
|
6105
|
+
}];
|
|
6101
6106
|
const BOOL = {
|
|
6102
6107
|
"0": false,
|
|
6103
6108
|
false: false,
|
|
6104
6109
|
"1": true,
|
|
6105
6110
|
true: true
|
|
6106
6111
|
};
|
|
6112
|
+
/** A `flag_<name>` setting's value as the pinned `"1"`/`"0"`, or undefined when garbled. */
|
|
6113
|
+
const flagSettingValue = (raw) => {
|
|
6114
|
+
const key = raw.toLowerCase();
|
|
6115
|
+
return Object.hasOwn(BOOL, key) ? BOOL[key] ? "1" : "0" : void 0;
|
|
6116
|
+
};
|
|
6107
6117
|
const resolveFlags = (env, registry = FLAGS$1) => {
|
|
6108
6118
|
const out = {};
|
|
6109
6119
|
for (const { name, defaultOn } of registry) {
|
|
@@ -6118,6 +6128,7 @@ const resolveFlags = (env, registry = FLAGS$1) => {
|
|
|
6118
6128
|
}
|
|
6119
6129
|
return out;
|
|
6120
6130
|
};
|
|
6131
|
+
const flagSettings = (flags) => Object.fromEntries(Object.entries(flags).map(([name, on]) => [`flag_${name}`, on ? "1" : "0"]));
|
|
6121
6132
|
//#endregion
|
|
6122
6133
|
//#region src/install/Version.ts
|
|
6123
6134
|
const _require = createRequire(import.meta.url);
|
|
@@ -7533,6 +7544,8 @@ const compileConfig = (value, origin) => {
|
|
|
7533
7544
|
//#endregion
|
|
7534
7545
|
//#region src/workflow/vars.ts
|
|
7535
7546
|
const PREFIX = "GTD_";
|
|
7547
|
+
/** The live release flags as `flag_<name>` settings, provided by the CLI; absent means no flags. */
|
|
7548
|
+
var StartFlags = class extends Reference()("StartFlags", { defaultValue: () => ({}) }) {};
|
|
7536
7549
|
/**
|
|
7537
7550
|
* One kind of setting, later wins: the workflow's own defaults, `--var`
|
|
7538
7551
|
* overrides (process settings only; environment settings pass `{}`), then
|
|
@@ -7552,6 +7565,18 @@ const resolveVars = (workflowVars, entryVars, env) => {
|
|
|
7552
7565
|
}
|
|
7553
7566
|
return merged;
|
|
7554
7567
|
};
|
|
7568
|
+
/**
|
|
7569
|
+
* `resolveVars` for a process being STARTED: `flags` land between the workflow
|
|
7570
|
+
* defaults and `--var`, for already-declared names only. A running process never
|
|
7571
|
+
* calls this — it replays its pinned record.
|
|
7572
|
+
*/
|
|
7573
|
+
const resolveStartVars = (workflowVars, flags, entryVars, env) => {
|
|
7574
|
+
const declared = Object.fromEntries(Object.entries(flags).filter(([name]) => Object.hasOwn(workflowVars, name)));
|
|
7575
|
+
return resolveVars({
|
|
7576
|
+
...workflowVars,
|
|
7577
|
+
...declared
|
|
7578
|
+
}, entryVars, env);
|
|
7579
|
+
};
|
|
7555
7580
|
/** The first process setting whose value spans lines — a `Gtd-Var:` trailer cannot carry it. */
|
|
7556
7581
|
const multilineSetting = (vars) => Object.keys(vars).sort().find((name) => /[\r\n]/.test(vars[name]));
|
|
7557
7582
|
const SETTING_NAME = /^[A-Za-z_][A-Za-z0-9_]*$/;
|
|
@@ -8480,7 +8505,7 @@ const planStart = (current, actor, start) => gen(function* () {
|
|
|
8480
8505
|
const overrideRefusal = yield* checkOverrides(commandLabel, varOverrides, Object.keys(workflow.vars), Object.keys(workflow.env));
|
|
8481
8506
|
if (overrideRefusal !== void 0) return overrideRefusal;
|
|
8482
8507
|
const baseOf = workflow.def.base;
|
|
8483
|
-
const vars =
|
|
8508
|
+
const vars = resolveStartVars(workflow.vars, yield* StartFlags, varOverrides, (yield* Host).env);
|
|
8484
8509
|
const multiline = multilineSetting(vars);
|
|
8485
8510
|
if (multiline !== void 0) return refusal(`${commandLabel}: process setting "${multiline}" spans several lines — a process setting is pinned in a commit trailer and must be a single line`);
|
|
8486
8511
|
const template = yield* try_({
|
|
@@ -8828,9 +8853,9 @@ const pendingTree = (workspace, entries, rewrite) => {
|
|
|
8828
8853
|
* are always live. `startOverrides` are `--var` values, passed only while a
|
|
8829
8854
|
* process is being started.
|
|
8830
8855
|
*/
|
|
8831
|
-
const settingsFor = (workflow, pinnedVars, hostEnv, startOverrides = {}) => ({
|
|
8856
|
+
const settingsFor = (workflow, pinnedVars, hostEnv, startOverrides = {}, startFlags) => ({
|
|
8832
8857
|
vars: {
|
|
8833
|
-
...
|
|
8858
|
+
...resolveStartVars(workflow.vars, startFlags, startOverrides, hostEnv),
|
|
8834
8859
|
...pinnedVars
|
|
8835
8860
|
},
|
|
8836
8861
|
env: resolveVars(workflow.env, {}, hostEnv)
|
|
@@ -9004,7 +9029,8 @@ const costByModel = (entries) => {
|
|
|
9004
9029
|
const setupFor = (config, run, workspace, host, startOverrides = {}) => gen(function* () {
|
|
9005
9030
|
const resolved = yield* workflowOf(config, run);
|
|
9006
9031
|
const def = resolved.def;
|
|
9007
|
-
const
|
|
9032
|
+
const startFlags = run.trace.length === 0 ? yield* StartFlags : {};
|
|
9033
|
+
const { vars, env } = settingsFor(resolved, run.pinnedVars, host.env, startOverrides, startFlags);
|
|
9008
9034
|
const skills = yield* resolveScopeSkills(def, vars);
|
|
9009
9035
|
const access = yield* resolveScopeAccess(def, skills, vars);
|
|
9010
9036
|
const budget = yield* try_({
|
|
@@ -9114,7 +9140,7 @@ const currentRest = restAt(void 0);
|
|
|
9114
9140
|
*/
|
|
9115
9141
|
const startRefusal = (rest, resolved, startVars) => gen(function* () {
|
|
9116
9142
|
const host = yield* Host;
|
|
9117
|
-
const { vars, env } = settingsFor(resolved, {}, host.env, startVars);
|
|
9143
|
+
const { vars, env } = settingsFor(resolved, {}, host.env, startVars, yield* StartFlags);
|
|
9118
9144
|
const skills = yield* resolveScopeSkills(resolved.def, vars);
|
|
9119
9145
|
const access = yield* resolveScopeAccess(resolved.def, skills, vars);
|
|
9120
9146
|
const workspace = rest.setup.workspace;
|
|
@@ -9328,7 +9354,7 @@ const summaryFor = (run) => gen(function* () {
|
|
|
9328
9354
|
})),
|
|
9329
9355
|
processCost: run.costEntries.reduce((sum, entry) => sum + entry.cost, 0),
|
|
9330
9356
|
processCostByModel: costByModel(run.costEntries),
|
|
9331
|
-
...settingsFor(resolved, run.pinnedVars, host.env)
|
|
9357
|
+
...settingsFor(resolved, run.pinnedVars, host.env, {}, {})
|
|
9332
9358
|
});
|
|
9333
9359
|
});
|
|
9334
9360
|
/** Repository-relative paths of the config files today's config and the process's own record name; one outside the repository cannot be read at a ref, so it is left out. */
|
|
@@ -10800,6 +10826,12 @@ const FLAGS = [
|
|
|
10800
10826
|
if (/[\r\n]/.test(value)) return left(`gtd: --var ${name} must be a single-line value`);
|
|
10801
10827
|
if (seen.has(name)) return left(`gtd: --var ${name} specified more than once`);
|
|
10802
10828
|
seen.add(name);
|
|
10829
|
+
if (name.startsWith("flag_")) {
|
|
10830
|
+
const pinned = flagSettingValue(value);
|
|
10831
|
+
if (pinned === void 0) return left(`gtd: --var ${name} must be 1, 0, true or false`);
|
|
10832
|
+
vars[name] = pinned;
|
|
10833
|
+
continue;
|
|
10834
|
+
}
|
|
10803
10835
|
vars[name] = value;
|
|
10804
10836
|
}
|
|
10805
10837
|
return right(vars);
|
|
@@ -11624,7 +11656,7 @@ const runCli = (argv, io) => {
|
|
|
11624
11656
|
return flatMap$4(Host, ({ env }) => try_({
|
|
11625
11657
|
try: () => resolveFlags(env, io.flags),
|
|
11626
11658
|
catch: (e) => new GtdError(e.message)
|
|
11627
|
-
})).pipe(flatMap$4(() => runCommand$1(plan.command, plan.json, out)), map$4((code) => {
|
|
11659
|
+
})).pipe(flatMap$4((flags) => runCommand$1(plan.command, plan.json, out).pipe(provideService(StartFlags, flagSettings(flags)))), map$4((code) => {
|
|
11628
11660
|
out.flush();
|
|
11629
11661
|
io.exit(code);
|
|
11630
11662
|
}), provide$2(io.layers(plan.verbose)), sandbox, catchAll$1((cause) => isInterruptedOnly(cause) ? failCause$4(cause) : report(io, plan.json.kind !== "off")(cause)));
|
|
@@ -13376,7 +13408,8 @@ const testRepo = (options) => {
|
|
|
13376
13408
|
}
|
|
13377
13409
|
throw new Error(`the process did not rest within ${maxBeats} beats`);
|
|
13378
13410
|
},
|
|
13379
|
-
subjects: () => repo.commitHistory().map(({ message }) => message.split("\n")[0] ?? "")
|
|
13411
|
+
subjects: () => repo.commitHistory().map(({ message }) => message.split("\n")[0] ?? ""),
|
|
13412
|
+
messages: () => repo.commitHistory().map(({ message }) => message)
|
|
13380
13413
|
};
|
|
13381
13414
|
return self;
|
|
13382
13415
|
};
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { agent, changes, glob, read, refuse, scope, start, vars } from "../flows.mjs";
|
|
2
|
-
import { a as flagShipped, b as coder, c as envDefaults, i as skills, n as summary, r as access, s as defaults, t as steering } from "../chunks/reserved-
|
|
3
|
-
import { i as refusePendingHandOff, r as handOffTail } from "../chunks/tail-
|
|
2
|
+
import { a as flagShipped, b as coder, c as envDefaults, i as skills, n as summary, r as access, s as defaults, t as steering } from "../chunks/reserved-DM5W_LAt.mjs";
|
|
3
|
+
import { i as refusePendingHandOff, r as handOffTail } from "../chunks/tail-6gvLXXcg.mjs";
|
|
4
4
|
import { i as requireFlag, r as registryEntry, t as flagReferences } from "../chunks/registry-CP3YuV9j.mjs";
|
|
5
5
|
//#region src/workflows/cleanup/cleanup.ts
|
|
6
6
|
const removingPrompt = (name, registry) => `Clean up the release flag "${name}", which is default-on: delete its entry in ${registry}, and remove every \`GTD_FLAG_${name.toUpperCase()}\` check from the shipped sources. Keep the flag-on path; delete code only the off path reached, including tests that pin the off path.`;
|