chief-clancy 0.5.4 → 0.5.5
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.md +1 -1
- package/dist/bundle/clancy-once.js +54 -29
- package/dist/schemas/bitbucket-pr.d.ts +122 -0
- package/dist/schemas/bitbucket-pr.d.ts.map +1 -0
- package/dist/schemas/bitbucket-pr.js +69 -0
- package/dist/schemas/bitbucket-pr.js.map +1 -0
- package/dist/schemas/env.d.ts +4 -0
- package/dist/schemas/env.d.ts.map +1 -1
- package/dist/schemas/env.js +2 -0
- package/dist/schemas/env.js.map +1 -1
- package/dist/schemas/github.d.ts +60 -0
- package/dist/schemas/github.d.ts.map +1 -1
- package/dist/schemas/github.js +32 -0
- package/dist/schemas/github.js.map +1 -1
- package/dist/schemas/gitlab-mr.d.ts +62 -0
- package/dist/schemas/gitlab-mr.d.ts.map +1 -0
- package/dist/schemas/gitlab-mr.js +31 -0
- package/dist/schemas/gitlab-mr.js.map +1 -0
- package/dist/scripts/once/once.d.ts.map +1 -1
- package/dist/scripts/once/once.js +181 -23
- package/dist/scripts/once/once.js.map +1 -1
- package/dist/scripts/shared/git-ops/git-ops.d.ts +9 -0
- package/dist/scripts/shared/git-ops/git-ops.d.ts.map +1 -1
- package/dist/scripts/shared/git-ops/git-ops.js +20 -0
- package/dist/scripts/shared/git-ops/git-ops.js.map +1 -1
- package/dist/scripts/shared/progress/progress.d.ts +41 -0
- package/dist/scripts/shared/progress/progress.d.ts.map +1 -1
- package/dist/scripts/shared/progress/progress.js +96 -1
- package/dist/scripts/shared/progress/progress.js.map +1 -1
- package/dist/scripts/shared/prompt/prompt.d.ts +27 -0
- package/dist/scripts/shared/prompt/prompt.d.ts.map +1 -1
- package/dist/scripts/shared/prompt/prompt.js +32 -7
- package/dist/scripts/shared/prompt/prompt.js.map +1 -1
- package/dist/scripts/shared/pull-request/bitbucket/bitbucket.d.ts +41 -9
- package/dist/scripts/shared/pull-request/bitbucket/bitbucket.d.ts.map +1 -1
- package/dist/scripts/shared/pull-request/bitbucket/bitbucket.js +182 -0
- package/dist/scripts/shared/pull-request/bitbucket/bitbucket.js.map +1 -1
- package/dist/scripts/shared/pull-request/github/github.d.ts +34 -1
- package/dist/scripts/shared/pull-request/github/github.d.ts.map +1 -1
- package/dist/scripts/shared/pull-request/github/github.js +106 -2
- package/dist/scripts/shared/pull-request/github/github.js.map +1 -1
- package/dist/scripts/shared/pull-request/gitlab/gitlab.d.ts +32 -9
- package/dist/scripts/shared/pull-request/gitlab/gitlab.d.ts.map +1 -1
- package/dist/scripts/shared/pull-request/gitlab/gitlab.js +127 -0
- package/dist/scripts/shared/pull-request/gitlab/gitlab.js.map +1 -1
- package/dist/scripts/shared/pull-request/pr-body/pr-body.d.ts.map +1 -1
- package/dist/scripts/shared/pull-request/pr-body/pr-body.js +7 -0
- package/dist/scripts/shared/pull-request/pr-body/pr-body.js.map +1 -1
- package/dist/scripts/shared/pull-request/rework-comment/rework-comment.d.ts +23 -0
- package/dist/scripts/shared/pull-request/rework-comment/rework-comment.d.ts.map +1 -0
- package/dist/scripts/shared/pull-request/rework-comment/rework-comment.js +30 -0
- package/dist/scripts/shared/pull-request/rework-comment/rework-comment.js.map +1 -0
- package/dist/types/index.d.ts +1 -1
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/remote.d.ts +9 -0
- package/dist/types/remote.d.ts.map +1 -1
- package/package.json +1 -1
- package/src/roles/setup/workflows/init.md +15 -0
- package/src/roles/setup/workflows/scaffold.md +18 -0
- package/src/roles/setup/workflows/settings.md +20 -5
|
@@ -1,4 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* GitLab merge request creation and review state checking.
|
|
3
|
+
*
|
|
4
|
+
* Uses the GitLab REST API v4 to create merge requests, check review state,
|
|
5
|
+
* and fetch review comments.
|
|
6
|
+
* Supports both gitlab.com and self-hosted instances.
|
|
7
|
+
*
|
|
8
|
+
* Auth: `PRIVATE-TOKEN` header (personal access token with `api` scope).
|
|
9
|
+
*/
|
|
10
|
+
import { gitlabDiscussionsSchema, gitlabMrListSchema, } from '../../../../schemas/gitlab-mr.js';
|
|
1
11
|
import { postPullRequest } from '../post-pr/post-pr.js';
|
|
12
|
+
import { extractReworkContent, isReworkComment, } from '../rework-comment/rework-comment.js';
|
|
2
13
|
/**
|
|
3
14
|
* Create a merge request on GitLab.
|
|
4
15
|
*
|
|
@@ -24,4 +35,120 @@ export async function createMergeRequest(token, apiBase, projectPath, sourceBran
|
|
|
24
35
|
return { url: data.web_url ?? '', number: data.iid ?? 0 };
|
|
25
36
|
}, (status, text) => status === 409 && text.includes('already exists'));
|
|
26
37
|
}
|
|
38
|
+
/**
|
|
39
|
+
* Check the review state of an open MR for a given branch.
|
|
40
|
+
*
|
|
41
|
+
* Finds the open MR matching the source branch, fetches all discussions.
|
|
42
|
+
* Inline notes (type `DiffNote`) always trigger rework. General conversation
|
|
43
|
+
* notes only trigger rework when prefixed with `Rework:`.
|
|
44
|
+
*
|
|
45
|
+
* @param token - The GitLab personal access token.
|
|
46
|
+
* @param apiBase - The API base URL (e.g. `https://gitlab.com/api/v4`).
|
|
47
|
+
* @param projectPath - The raw project path (e.g. `group/subgroup/project`). URL-encoded internally.
|
|
48
|
+
* @param branch - The source branch to look up.
|
|
49
|
+
* @param since - ISO 8601 timestamp; only notes created after this time trigger rework.
|
|
50
|
+
* @returns The review state if an open MR exists, otherwise `undefined`.
|
|
51
|
+
*/
|
|
52
|
+
export async function checkMrReviewState(token, apiBase, projectPath, branch, since) {
|
|
53
|
+
try {
|
|
54
|
+
const encodedPath = encodeURIComponent(projectPath);
|
|
55
|
+
const mrUrl = `${apiBase}/projects/${encodedPath}/merge_requests?source_branch=${branch}&state=opened`;
|
|
56
|
+
const mrRes = await fetch(mrUrl, {
|
|
57
|
+
headers: { 'PRIVATE-TOKEN': token },
|
|
58
|
+
});
|
|
59
|
+
if (!mrRes.ok)
|
|
60
|
+
return undefined;
|
|
61
|
+
const data = gitlabMrListSchema.parse(await mrRes.json());
|
|
62
|
+
if (data.length === 0)
|
|
63
|
+
return undefined;
|
|
64
|
+
const mr = data[0];
|
|
65
|
+
const discussionsUrl = `${apiBase}/projects/${encodedPath}/merge_requests/${mr.iid}/discussions?per_page=100`;
|
|
66
|
+
const discussionsRes = await fetch(discussionsUrl, {
|
|
67
|
+
headers: { 'PRIVATE-TOKEN': token },
|
|
68
|
+
});
|
|
69
|
+
if (!discussionsRes.ok)
|
|
70
|
+
return undefined;
|
|
71
|
+
const discussions = gitlabDiscussionsSchema.parse(await discussionsRes.json());
|
|
72
|
+
let hasRework = false;
|
|
73
|
+
for (const discussion of discussions) {
|
|
74
|
+
for (const note of discussion.notes) {
|
|
75
|
+
if (note.system)
|
|
76
|
+
continue;
|
|
77
|
+
if (since && note.created_at && note.created_at <= since)
|
|
78
|
+
continue;
|
|
79
|
+
if (note.type === 'DiffNote' &&
|
|
80
|
+
note.resolvable !== false &&
|
|
81
|
+
note.resolved !== true) {
|
|
82
|
+
hasRework = true;
|
|
83
|
+
break;
|
|
84
|
+
}
|
|
85
|
+
if (isReworkComment(note.body)) {
|
|
86
|
+
hasRework = true;
|
|
87
|
+
break;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
if (hasRework)
|
|
91
|
+
break;
|
|
92
|
+
}
|
|
93
|
+
return {
|
|
94
|
+
changesRequested: hasRework,
|
|
95
|
+
prNumber: mr.iid,
|
|
96
|
+
prUrl: mr.web_url,
|
|
97
|
+
};
|
|
98
|
+
}
|
|
99
|
+
catch {
|
|
100
|
+
return undefined;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
/**
|
|
104
|
+
* Fetch feedback comments from an MR's discussions.
|
|
105
|
+
*
|
|
106
|
+
* Inline notes (type `DiffNote`) are always included — they inherently
|
|
107
|
+
* represent change requests. General conversation notes are only included
|
|
108
|
+
* when they start with `Rework:` (case-insensitive), with the prefix
|
|
109
|
+
* stripped. Inline notes are prefixed with `[new_path]` when available.
|
|
110
|
+
*
|
|
111
|
+
* @param token - The GitLab personal access token.
|
|
112
|
+
* @param apiBase - The API base URL (e.g. `https://gitlab.com/api/v4`).
|
|
113
|
+
* @param projectPath - The raw project path. URL-encoded internally.
|
|
114
|
+
* @param mrIid - The MR internal ID (iid).
|
|
115
|
+
* @param since - ISO 8601 timestamp; only notes created after this time are returned.
|
|
116
|
+
* @returns An array of feedback descriptions.
|
|
117
|
+
*/
|
|
118
|
+
export async function fetchMrReviewComments(token, apiBase, projectPath, mrIid, since) {
|
|
119
|
+
try {
|
|
120
|
+
const encodedPath = encodeURIComponent(projectPath);
|
|
121
|
+
const url = `${apiBase}/projects/${encodedPath}/merge_requests/${mrIid}/discussions?per_page=100`;
|
|
122
|
+
const res = await fetch(url, {
|
|
123
|
+
headers: { 'PRIVATE-TOKEN': token },
|
|
124
|
+
});
|
|
125
|
+
if (!res.ok)
|
|
126
|
+
return [];
|
|
127
|
+
const discussions = gitlabDiscussionsSchema.parse(await res.json());
|
|
128
|
+
const comments = [];
|
|
129
|
+
for (const discussion of discussions) {
|
|
130
|
+
for (const note of discussion.notes) {
|
|
131
|
+
if (note.system)
|
|
132
|
+
continue;
|
|
133
|
+
if (since && note.created_at && note.created_at <= since)
|
|
134
|
+
continue;
|
|
135
|
+
if (note.type === 'DiffNote' &&
|
|
136
|
+
note.resolvable !== false &&
|
|
137
|
+
note.resolved !== true) {
|
|
138
|
+
const prefix = note.position?.new_path
|
|
139
|
+
? `[${note.position.new_path}] `
|
|
140
|
+
: '';
|
|
141
|
+
comments.push(`${prefix}${note.body}`);
|
|
142
|
+
}
|
|
143
|
+
else if (isReworkComment(note.body)) {
|
|
144
|
+
comments.push(extractReworkContent(note.body));
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
return comments;
|
|
149
|
+
}
|
|
150
|
+
catch {
|
|
151
|
+
return [];
|
|
152
|
+
}
|
|
153
|
+
}
|
|
27
154
|
//# sourceMappingURL=gitlab.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"gitlab.js","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/gitlab/gitlab.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"gitlab.js","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/gitlab/gitlab.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pr-body.d.ts","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/pr-body/pr-body.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,kBAAkB,CAAC;AAE5D;;;;;;;;;GASG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,
|
|
1
|
+
{"version":3,"file":"pr-body.d.ts","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/pr-body/pr-body.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,kBAAkB,CAAC;AAE5D;;;;;;;;;GASG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,CA2CvE"}
|
|
@@ -30,6 +30,13 @@ export function buildPrBody(config, ticket) {
|
|
|
30
30
|
}
|
|
31
31
|
lines.push('---');
|
|
32
32
|
lines.push('*Created by [Clancy](https://github.com/Pushedskydiver/clancy)*');
|
|
33
|
+
lines.push('');
|
|
34
|
+
lines.push('---');
|
|
35
|
+
lines.push('**Rework instructions:** To request changes:');
|
|
36
|
+
lines.push('- **Code comments** — leave inline comments on specific lines. These are always picked up automatically.');
|
|
37
|
+
lines.push('- **General feedback** — reply with a comment starting with `Rework:` followed by what needs fixing. Comments without the `Rework:` prefix are treated as discussion.');
|
|
38
|
+
lines.push('');
|
|
39
|
+
lines.push("Example: `Rework: The form validation doesn't handle empty passwords`");
|
|
33
40
|
return lines.join('\n');
|
|
34
41
|
}
|
|
35
42
|
//# sourceMappingURL=pr-body.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pr-body.js","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/pr-body/pr-body.ts"],"names":[],"mappings":"AAQA;;;;;;;;;GASG;AACH,MAAM,UAAU,WAAW,CAAC,MAAmB,EAAE,MAAc;IAC7D,MAAM,KAAK,GAAa,EAAE,CAAC;IAE3B,QAAQ,MAAM,CAAC,QAAQ,EAAE,CAAC;QACxB,KAAK,QAAQ;YACX,KAAK,CAAC,IAAI,CAAC,UAAU,MAAM,CAAC,GAAG,EAAE,CAAC,CAAC;YACnC,MAAM;QACR,KAAK,MAAM;YACT,KAAK,CAAC,IAAI,CACR,cAAc,MAAM,CAAC,GAAG,KAAK,MAAM,CAAC,GAAG,CAAC,aAAa,WAAW,MAAM,CAAC,GAAG,GAAG,CAC9E,CAAC;YACF,MAAM;QACR,KAAK,QAAQ;YACX,KAAK,CAAC,IAAI,CAAC,eAAe,MAAM,CAAC,GAAG,EAAE,CAAC,CAAC;YACxC,MAAM;IACV,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IAEf,IAAI,MAAM,CAAC,WAAW,EAAE,CAAC;QACvB,KAAK,CAAC,IAAI,CAAC,gBAAgB,CAAC,CAAC;QAC7B,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACf,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;QAC/B,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IACjB,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAClB,KAAK,CAAC,IAAI,CAAC,iEAAiE,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"pr-body.js","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/pr-body/pr-body.ts"],"names":[],"mappings":"AAQA;;;;;;;;;GASG;AACH,MAAM,UAAU,WAAW,CAAC,MAAmB,EAAE,MAAc;IAC7D,MAAM,KAAK,GAAa,EAAE,CAAC;IAE3B,QAAQ,MAAM,CAAC,QAAQ,EAAE,CAAC;QACxB,KAAK,QAAQ;YACX,KAAK,CAAC,IAAI,CAAC,UAAU,MAAM,CAAC,GAAG,EAAE,CAAC,CAAC;YACnC,MAAM;QACR,KAAK,MAAM;YACT,KAAK,CAAC,IAAI,CACR,cAAc,MAAM,CAAC,GAAG,KAAK,MAAM,CAAC,GAAG,CAAC,aAAa,WAAW,MAAM,CAAC,GAAG,GAAG,CAC9E,CAAC;YACF,MAAM;QACR,KAAK,QAAQ;YACX,KAAK,CAAC,IAAI,CAAC,eAAe,MAAM,CAAC,GAAG,EAAE,CAAC,CAAC;YACxC,MAAM;IACV,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IAEf,IAAI,MAAM,CAAC,WAAW,EAAE,CAAC;QACvB,KAAK,CAAC,IAAI,CAAC,gBAAgB,CAAC,CAAC;QAC7B,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACf,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;QAC/B,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IACjB,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAClB,KAAK,CAAC,IAAI,CAAC,iEAAiE,CAAC,CAAC;IAC9E,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IACf,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAClB,KAAK,CAAC,IAAI,CAAC,8CAA8C,CAAC,CAAC;IAC3D,KAAK,CAAC,IAAI,CACR,0GAA0G,CAC3G,CAAC;IACF,KAAK,CAAC,IAAI,CACR,uKAAuK,CACxK,CAAC;IACF,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IACf,KAAK,CAAC,IAAI,CACR,uEAAuE,CACxE,CAAC;IAEF,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC1B,CAAC"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Rework comment detection and extraction utilities.
|
|
3
|
+
*
|
|
4
|
+
* Comments starting with "Rework:" (case-insensitive) are treated as
|
|
5
|
+
* rework requests. All other comments are treated as discussion and ignored.
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Check if a comment is a rework request (starts with "Rework:" case-insensitive).
|
|
9
|
+
*
|
|
10
|
+
* @param body - The comment body to check.
|
|
11
|
+
* @returns `true` if the comment starts with "Rework:".
|
|
12
|
+
*/
|
|
13
|
+
export declare function isReworkComment(body: string): boolean;
|
|
14
|
+
/**
|
|
15
|
+
* Extract the rework description from a "Rework: ..." comment.
|
|
16
|
+
*
|
|
17
|
+
* Strips the "Rework:" prefix and returns the remaining content trimmed.
|
|
18
|
+
*
|
|
19
|
+
* @param body - The full comment body starting with "Rework:".
|
|
20
|
+
* @returns The description after the prefix.
|
|
21
|
+
*/
|
|
22
|
+
export declare function extractReworkContent(body: string): string;
|
|
23
|
+
//# sourceMappingURL=rework-comment.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rework-comment.d.ts","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/rework-comment/rework-comment.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH;;;;;GAKG;AACH,wBAAgB,eAAe,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAErD;AAED;;;;;;;GAOG;AACH,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAKzD"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Rework comment detection and extraction utilities.
|
|
3
|
+
*
|
|
4
|
+
* Comments starting with "Rework:" (case-insensitive) are treated as
|
|
5
|
+
* rework requests. All other comments are treated as discussion and ignored.
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Check if a comment is a rework request (starts with "Rework:" case-insensitive).
|
|
9
|
+
*
|
|
10
|
+
* @param body - The comment body to check.
|
|
11
|
+
* @returns `true` if the comment starts with "Rework:".
|
|
12
|
+
*/
|
|
13
|
+
export function isReworkComment(body) {
|
|
14
|
+
return body.trim().toLowerCase().startsWith('rework:');
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Extract the rework description from a "Rework: ..." comment.
|
|
18
|
+
*
|
|
19
|
+
* Strips the "Rework:" prefix and returns the remaining content trimmed.
|
|
20
|
+
*
|
|
21
|
+
* @param body - The full comment body starting with "Rework:".
|
|
22
|
+
* @returns The description after the prefix.
|
|
23
|
+
*/
|
|
24
|
+
export function extractReworkContent(body) {
|
|
25
|
+
return body
|
|
26
|
+
.trim()
|
|
27
|
+
.replace(/^rework:\s*/i, '')
|
|
28
|
+
.trim();
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=rework-comment.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rework-comment.js","sourceRoot":"","sources":["../../../../../src/scripts/shared/pull-request/rework-comment/rework-comment.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH;;;;;GAKG;AACH,MAAM,UAAU,eAAe,CAAC,IAAY;IAC1C,OAAO,IAAI,CAAC,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC;AACzD,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,UAAU,oBAAoB,CAAC,IAAY;IAC/C,OAAO,IAAI;SACR,IAAI,EAAE;SACN,OAAO,CAAC,cAAc,EAAE,EAAE,CAAC;SAC3B,IAAI,EAAE,CAAC;AACZ,CAAC"}
|
package/dist/types/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
export type { BoardProvider, Ticket } from './board.js';
|
|
2
|
-
export type { GitPlatform, PrCreationResult, ProgressStatus, RemoteInfo, } from './remote.js';
|
|
2
|
+
export type { GitPlatform, PrCreationResult, PrReviewState, ProgressStatus, RemoteInfo, } from './remote.js';
|
|
3
3
|
export type { BoardConfig, GitHubEnv, JiraEnv, LinearEnv, SharedEnv, } from '../schemas/env.js';
|
|
4
4
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/types/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,aAAa,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;AACxD,YAAY,EACV,WAAW,EACX,gBAAgB,EAChB,cAAc,EACd,UAAU,GACX,MAAM,aAAa,CAAC;AACrB,YAAY,EACV,WAAW,EACX,SAAS,EACT,OAAO,EACP,SAAS,EACT,SAAS,GACV,MAAM,kBAAkB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/types/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,aAAa,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;AACxD,YAAY,EACV,WAAW,EACX,gBAAgB,EAChB,aAAa,EACb,cAAc,EACd,UAAU,GACX,MAAM,aAAa,CAAC;AACrB,YAAY,EACV,WAAW,EACX,SAAS,EACT,OAAO,EACP,SAAS,EACT,SAAS,GACV,MAAM,kBAAkB,CAAC"}
|
package/dist/types/remote.d.ts
CHANGED
|
@@ -39,6 +39,15 @@ export type PrCreationResult = {
|
|
|
39
39
|
error: string;
|
|
40
40
|
alreadyExists?: boolean;
|
|
41
41
|
};
|
|
42
|
+
/** Result of checking PR/MR review state. */
|
|
43
|
+
export type PrReviewState = {
|
|
44
|
+
/** Whether changes have been requested by a reviewer. */
|
|
45
|
+
changesRequested: boolean;
|
|
46
|
+
/** The PR/MR number/ID (needed to fetch comments). */
|
|
47
|
+
prNumber: number;
|
|
48
|
+
/** The PR/MR URL (for logging). */
|
|
49
|
+
prUrl: string;
|
|
50
|
+
};
|
|
42
51
|
/** Progress log status values. */
|
|
43
52
|
export type ProgressStatus = 'DONE' | 'SKIPPED' | 'PR_CREATED' | 'PUSHED' | 'PUSH_FAILED' | 'LOCAL' | 'PLAN' | 'APPROVE' | 'REWORK';
|
|
44
53
|
//# sourceMappingURL=remote.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"remote.d.ts","sourceRoot":"","sources":["../../src/types/remote.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,uCAAuC;AACvC,MAAM,MAAM,WAAW,GACnB,QAAQ,GACR,QAAQ,GACR,WAAW,GACX,kBAAkB,GAClB,OAAO,GACP,SAAS,CAAC;AAEd,qDAAqD;AACrD,MAAM,MAAM,UAAU,GAClB;IACE,IAAI,EAAE,QAAQ,CAAC;IACf,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,QAAQ,CAAC;IACf,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,WAAW,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,kBAAkB,CAAC;IACzB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,OAAO,GAAG,SAAS,CAAC;IAC1B,GAAG,EAAE,MAAM,CAAC;CACb,GACD;IACE,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEN,0CAA0C;AAC1C,MAAM,MAAM,gBAAgB,GACxB;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GACzC;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,KAAK,EAAE,MAAM,CAAC;IAAC,aAAa,CAAC,EAAE,OAAO,CAAA;CAAE,CAAC;AAE1D,kCAAkC;AAClC,MAAM,MAAM,cAAc,GACtB,MAAM,GACN,SAAS,GACT,YAAY,GACZ,QAAQ,GACR,aAAa,GACb,OAAO,GACP,MAAM,GACN,SAAS,GACT,QAAQ,CAAC"}
|
|
1
|
+
{"version":3,"file":"remote.d.ts","sourceRoot":"","sources":["../../src/types/remote.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,uCAAuC;AACvC,MAAM,MAAM,WAAW,GACnB,QAAQ,GACR,QAAQ,GACR,WAAW,GACX,kBAAkB,GAClB,OAAO,GACP,SAAS,CAAC;AAEd,qDAAqD;AACrD,MAAM,MAAM,UAAU,GAClB;IACE,IAAI,EAAE,QAAQ,CAAC;IACf,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,QAAQ,CAAC;IACf,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,WAAW,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,kBAAkB,CAAC;IACzB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;CAClB,GACD;IACE,IAAI,EAAE,OAAO,GAAG,SAAS,CAAC;IAC1B,GAAG,EAAE,MAAM,CAAC;CACb,GACD;IACE,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEN,0CAA0C;AAC1C,MAAM,MAAM,gBAAgB,GACxB;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,GAAG,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GACzC;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,KAAK,EAAE,MAAM,CAAC;IAAC,aAAa,CAAC,EAAE,OAAO,CAAA;CAAE,CAAC;AAE1D,6CAA6C;AAC7C,MAAM,MAAM,aAAa,GAAG;IAC1B,yDAAyD;IACzD,gBAAgB,EAAE,OAAO,CAAC;IAC1B,sDAAsD;IACtD,QAAQ,EAAE,MAAM,CAAC;IACjB,mCAAmC;IACnC,KAAK,EAAE,MAAM,CAAC;CACf,CAAC;AAEF,kCAAkC;AAClC,MAAM,MAAM,cAAc,GACtB,MAAM,GACN,SAAS,GACT,YAAY,GACZ,QAAQ,GACR,aAAa,GACb,OAAO,GACP,MAAM,GACN,SAAS,GACT,QAAQ,CAAC"}
|
package/package.json
CHANGED
|
@@ -406,6 +406,21 @@ Same storage logic as Jira above.
|
|
|
406
406
|
|
|
407
407
|
---
|
|
408
408
|
|
|
409
|
+
### Q3e (all boards): Max rework cycles
|
|
410
|
+
|
|
411
|
+
PR-based rework detection is automatic — no configuration needed. This setting controls the safety limit.
|
|
412
|
+
|
|
413
|
+
Output:
|
|
414
|
+
|
|
415
|
+
```
|
|
416
|
+
Max rework cycles before flagging for human intervention? [3]
|
|
417
|
+
```
|
|
418
|
+
|
|
419
|
+
If a number is entered: store as `CLANCY_MAX_REWORK` in `.clancy/.env`.
|
|
420
|
+
If enter is pressed with no value: use default 3 — store `CLANCY_MAX_REWORK=3` in `.clancy/.env`.
|
|
421
|
+
|
|
422
|
+
---
|
|
423
|
+
|
|
409
424
|
### Q4: Base branch (auto-detect)
|
|
410
425
|
|
|
411
426
|
Silently detect the base branch — do not ask unless detection fails:
|
|
@@ -396,6 +396,12 @@ MAX_ITERATIONS=5
|
|
|
396
396
|
# CLANCY_GIT_PLATFORM=gitlab # override auto-detection (github/gitlab/bitbucket)
|
|
397
397
|
# CLANCY_GIT_API_URL=https://gitlab.example.com/api/v4 # self-hosted git API base URL
|
|
398
398
|
|
|
399
|
+
# ─── Optional: Rework loop ──────────────────────────────────────────────────
|
|
400
|
+
# PR-based rework is automatic — when a reviewer leaves inline comments or
|
|
401
|
+
# a conversation comment prefixed with "Rework:", Clancy picks it up on the
|
|
402
|
+
# next run. No configuration needed.
|
|
403
|
+
# CLANCY_MAX_REWORK=3 # Max rework cycles before human intervention (default: 3)
|
|
404
|
+
|
|
399
405
|
# ─── Optional: Planner queue ─────────────────────────────────────────────────
|
|
400
406
|
# Status for backlog tickets that /clancy:plan fetches from (default: Backlog)
|
|
401
407
|
# Only used if Planner role is enabled via CLANCY_ROLES
|
|
@@ -457,6 +463,12 @@ MAX_ITERATIONS=20
|
|
|
457
463
|
# PLAYWRIGHT_STORYBOOK_PORT=6006
|
|
458
464
|
# PLAYWRIGHT_STARTUP_WAIT=15
|
|
459
465
|
|
|
466
|
+
# ─── Optional: Rework loop ──────────────────────────────────────────────────
|
|
467
|
+
# PR-based rework is automatic — when a reviewer leaves inline comments or
|
|
468
|
+
# a conversation comment prefixed with "Rework:", Clancy picks it up on the
|
|
469
|
+
# next run. No configuration needed.
|
|
470
|
+
# CLANCY_MAX_REWORK=3 # Max rework cycles before human intervention (default: 3)
|
|
471
|
+
|
|
460
472
|
# ─── Optional: Notifications ──────────────────────────────────────────────────
|
|
461
473
|
# Webhook URL for Slack or Teams notifications on ticket completion
|
|
462
474
|
# CLANCY_NOTIFY_WEBHOOK=https://hooks.slack.com/services/your/webhook/url
|
|
@@ -513,6 +525,12 @@ MAX_ITERATIONS=20
|
|
|
513
525
|
# CLANCY_STATUS_DONE="Done"
|
|
514
526
|
# CLANCY_STATUS_REVIEW="In Review" # used when creating a PR instead of merging locally
|
|
515
527
|
|
|
528
|
+
# ─── Optional: Rework loop ──────────────────────────────────────────────────
|
|
529
|
+
# PR-based rework is automatic — when a reviewer leaves inline comments or
|
|
530
|
+
# a conversation comment prefixed with "Rework:", Clancy picks it up on the
|
|
531
|
+
# next run. No configuration needed.
|
|
532
|
+
# CLANCY_MAX_REWORK=3 # Max rework cycles before human intervention (default: 3)
|
|
533
|
+
|
|
516
534
|
# ─── Optional: Git host (PR creation) ───────────────────────────────────────
|
|
517
535
|
# When an issue has no parent, Clancy pushes the feature branch and creates a
|
|
518
536
|
# pull request instead of squash-merging locally. Requires a git host token.
|
|
@@ -51,6 +51,7 @@ General
|
|
|
51
51
|
[G1] Max iterations {MAX_ITERATIONS:-5} tickets per /clancy:run session
|
|
52
52
|
[G2] Claude model {CLANCY_MODEL:-default} model used for each ticket session
|
|
53
53
|
[G3] Base branch {CLANCY_BASE_BRANCH:-main}
|
|
54
|
+
[G4] Max rework {CLANCY_MAX_REWORK:-3}
|
|
54
55
|
|
|
55
56
|
{If Jira:}
|
|
56
57
|
Jira
|
|
@@ -61,16 +62,12 @@ Jira
|
|
|
61
62
|
[B5] Done status {CLANCY_STATUS_DONE if set, else off}
|
|
62
63
|
[B6] Review status {CLANCY_STATUS_REVIEW if set, else "uses Done status"}
|
|
63
64
|
|
|
64
|
-
{If GitHub:}
|
|
65
|
-
GitHub
|
|
66
|
-
(No board-specific settings — labels are managed in GitHub directly)
|
|
67
|
-
|
|
68
65
|
{If Linear:}
|
|
69
66
|
Linear
|
|
70
67
|
[B1] Label filter {CLANCY_LABEL if set, else off}
|
|
71
68
|
[B2] Pickup status {CLANCY_STATUS_IN_PROGRESS if set, else off}
|
|
72
69
|
[B3] Done status {CLANCY_STATUS_DONE if set, else off}
|
|
73
|
-
[B4] Review status {CLANCY_STATUS_REVIEW if set, else "uses Done
|
|
70
|
+
[B4] Review status {CLANCY_STATUS_REVIEW if set, else "uses Done state"}
|
|
74
71
|
|
|
75
72
|
Roles
|
|
76
73
|
[R1] Planner {✅ enabled / ─ disabled}
|
|
@@ -156,6 +153,24 @@ Write `CLANCY_BASE_BRANCH=<value>` to `.clancy/.env`.
|
|
|
156
153
|
|
|
157
154
|
---
|
|
158
155
|
|
|
156
|
+
### [G4] Max rework cycles
|
|
157
|
+
|
|
158
|
+
```
|
|
159
|
+
Max rework cycles — current: {value or 3}
|
|
160
|
+
After this many rework cycles on a single ticket, Clancy flags it for human intervention.
|
|
161
|
+
|
|
162
|
+
[1] 3 (default)
|
|
163
|
+
[2] Enter a different number
|
|
164
|
+
[3] Cancel
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
Validate the input is a positive integer between 1 and 20. If invalid, re-prompt.
|
|
168
|
+
|
|
169
|
+
If [1]: remove `CLANCY_MAX_REWORK` from `.clancy/.env` (uses default).
|
|
170
|
+
If [2]: prompt `How many rework cycles before human intervention?` then write `CLANCY_MAX_REWORK=<value>` to `.clancy/.env`.
|
|
171
|
+
|
|
172
|
+
---
|
|
173
|
+
|
|
159
174
|
### [B1] Jira status filter (Jira only)
|
|
160
175
|
|
|
161
176
|
```
|