ado-sync 0.1.49 → 0.1.51
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 +44 -110
- package/dist/azure/test-cases.d.ts +6 -0
- package/dist/azure/test-cases.js +24 -0
- package/dist/azure/test-cases.js.map +1 -1
- package/dist/azure/test-runs.d.ts +60 -0
- package/dist/azure/test-runs.js +293 -0
- package/dist/azure/test-runs.js.map +1 -0
- package/dist/azure/work-items.d.ts +26 -0
- package/dist/azure/work-items.js +53 -0
- package/dist/azure/work-items.js.map +1 -1
- package/dist/cli.js +226 -1
- package/dist/cli.js.map +1 -1
- package/dist/sync/publish-results.d.ts +7 -0
- package/dist/sync/publish-results.js +27 -0
- package/dist/sync/publish-results.js.map +1 -1
- package/docs/cli.md +200 -1
- package/docs/publish-test-results.md +69 -0
- package/docs/workflows.md +76 -0
- package/package.json +1 -1
- package/.next-steps.md +0 -179
|
@@ -0,0 +1,293 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Trend analysis over historical ADO test runs.
|
|
4
|
+
*
|
|
5
|
+
* Queries the Azure DevOps Test API for past runs, aggregates pass/fail counts
|
|
6
|
+
* per Test Case, and flags flaky tests (tests that both passed and failed
|
|
7
|
+
* across recent runs).
|
|
8
|
+
*
|
|
9
|
+
* Also supports posting a Markdown summary to a Slack incoming webhook,
|
|
10
|
+
* Microsoft Teams webhook, or a generic HTTP endpoint.
|
|
11
|
+
*/
|
|
12
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
13
|
+
if (k2 === undefined) k2 = k;
|
|
14
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
15
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
16
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
17
|
+
}
|
|
18
|
+
Object.defineProperty(o, k2, desc);
|
|
19
|
+
}) : (function(o, m, k, k2) {
|
|
20
|
+
if (k2 === undefined) k2 = k;
|
|
21
|
+
o[k2] = m[k];
|
|
22
|
+
}));
|
|
23
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
24
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
25
|
+
}) : function(o, v) {
|
|
26
|
+
o["default"] = v;
|
|
27
|
+
});
|
|
28
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
29
|
+
var ownKeys = function(o) {
|
|
30
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
31
|
+
var ar = [];
|
|
32
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
33
|
+
return ar;
|
|
34
|
+
};
|
|
35
|
+
return ownKeys(o);
|
|
36
|
+
};
|
|
37
|
+
return function (mod) {
|
|
38
|
+
if (mod && mod.__esModule) return mod;
|
|
39
|
+
var result = {};
|
|
40
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
41
|
+
__setModuleDefault(result, mod);
|
|
42
|
+
return result;
|
|
43
|
+
};
|
|
44
|
+
})();
|
|
45
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
46
|
+
exports.trendReport = trendReport;
|
|
47
|
+
exports.postTrendToWebhook = postTrendToWebhook;
|
|
48
|
+
exports.buildMarkdownSummary = buildMarkdownSummary;
|
|
49
|
+
const https = __importStar(require("https"));
|
|
50
|
+
const url = __importStar(require("url"));
|
|
51
|
+
const client_1 = require("./client");
|
|
52
|
+
// ─── Main entry point ──────────────────────────────────────────────────────────
|
|
53
|
+
async function trendReport(config, opts = {}) {
|
|
54
|
+
const days = opts.days ?? 30;
|
|
55
|
+
const maxRuns = opts.maxRuns ?? 50;
|
|
56
|
+
const topN = opts.topN ?? 10;
|
|
57
|
+
const toDate = new Date();
|
|
58
|
+
const fromDate = new Date(toDate.getTime() - days * 24 * 60 * 60 * 1000);
|
|
59
|
+
const client = await client_1.AzureClient.create(config);
|
|
60
|
+
const testApi = await client.getTestApi();
|
|
61
|
+
// Fetch runs in the date window — ADO returns newest-first
|
|
62
|
+
const runs = (await testApi.getTestRuns(config.project, undefined, undefined, undefined, undefined, undefined, undefined, fromDate.toISOString(), toDate.toISOString()) ?? []);
|
|
63
|
+
const filtered = runs
|
|
64
|
+
.filter((r) => !opts.runNameFilter || (r.name ?? '').includes(opts.runNameFilter))
|
|
65
|
+
.slice(0, maxRuns);
|
|
66
|
+
// Aggregate per test name
|
|
67
|
+
const byTest = new Map();
|
|
68
|
+
for (const run of filtered) {
|
|
69
|
+
const runId = run.id;
|
|
70
|
+
let skip = 0;
|
|
71
|
+
const PAGE = 1000;
|
|
72
|
+
while (true) {
|
|
73
|
+
const batch = (await testApi.getTestResults(config.project, runId, undefined, skip, PAGE) ?? []);
|
|
74
|
+
if (!batch.length)
|
|
75
|
+
break;
|
|
76
|
+
for (const r of batch) {
|
|
77
|
+
const name = r.testCaseTitle ?? r.automatedTestName ?? 'Unknown';
|
|
78
|
+
if (!byTest.has(name))
|
|
79
|
+
byTest.set(name, { tcId: r.testCase?.id ? parseInt(r.testCase.id, 10) : undefined, passes: 0, fails: 0, outcomes: [] });
|
|
80
|
+
const entry = byTest.get(name);
|
|
81
|
+
const outcome = r.outcome ?? 'NotExecuted';
|
|
82
|
+
entry.outcomes.push(outcome);
|
|
83
|
+
if (outcome === 'Passed')
|
|
84
|
+
entry.passes++;
|
|
85
|
+
else if (outcome === 'Failed')
|
|
86
|
+
entry.fails++;
|
|
87
|
+
}
|
|
88
|
+
if (batch.length < PAGE)
|
|
89
|
+
break;
|
|
90
|
+
skip += PAGE;
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
const allTests = [];
|
|
94
|
+
for (const [name, data] of byTest) {
|
|
95
|
+
const total = data.passes + data.fails + (data.outcomes.length - data.passes - data.fails);
|
|
96
|
+
const passRate = total > 0 ? Math.round((data.passes / total) * 100) : 100;
|
|
97
|
+
const isFlaky = data.passes > 0 && data.fails > 0;
|
|
98
|
+
const lastOutcome = data.outcomes[data.outcomes.length - 1] ?? 'NotExecuted';
|
|
99
|
+
allTests.push({
|
|
100
|
+
testName: name,
|
|
101
|
+
testCaseId: data.tcId,
|
|
102
|
+
totalRuns: total,
|
|
103
|
+
passed: data.passes,
|
|
104
|
+
failed: data.fails,
|
|
105
|
+
passRate,
|
|
106
|
+
isFlaky,
|
|
107
|
+
lastOutcome,
|
|
108
|
+
});
|
|
109
|
+
}
|
|
110
|
+
const flakyTests = allTests.filter((t) => t.isFlaky).sort((a, b) => a.passRate - b.passRate);
|
|
111
|
+
const topFailingTests = [...allTests].sort((a, b) => b.failed - a.failed).filter((t) => t.failed > 0).slice(0, topN);
|
|
112
|
+
const totalResults = allTests.reduce((s, t) => s + t.totalRuns, 0);
|
|
113
|
+
const totalPassed = allTests.reduce((s, t) => s + t.passed, 0);
|
|
114
|
+
const totalFailed = allTests.reduce((s, t) => s + t.failed, 0);
|
|
115
|
+
const overallPassRate = totalResults > 0 ? Math.round((totalPassed / totalResults) * 100) : 100;
|
|
116
|
+
return {
|
|
117
|
+
fromDate: fromDate.toISOString().split('T')[0],
|
|
118
|
+
toDate: toDate.toISOString().split('T')[0],
|
|
119
|
+
runsAnalyzed: filtered.length,
|
|
120
|
+
totalResults,
|
|
121
|
+
totalPassed,
|
|
122
|
+
totalFailed,
|
|
123
|
+
overallPassRate,
|
|
124
|
+
flakyTests,
|
|
125
|
+
topFailingTests,
|
|
126
|
+
allTests,
|
|
127
|
+
};
|
|
128
|
+
}
|
|
129
|
+
async function postTrendToWebhook(report, webhook) {
|
|
130
|
+
let body;
|
|
131
|
+
if (webhook.type === 'slack') {
|
|
132
|
+
body = buildSlackPayload(report);
|
|
133
|
+
}
|
|
134
|
+
else if (webhook.type === 'teams') {
|
|
135
|
+
body = buildTeamsPayload(report);
|
|
136
|
+
}
|
|
137
|
+
else {
|
|
138
|
+
body = JSON.stringify(report);
|
|
139
|
+
}
|
|
140
|
+
await httpPost(webhook.webhookUrl, body);
|
|
141
|
+
}
|
|
142
|
+
// ─── Markdown summary ─────────────────────────────────────────────────────────
|
|
143
|
+
function buildMarkdownSummary(report) {
|
|
144
|
+
const passIcon = report.overallPassRate >= 90 ? '✅' : report.overallPassRate >= 70 ? '⚠️' : '❌';
|
|
145
|
+
const lines = [
|
|
146
|
+
`## ${passIcon} Test Trend Report — ${report.fromDate} → ${report.toDate}`,
|
|
147
|
+
'',
|
|
148
|
+
`| Metric | Value |`,
|
|
149
|
+
`|--------|-------|`,
|
|
150
|
+
`| Runs analysed | ${report.runsAnalyzed} |`,
|
|
151
|
+
`| Total results | ${report.totalResults} |`,
|
|
152
|
+
`| Overall pass rate | **${report.overallPassRate}%** |`,
|
|
153
|
+
`| Total passed | ${report.totalPassed} |`,
|
|
154
|
+
`| Total failed | ${report.totalFailed} |`,
|
|
155
|
+
`| Flaky tests | ${report.flakyTests.length} |`,
|
|
156
|
+
'',
|
|
157
|
+
];
|
|
158
|
+
if (report.flakyTests.length > 0) {
|
|
159
|
+
lines.push('### 🔀 Flaky Tests (passed AND failed in the period)');
|
|
160
|
+
lines.push('');
|
|
161
|
+
lines.push('| Test | Pass rate | Passes | Fails |');
|
|
162
|
+
lines.push('|------|-----------|--------|-------|');
|
|
163
|
+
for (const t of report.flakyTests.slice(0, 15)) {
|
|
164
|
+
const idStr = t.testCaseId ? `[#${t.testCaseId}] ` : '';
|
|
165
|
+
lines.push(`| ${idStr}${t.testName.slice(0, 60)} | ${t.passRate}% | ${t.passed} | ${t.failed} |`);
|
|
166
|
+
}
|
|
167
|
+
if (report.flakyTests.length > 15)
|
|
168
|
+
lines.push(`| _…and ${report.flakyTests.length - 15} more_ | | | |`);
|
|
169
|
+
lines.push('');
|
|
170
|
+
}
|
|
171
|
+
if (report.topFailingTests.length > 0) {
|
|
172
|
+
lines.push('### ❌ Top Failing Tests');
|
|
173
|
+
lines.push('');
|
|
174
|
+
lines.push('| Test | Failures | Pass rate |');
|
|
175
|
+
lines.push('|------|----------|-----------|');
|
|
176
|
+
for (const t of report.topFailingTests) {
|
|
177
|
+
const idStr = t.testCaseId ? `[#${t.testCaseId}] ` : '';
|
|
178
|
+
lines.push(`| ${idStr}${t.testName.slice(0, 60)} | ${t.failed} | ${t.passRate}% |`);
|
|
179
|
+
}
|
|
180
|
+
lines.push('');
|
|
181
|
+
}
|
|
182
|
+
lines.push('---');
|
|
183
|
+
lines.push('_Generated by [ado-sync](https://github.com/PavanMudigonda/ado-sync)_');
|
|
184
|
+
return lines.join('\n');
|
|
185
|
+
}
|
|
186
|
+
// ─── Slack payload ────────────────────────────────────────────────────────────
|
|
187
|
+
function buildSlackPayload(report) {
|
|
188
|
+
const passIcon = report.overallPassRate >= 90 ? ':white_check_mark:' : report.overallPassRate >= 70 ? ':warning:' : ':x:';
|
|
189
|
+
const blocks = [
|
|
190
|
+
{
|
|
191
|
+
type: 'header',
|
|
192
|
+
text: { type: 'plain_text', text: `${passIcon} Test Trend — ${report.fromDate} to ${report.toDate}` },
|
|
193
|
+
},
|
|
194
|
+
{
|
|
195
|
+
type: 'section',
|
|
196
|
+
fields: [
|
|
197
|
+
{ type: 'mrkdwn', text: `*Runs analysed*\n${report.runsAnalyzed}` },
|
|
198
|
+
{ type: 'mrkdwn', text: `*Overall pass rate*\n${report.overallPassRate}%` },
|
|
199
|
+
{ type: 'mrkdwn', text: `*Passed*\n${report.totalPassed}` },
|
|
200
|
+
{ type: 'mrkdwn', text: `*Failed*\n${report.totalFailed}` },
|
|
201
|
+
{ type: 'mrkdwn', text: `*Flaky tests*\n${report.flakyTests.length}` },
|
|
202
|
+
],
|
|
203
|
+
},
|
|
204
|
+
];
|
|
205
|
+
if (report.flakyTests.length > 0) {
|
|
206
|
+
const flakyText = report.flakyTests.slice(0, 5)
|
|
207
|
+
.map((t) => `• ${t.testName.slice(0, 60)} (${t.passRate}% pass rate)`)
|
|
208
|
+
.join('\n');
|
|
209
|
+
blocks.push({
|
|
210
|
+
type: 'section',
|
|
211
|
+
text: { type: 'mrkdwn', text: `*:twisted_rightwards_arrows: Top flaky tests*\n${flakyText}${report.flakyTests.length > 5 ? `\n_…and ${report.flakyTests.length - 5} more_` : ''}` },
|
|
212
|
+
});
|
|
213
|
+
}
|
|
214
|
+
if (report.topFailingTests.length > 0) {
|
|
215
|
+
const failText = report.topFailingTests.slice(0, 5)
|
|
216
|
+
.map((t) => `• ${t.testName.slice(0, 60)} (${t.failed} failures)`)
|
|
217
|
+
.join('\n');
|
|
218
|
+
blocks.push({
|
|
219
|
+
type: 'section',
|
|
220
|
+
text: { type: 'mrkdwn', text: `*:x: Top failing tests*\n${failText}` },
|
|
221
|
+
});
|
|
222
|
+
}
|
|
223
|
+
return JSON.stringify({ blocks });
|
|
224
|
+
}
|
|
225
|
+
// ─── Teams payload ─────────────────────────────────────────────────────────────
|
|
226
|
+
function buildTeamsPayload(report) {
|
|
227
|
+
const passIcon = report.overallPassRate >= 90 ? '✅' : report.overallPassRate >= 70 ? '⚠️' : '❌';
|
|
228
|
+
const card = {
|
|
229
|
+
type: 'message',
|
|
230
|
+
attachments: [{
|
|
231
|
+
contentType: 'application/vnd.microsoft.card.adaptive',
|
|
232
|
+
contentUrl: null,
|
|
233
|
+
content: {
|
|
234
|
+
$schema: 'http://adaptivecards.io/schemas/adaptive-card.json',
|
|
235
|
+
type: 'AdaptiveCard',
|
|
236
|
+
version: '1.4',
|
|
237
|
+
body: [
|
|
238
|
+
{
|
|
239
|
+
type: 'TextBlock',
|
|
240
|
+
size: 'Large',
|
|
241
|
+
weight: 'Bolder',
|
|
242
|
+
text: `${passIcon} Test Trend — ${report.fromDate} to ${report.toDate}`,
|
|
243
|
+
},
|
|
244
|
+
{
|
|
245
|
+
type: 'FactSet',
|
|
246
|
+
facts: [
|
|
247
|
+
{ title: 'Runs analysed', value: String(report.runsAnalyzed) },
|
|
248
|
+
{ title: 'Overall pass rate', value: `${report.overallPassRate}%` },
|
|
249
|
+
{ title: 'Passed', value: String(report.totalPassed) },
|
|
250
|
+
{ title: 'Failed', value: String(report.totalFailed) },
|
|
251
|
+
{ title: 'Flaky tests', value: String(report.flakyTests.length) },
|
|
252
|
+
],
|
|
253
|
+
},
|
|
254
|
+
...(report.topFailingTests.length > 0 ? [{
|
|
255
|
+
type: 'TextBlock',
|
|
256
|
+
text: '**Top Failing Tests**',
|
|
257
|
+
wrap: true,
|
|
258
|
+
}, {
|
|
259
|
+
type: 'TextBlock',
|
|
260
|
+
text: report.topFailingTests.slice(0, 5).map((t) => `- ${t.testName.slice(0, 70)} (${t.failed} failures)`).join('\n'),
|
|
261
|
+
wrap: true,
|
|
262
|
+
}] : []),
|
|
263
|
+
],
|
|
264
|
+
},
|
|
265
|
+
}],
|
|
266
|
+
};
|
|
267
|
+
return JSON.stringify(card);
|
|
268
|
+
}
|
|
269
|
+
// ─── HTTP helper ───────────────────────────────────────────────────────────────
|
|
270
|
+
function httpPost(webhookUrl, body) {
|
|
271
|
+
return new Promise((resolve, reject) => {
|
|
272
|
+
const parsed = new url.URL(webhookUrl);
|
|
273
|
+
const options = {
|
|
274
|
+
hostname: parsed.hostname,
|
|
275
|
+
path: parsed.pathname + parsed.search,
|
|
276
|
+
method: 'POST',
|
|
277
|
+
headers: { 'Content-Type': 'application/json', 'Content-Length': Buffer.byteLength(body) },
|
|
278
|
+
};
|
|
279
|
+
const req = https.request(options, (res) => {
|
|
280
|
+
if ((res.statusCode ?? 200) >= 400) {
|
|
281
|
+
reject(new Error(`Webhook returned HTTP ${res.statusCode}`));
|
|
282
|
+
}
|
|
283
|
+
else {
|
|
284
|
+
res.resume();
|
|
285
|
+
resolve();
|
|
286
|
+
}
|
|
287
|
+
});
|
|
288
|
+
req.on('error', reject);
|
|
289
|
+
req.write(body);
|
|
290
|
+
req.end();
|
|
291
|
+
});
|
|
292
|
+
}
|
|
293
|
+
//# sourceMappingURL=test-runs.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"test-runs.js","sourceRoot":"","sources":["../../src/azure/test-runs.ts"],"names":[],"mappings":"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"}
|
|
@@ -54,6 +54,32 @@ export interface StoryContext {
|
|
|
54
54
|
* Includes related TC IDs (already written), suggested tags, and extracted actors.
|
|
55
55
|
*/
|
|
56
56
|
export declare function getStoryContext(client: AzureClient, project: string, storyId: number, orgUrl: string): Promise<StoryContext>;
|
|
57
|
+
export type AcGateOutcome = 'pass' | 'no-ac' | 'no-tc';
|
|
58
|
+
export interface AcGateResult {
|
|
59
|
+
storyId: number;
|
|
60
|
+
title: string;
|
|
61
|
+
state?: string;
|
|
62
|
+
url: string;
|
|
63
|
+
outcome: AcGateOutcome;
|
|
64
|
+
/** Number of AC items found */
|
|
65
|
+
acCount: number;
|
|
66
|
+
/** Test Case IDs already linked to this story */
|
|
67
|
+
linkedTcs: number[];
|
|
68
|
+
}
|
|
69
|
+
export interface AcGateReport {
|
|
70
|
+
passed: AcGateResult[];
|
|
71
|
+
failed: AcGateResult[];
|
|
72
|
+
/** Exit code: 0 when all pass, 1 when any fail */
|
|
73
|
+
exitCode: 0 | 1;
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Validate that each story in `storyIds` has:
|
|
77
|
+
* - at least one AC item
|
|
78
|
+
* - at least one linked Test Case
|
|
79
|
+
*
|
|
80
|
+
* Returns a report with per-story outcomes and an overall exitCode.
|
|
81
|
+
*/
|
|
82
|
+
export declare function acGate(client: AzureClient, project: string, storyIds: number[], orgUrl: string): Promise<AcGateReport>;
|
|
57
83
|
/**
|
|
58
84
|
* Fetch User Stories under a specific area path.
|
|
59
85
|
*/
|
package/dist/azure/work-items.js
CHANGED
|
@@ -11,6 +11,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
11
11
|
exports.getWorkItemsByIds = getWorkItemsByIds;
|
|
12
12
|
exports.getWorkItemsByQuery = getWorkItemsByQuery;
|
|
13
13
|
exports.getStoryContext = getStoryContext;
|
|
14
|
+
exports.acGate = acGate;
|
|
14
15
|
exports.getWorkItemsByAreaPath = getWorkItemsByAreaPath;
|
|
15
16
|
const FIELDS = [
|
|
16
17
|
'System.Id',
|
|
@@ -180,6 +181,58 @@ function extractActors(ac) {
|
|
|
180
181
|
const actors = [...found];
|
|
181
182
|
return actors.filter((a) => !actors.some((b) => b !== a && b.includes(a)));
|
|
182
183
|
}
|
|
184
|
+
/**
|
|
185
|
+
* Validate that each story in `storyIds` has:
|
|
186
|
+
* - at least one AC item
|
|
187
|
+
* - at least one linked Test Case
|
|
188
|
+
*
|
|
189
|
+
* Returns a report with per-story outcomes and an overall exitCode.
|
|
190
|
+
*/
|
|
191
|
+
async function acGate(client, project, storyIds, orgUrl) {
|
|
192
|
+
const witApi = await client.getWitApi();
|
|
193
|
+
const passed = [];
|
|
194
|
+
const failed = [];
|
|
195
|
+
for (const id of storyIds) {
|
|
196
|
+
// Expand relations (4 = WorkItemExpand.Relations)
|
|
197
|
+
const wi = await witApi.getWorkItem(id, undefined, undefined, 4);
|
|
198
|
+
const f = wi?.fields ?? {};
|
|
199
|
+
const rawAc = f['Microsoft.VSTS.Common.AcceptanceCriteria'];
|
|
200
|
+
const rawTitle = f['System.Title'] ?? `Work Item ${id}`;
|
|
201
|
+
const state = f['System.State'];
|
|
202
|
+
const acText = stripHtml(rawAc) ?? '';
|
|
203
|
+
const acItems = acText
|
|
204
|
+
.split('\n')
|
|
205
|
+
.map((l) => l.replace(/^[-*•\d.)\s]+/, '').trim())
|
|
206
|
+
.filter((l) => l.length > 0);
|
|
207
|
+
const relations = wi?.relations ?? [];
|
|
208
|
+
const linkedTcs = relations
|
|
209
|
+
.filter((r) => typeof r.rel === 'string' && r.rel.includes('TestedBy'))
|
|
210
|
+
.map((r) => {
|
|
211
|
+
const m = (r.url ?? '').match(/\/(\d+)$/);
|
|
212
|
+
return m ? parseInt(m[1], 10) : NaN;
|
|
213
|
+
})
|
|
214
|
+
.filter((tcId) => !isNaN(tcId));
|
|
215
|
+
const url = `${orgUrl.replace(/\/$/, '')}/${project}/_workitems/edit/${id}`;
|
|
216
|
+
let outcome;
|
|
217
|
+
if (acItems.length === 0) {
|
|
218
|
+
outcome = 'no-ac';
|
|
219
|
+
}
|
|
220
|
+
else if (linkedTcs.length === 0) {
|
|
221
|
+
outcome = 'no-tc';
|
|
222
|
+
}
|
|
223
|
+
else {
|
|
224
|
+
outcome = 'pass';
|
|
225
|
+
}
|
|
226
|
+
const result = { storyId: id, title: rawTitle, state, url, outcome, acCount: acItems.length, linkedTcs };
|
|
227
|
+
if (outcome === 'pass') {
|
|
228
|
+
passed.push(result);
|
|
229
|
+
}
|
|
230
|
+
else {
|
|
231
|
+
failed.push(result);
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
return { passed, failed, exitCode: failed.length > 0 ? 1 : 0 };
|
|
235
|
+
}
|
|
183
236
|
/**
|
|
184
237
|
* Fetch User Stories under a specific area path.
|
|
185
238
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"work-items.js","sourceRoot":"","sources":["../../src/azure/work-items.ts"],"names":[],"mappings":";AAAA;;;;;;;GAOG;;AAsEH,8CAkBC;AAOD,kDASC;AA4BD,0CA2DC;
|
|
1
|
+
{"version":3,"file":"work-items.js","sourceRoot":"","sources":["../../src/azure/work-items.ts"],"names":[],"mappings":"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"}
|