@yagni-app/code-staging 1.2.13-staging.2167.1 → 1.2.13-staging.2171.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.
|
@@ -46,6 +46,15 @@ export interface PlanFile {
|
|
|
46
46
|
repository: string;
|
|
47
47
|
what: string;
|
|
48
48
|
}>;
|
|
49
|
+
/**
|
|
50
|
+
* What the plan found that the ticket did not ask for (ENG-2966): kept off
|
|
51
|
+
* the plan, shown at its gate for a person to make a ticket of.
|
|
52
|
+
*/
|
|
53
|
+
followUps: Array<{
|
|
54
|
+
title: string;
|
|
55
|
+
why: string;
|
|
56
|
+
repository?: string;
|
|
57
|
+
}>;
|
|
49
58
|
}
|
|
50
59
|
/** The plan's `wrongRepository`, or null when it names no `owner/name`. Confidence is high only when said. */
|
|
51
60
|
export declare function readWrongRepository(value: unknown): PlanFile["wrongRepository"] | null;
|
|
@@ -59,6 +68,12 @@ export declare function repositoryName(value: unknown): string | null;
|
|
|
59
68
|
* for the same repository (case-insensitive) is dropped too.
|
|
60
69
|
*/
|
|
61
70
|
export declare function readRepositoriesNeeded(value: unknown): PlanFile["repositoriesNeeded"];
|
|
71
|
+
/**
|
|
72
|
+
* The plan's `followUps`, one per distinct title in the order written. An
|
|
73
|
+
* entry with no title is dropped; a repository that is not `owner/name` is
|
|
74
|
+
* left off its entry.
|
|
75
|
+
*/
|
|
76
|
+
export declare function readFollowUps(value: unknown): PlanFile["followUps"];
|
|
62
77
|
/** The plan's ```plan-json block as an object, or null when it has none that parses. */
|
|
63
78
|
export declare function extractPlanJson(text: string): Record<string, unknown> | null;
|
|
64
79
|
/** The plan for a person to read: the text without its machine-readable block. */
|
|
@@ -77,6 +77,30 @@ export function readRepositoriesNeeded(value) {
|
|
|
77
77
|
}
|
|
78
78
|
return out;
|
|
79
79
|
}
|
|
80
|
+
/** At most this many follow-ups; the host keeps the same number. */
|
|
81
|
+
const MAX_FOLLOW_UPS = 10;
|
|
82
|
+
/**
|
|
83
|
+
* The plan's `followUps`, one per distinct title in the order written. An
|
|
84
|
+
* entry with no title is dropped; a repository that is not `owner/name` is
|
|
85
|
+
* left off its entry.
|
|
86
|
+
*/
|
|
87
|
+
export function readFollowUps(value) {
|
|
88
|
+
const out = [];
|
|
89
|
+
const seen = new Set();
|
|
90
|
+
for (const entry of list(value)) {
|
|
91
|
+
if (!isRecord(entry))
|
|
92
|
+
continue;
|
|
93
|
+
const title = text(entry.title, 200);
|
|
94
|
+
if (!title || seen.has(title.toLowerCase()))
|
|
95
|
+
continue;
|
|
96
|
+
seen.add(title.toLowerCase());
|
|
97
|
+
const repository = repositoryName(entry.repository);
|
|
98
|
+
out.push({ title, why: text(entry.why) ?? "", ...(repository ? { repository } : {}) });
|
|
99
|
+
if (out.length === MAX_FOLLOW_UPS)
|
|
100
|
+
break;
|
|
101
|
+
}
|
|
102
|
+
return out;
|
|
103
|
+
}
|
|
80
104
|
/** The plan's ```plan-json block as an object, or null when it has none that parses. */
|
|
81
105
|
export function extractPlanJson(text) {
|
|
82
106
|
let found = null;
|
|
@@ -162,6 +186,7 @@ export function buildPlanFile(planText, fallbackPaths) {
|
|
|
162
186
|
repositoriesNeeded,
|
|
163
187
|
...(wrongRepository ? { wrongRepository } : {}),
|
|
164
188
|
dependsOn: readDependsOn(block?.dependsOn),
|
|
189
|
+
followUps: readFollowUps(block?.followUps),
|
|
165
190
|
},
|
|
166
191
|
found: block !== null,
|
|
167
192
|
};
|
|
@@ -74,6 +74,14 @@ export declare const DOCUMENTATION_REPOSITORY_RULE: string;
|
|
|
74
74
|
* without another repository is named, not left as a Risks bullet.
|
|
75
75
|
*/
|
|
76
76
|
export declare const RIGHT_REPOSITORY_RULE: string;
|
|
77
|
+
/**
|
|
78
|
+
* What the planner does with what it finds that the ticket did not ask for
|
|
79
|
+
* (ENG-2966): a nearby bug, a leak, a refactor is a follow-up a person can
|
|
80
|
+
* make a ticket of, never a question, a decision or a step of this plan. And
|
|
81
|
+
* nothing the ticket asked for is put off: work it needs in another
|
|
82
|
+
* repository goes in repositoriesNeeded, so the host offers the split.
|
|
83
|
+
*/
|
|
84
|
+
export declare const FOLLOW_UPS_RULE: string;
|
|
77
85
|
export declare const PLAN_JSON_CONTRACT: string;
|
|
78
86
|
/**
|
|
79
87
|
* The one-attempt lane's session (`yagni go --headless --cloud`): plan,
|
|
@@ -167,6 +167,20 @@ export const RIGHT_REPOSITORY_RULE = '- "wrongRepository" is for a ticket whose
|
|
|
167
167
|
'- "dependsOn" lists every other repository that needs a change before this one can work, each ' +
|
|
168
168
|
"with one line on what it needs there, whether or not the Other repositories section lists it. " +
|
|
169
169
|
"Such a dependency is never only a Risks bullet. Never list a repository the change only reads.";
|
|
170
|
+
/**
|
|
171
|
+
* What the planner does with what it finds that the ticket did not ask for
|
|
172
|
+
* (ENG-2966): a nearby bug, a leak, a refactor is a follow-up a person can
|
|
173
|
+
* make a ticket of, never a question, a decision or a step of this plan. And
|
|
174
|
+
* nothing the ticket asked for is put off: work it needs in another
|
|
175
|
+
* repository goes in repositoriesNeeded, so the host offers the split.
|
|
176
|
+
*/
|
|
177
|
+
export const FOLLOW_UPS_RULE = '- "followUps" lists what you found that the ticket did not ask for: a nearby bug, a security ' +
|
|
178
|
+
"leak, a refactor. Each is a title, one line on why it matters, and its repository when that is " +
|
|
179
|
+
"not this one. A follow-up is never a question, a decision or a step of this plan, however real " +
|
|
180
|
+
"it is: a person makes a ticket of it if they want one. Leave it out when you found nothing.\n" +
|
|
181
|
+
'- Never put off the ticket\'s own work ("for another session", "in a later ticket"). Plan all of ' +
|
|
182
|
+
"what it asked for. Work it needs in another repository goes in repositoriesNeeded, so the ticket " +
|
|
183
|
+
"is split, and is never left out of the plan.";
|
|
170
184
|
export const PLAN_JSON_CONTRACT = "End your answer with a fenced ```plan-json block and nothing after it:\n" +
|
|
171
185
|
"```plan-json\n" +
|
|
172
186
|
"{\n" +
|
|
@@ -181,12 +195,14 @@ export const PLAN_JSON_CONTRACT = "End your answer with a fenced ```plan-json bl
|
|
|
181
195
|
' "paths": ["apps/web"],\n' +
|
|
182
196
|
' "repositoriesNeeded": [{"repository": "owner/name", "summary": "one line on what changes there"}],\n' +
|
|
183
197
|
' "wrongRepository": {"repository": "owner/name", "why": "one line", "confidence": "high|low"},\n' +
|
|
184
|
-
' "dependsOn": [{"repository": "owner/name", "what": "one line on what it needs there"}]
|
|
198
|
+
' "dependsOn": [{"repository": "owner/name", "what": "one line on what it needs there"}],\n' +
|
|
199
|
+
' "followUps": [{"title": "...", "why": "one line", "repository": "owner/name"}]\n' +
|
|
185
200
|
"}\n" +
|
|
186
201
|
"```\n" +
|
|
187
202
|
"Rules the host enforces, so getting them wrong loses the question:\n" +
|
|
188
203
|
'- "kind" is "fact" when the answer could be looked up and "decision" when it is a person\'s call. ' +
|
|
189
|
-
'A decision you would make yourself carries your recommendation and is stated, not asked; mark "oneWay": true only when it cannot be undone
|
|
204
|
+
'A decision you would make yourself carries your recommendation and is stated, not asked; mark "oneWay": true only when it cannot be undone. ' +
|
|
205
|
+
"A recommendation whose planChange adds acceptance criteria widens the ticket, so a person is asked it.\n" +
|
|
190
206
|
'- On a fact, "checked" says in at most 4 short lines what you read or ran for it and what it showed, and what you could not read. ' +
|
|
191
207
|
"A fact whose every answer plans the same work (no option carries a planChange) is stated as your assumption, not asked.\n" +
|
|
192
208
|
"- At most two alternatives per question. A planChange only adds or rewords; it never removes.\n" +
|
|
@@ -200,7 +216,9 @@ export const PLAN_JSON_CONTRACT = "End your answer with a fenced ```plan-json bl
|
|
|
200
216
|
"never list a repository the change only reads. " +
|
|
201
217
|
DOCUMENTATION_REPOSITORY_RULE +
|
|
202
218
|
"\n" +
|
|
203
|
-
RIGHT_REPOSITORY_RULE
|
|
219
|
+
RIGHT_REPOSITORY_RULE +
|
|
220
|
+
"\n" +
|
|
221
|
+
FOLLOW_UPS_RULE;
|
|
204
222
|
/**
|
|
205
223
|
* The cloud plan stage's task: the input folder the host wrote, read first,
|
|
206
224
|
* then a plan grounded in the installed checkout, inside the stage's own
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@yagni-app/code-staging",
|
|
3
|
-
"version": "1.2.13-staging.
|
|
3
|
+
"version": "1.2.13-staging.2171.1",
|
|
4
4
|
"description": "YAGNI Code: a terminal coding agent that already knows your company. One YAGNI login routes the model and grounds the agent in your team's context.",
|
|
5
5
|
"license": "SEE LICENSE IN LICENSE.md",
|
|
6
6
|
"author": "YAGNI, Inc. <jack@yagni.app> (https://yagni.app)",
|
|
@@ -58,5 +58,5 @@
|
|
|
58
58
|
"turndown": "^7.2.4",
|
|
59
59
|
"typebox": "^1.3.15"
|
|
60
60
|
},
|
|
61
|
-
"yagniSourceSha": "
|
|
61
|
+
"yagniSourceSha": "4c225e34b3364d25830d9d4d88f071ffedf799f3"
|
|
62
62
|
}
|