@vizzly-testing/cli 0.30.0 → 0.31.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/README.md +9 -9
- package/dist/api/client.js +6 -3
- package/dist/cli.js +58 -29
- package/dist/client/index.js +21 -29
- package/dist/commands/api.js +145 -90
- package/dist/commands/baselines.js +78 -47
- package/dist/commands/builds.js +9 -8
- package/dist/commands/comparisons.js +7 -8
- package/dist/commands/config-cmd.js +15 -7
- package/dist/commands/context.js +329 -18
- package/dist/commands/doctor.js +116 -81
- package/dist/commands/init.js +202 -201
- package/dist/commands/login.js +134 -65
- package/dist/commands/logout.js +17 -6
- package/dist/commands/preview.js +29 -57
- package/dist/commands/project.js +120 -0
- package/dist/commands/projects.js +9 -2
- package/dist/commands/review.js +236 -202
- package/dist/commands/run.js +75 -72
- package/dist/commands/status.js +228 -150
- package/dist/commands/tdd-daemon-process.js +98 -0
- package/dist/commands/tdd-daemon.js +318 -212
- package/dist/commands/tdd.js +23 -8
- package/dist/commands/upload.js +10 -9
- package/dist/commands/whoami.js +63 -25
- package/dist/config/core.js +36 -35
- package/dist/context/local-workspace-provider.js +132 -12
- package/dist/context/provider-resolver.js +5 -1
- package/dist/index.js +5 -4
- package/dist/plugin-loader.js +55 -49
- package/dist/project/core.js +2 -2
- package/dist/project/operations.js +6 -3
- package/dist/reporter/reporter-bundle.css +1 -1
- package/dist/reporter/reporter-bundle.iife.js +7 -7
- package/dist/sdk/index.js +162 -107
- package/dist/server/handlers/tdd-handler.js +30 -54
- package/dist/server/routers/baseline.js +195 -178
- package/dist/server/routers/events.js +212 -174
- package/dist/server/routers/projects.js +14 -5
- package/dist/server/routers/screenshot.js +1 -31
- package/dist/services/build-manager.js +19 -97
- package/dist/services/config-service.js +26 -34
- package/dist/services/index.js +2 -4
- package/dist/services/static-report-generator.js +11 -12
- package/dist/services/test-runner.js +21 -27
- package/dist/tdd/index.js +1 -1
- package/dist/tdd/metadata/region-metadata.js +0 -37
- package/dist/tdd/runtime-context.js +78 -0
- package/dist/tdd/server-registry.js +38 -17
- package/dist/tdd/services/baseline-manager.js +23 -0
- package/dist/tdd/services/hotspot-service.js +0 -13
- package/dist/tdd/tdd-service.js +82 -113
- package/dist/types/client.d.ts +36 -1
- package/dist/types/index.d.ts +114 -22
- package/dist/types/sdk.d.ts +40 -0
- package/dist/uploader/core.js +5 -4
- package/dist/uploader/index.js +79 -2
- package/dist/uploader/operations.js +40 -5
- package/dist/utils/api-url.js +14 -0
- package/dist/utils/async-utils.js +26 -0
- package/dist/utils/ci-env.js +19 -12
- package/dist/utils/config-loader.js +39 -65
- package/dist/utils/config-schema.js +19 -55
- package/dist/utils/fetch-utils.js +12 -5
- package/dist/utils/git.js +35 -72
- package/dist/utils/global-config.js +20 -1
- package/dist/utils/output.js +19 -7
- package/dist/utils/patterns.js +14 -0
- package/dist/utils/project-link-store.js +105 -0
- package/dist/utils/screenshot-options.js +28 -0
- package/dist/utils/secret-store.js +65 -0
- package/package.json +11 -8
- package/dist/services/screenshot-server.js +0 -65
- package/dist/services/server-manager.js +0 -81
- package/dist/services/uploader.js +0 -100
- package/dist/tdd/services/region-service.js +0 -75
- package/dist/utils/build-history.js +0 -103
package/dist/commands/review.js
CHANGED
|
@@ -4,91 +4,199 @@
|
|
|
4
4
|
|
|
5
5
|
import { createApiClient as defaultCreateApiClient } from '../api/index.js';
|
|
6
6
|
import { loadConfig as defaultLoadConfig } from '../utils/config-loader.js';
|
|
7
|
+
import { getAccessToken as defaultGetAccessToken } from '../utils/global-config.js';
|
|
7
8
|
import * as defaultOutput from '../utils/output.js';
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
loadConfig = defaultLoadConfig,
|
|
19
|
-
createApiClient = defaultCreateApiClient,
|
|
20
|
-
output = defaultOutput,
|
|
21
|
-
exit = code => process.exit(code)
|
|
22
|
-
} = deps;
|
|
9
|
+
function createReviewDeps(deps = {}) {
|
|
10
|
+
return {
|
|
11
|
+
loadConfig: deps.loadConfig || defaultLoadConfig,
|
|
12
|
+
createApiClient: deps.createApiClient || defaultCreateApiClient,
|
|
13
|
+
getAccessToken: deps.getAccessToken || defaultGetAccessToken,
|
|
14
|
+
output: deps.output || defaultOutput,
|
|
15
|
+
exit: deps.exit || (code => process.exit(code))
|
|
16
|
+
};
|
|
17
|
+
}
|
|
18
|
+
function configureOutput(output, globalOptions) {
|
|
23
19
|
output.configure({
|
|
24
20
|
json: globalOptions.json,
|
|
25
21
|
verbose: globalOptions.verbose,
|
|
26
22
|
color: !globalOptions.noColor
|
|
27
23
|
});
|
|
24
|
+
}
|
|
25
|
+
async function loadReviewConfig({
|
|
26
|
+
loadConfig,
|
|
27
|
+
options,
|
|
28
|
+
globalOptions
|
|
29
|
+
}) {
|
|
30
|
+
let allOptions = {
|
|
31
|
+
...globalOptions,
|
|
32
|
+
...options
|
|
33
|
+
};
|
|
34
|
+
return await loadConfig(globalOptions.config, allOptions);
|
|
35
|
+
}
|
|
36
|
+
function isProjectToken(token) {
|
|
37
|
+
return typeof token === 'string' && token.startsWith('vzt_');
|
|
38
|
+
}
|
|
39
|
+
async function getReviewToken(config, getAccessToken) {
|
|
40
|
+
if (config.userToken) {
|
|
41
|
+
return config.userToken;
|
|
42
|
+
}
|
|
43
|
+
let userToken = await getAccessToken();
|
|
44
|
+
if (userToken) {
|
|
45
|
+
return userToken;
|
|
46
|
+
}
|
|
47
|
+
if (config.apiKey && !isProjectToken(config.apiKey)) {
|
|
48
|
+
return config.apiKey;
|
|
49
|
+
}
|
|
50
|
+
return null;
|
|
51
|
+
}
|
|
52
|
+
function createReviewClient({
|
|
53
|
+
createApiClient,
|
|
54
|
+
config,
|
|
55
|
+
command,
|
|
56
|
+
token
|
|
57
|
+
}) {
|
|
58
|
+
return createApiClient({
|
|
59
|
+
baseUrl: config.apiUrl,
|
|
60
|
+
token,
|
|
61
|
+
command
|
|
62
|
+
});
|
|
63
|
+
}
|
|
64
|
+
function jsonBody(body) {
|
|
65
|
+
if (!body || Object.keys(body).length === 0) {
|
|
66
|
+
return {};
|
|
67
|
+
}
|
|
68
|
+
return {
|
|
69
|
+
body: JSON.stringify(body),
|
|
70
|
+
headers: {
|
|
71
|
+
'Content-Type': 'application/json'
|
|
72
|
+
}
|
|
73
|
+
};
|
|
74
|
+
}
|
|
75
|
+
async function runReviewMutation({
|
|
76
|
+
command,
|
|
77
|
+
endpoint,
|
|
78
|
+
failureMessage,
|
|
79
|
+
globalOptions,
|
|
80
|
+
options,
|
|
81
|
+
requestBody,
|
|
82
|
+
spinnerMessage,
|
|
83
|
+
writeJsonError,
|
|
84
|
+
writeJsonSuccess,
|
|
85
|
+
writeHumanSuccess,
|
|
86
|
+
deps,
|
|
87
|
+
configure = true
|
|
88
|
+
}) {
|
|
89
|
+
let {
|
|
90
|
+
loadConfig,
|
|
91
|
+
createApiClient,
|
|
92
|
+
getAccessToken,
|
|
93
|
+
output,
|
|
94
|
+
exit
|
|
95
|
+
} = createReviewDeps(deps);
|
|
96
|
+
if (configure) {
|
|
97
|
+
configureOutput(output, globalOptions);
|
|
98
|
+
}
|
|
28
99
|
try {
|
|
29
|
-
let
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
output.
|
|
100
|
+
let config = await loadReviewConfig({
|
|
101
|
+
loadConfig,
|
|
102
|
+
options,
|
|
103
|
+
globalOptions
|
|
104
|
+
});
|
|
105
|
+
let token = await getReviewToken(config, getAccessToken);
|
|
106
|
+
if (!token) {
|
|
107
|
+
output.error('User login required for review actions');
|
|
108
|
+
output.hint('Run "vizzly login" to approve, reject, or comment');
|
|
109
|
+
output.cleanup();
|
|
37
110
|
exit(1);
|
|
38
111
|
return;
|
|
39
112
|
}
|
|
40
|
-
output.startSpinner(
|
|
41
|
-
let client =
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
command
|
|
113
|
+
output.startSpinner(spinnerMessage);
|
|
114
|
+
let client = createReviewClient({
|
|
115
|
+
createApiClient,
|
|
116
|
+
config,
|
|
117
|
+
command,
|
|
118
|
+
token
|
|
45
119
|
});
|
|
46
|
-
let
|
|
47
|
-
if (options.comment) {
|
|
48
|
-
body.comment = options.comment;
|
|
49
|
-
}
|
|
50
|
-
let response = await client.request(`/api/sdk/comparisons/${comparisonId}/approve`, {
|
|
120
|
+
let response = await client.request(endpoint, {
|
|
51
121
|
method: 'POST',
|
|
52
|
-
|
|
53
|
-
headers: Object.keys(body).length > 0 ? {
|
|
54
|
-
'Content-Type': 'application/json'
|
|
55
|
-
} : undefined
|
|
122
|
+
...jsonBody(requestBody)
|
|
56
123
|
});
|
|
57
124
|
output.stopSpinner();
|
|
58
125
|
if (globalOptions.json) {
|
|
59
|
-
output
|
|
60
|
-
approved: true,
|
|
61
|
-
comparisonId,
|
|
62
|
-
comparison: response.comparison
|
|
63
|
-
});
|
|
126
|
+
writeJsonSuccess(output, response);
|
|
64
127
|
output.cleanup();
|
|
65
128
|
return;
|
|
66
129
|
}
|
|
67
|
-
output
|
|
68
|
-
if (options.comment) {
|
|
69
|
-
output.hint(`Comment: "${options.comment}"`);
|
|
70
|
-
}
|
|
130
|
+
writeHumanSuccess(output, response);
|
|
71
131
|
output.cleanup();
|
|
72
132
|
} catch (error) {
|
|
73
133
|
output.stopSpinner();
|
|
74
134
|
if (globalOptions.json) {
|
|
75
|
-
output
|
|
76
|
-
approved: false,
|
|
77
|
-
comparisonId,
|
|
78
|
-
error: {
|
|
79
|
-
message: error.message,
|
|
80
|
-
code: error.code
|
|
81
|
-
}
|
|
82
|
-
});
|
|
135
|
+
writeJsonError(output, error);
|
|
83
136
|
output.cleanup();
|
|
84
137
|
exit(1);
|
|
85
138
|
return;
|
|
86
139
|
}
|
|
87
|
-
output.error(
|
|
140
|
+
output.error(failureMessage, error);
|
|
88
141
|
output.cleanup();
|
|
89
142
|
exit(1);
|
|
90
143
|
}
|
|
91
144
|
}
|
|
145
|
+
export function createApprovalBody(options = {}) {
|
|
146
|
+
return options.comment ? {
|
|
147
|
+
comment: options.comment
|
|
148
|
+
} : {};
|
|
149
|
+
}
|
|
150
|
+
export function createRejectionBody(options = {}) {
|
|
151
|
+
return {
|
|
152
|
+
reason: options.reason
|
|
153
|
+
};
|
|
154
|
+
}
|
|
155
|
+
export function createCommentBody(message, options = {}) {
|
|
156
|
+
return {
|
|
157
|
+
content: message,
|
|
158
|
+
type: options.type || 'general'
|
|
159
|
+
};
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
/**
|
|
163
|
+
* Approve a comparison
|
|
164
|
+
* @param {string} comparisonId - Comparison ID to approve
|
|
165
|
+
* @param {Object} options - Command options
|
|
166
|
+
* @param {Object} globalOptions - Global CLI options
|
|
167
|
+
* @param {Object} deps - Dependencies for testing
|
|
168
|
+
*/
|
|
169
|
+
export async function approveCommand(comparisonId, options = {}, globalOptions = {}, deps = {}) {
|
|
170
|
+
return await runReviewMutation({
|
|
171
|
+
command: 'approve',
|
|
172
|
+
endpoint: `/api/sdk/comparisons/${comparisonId}/approve`,
|
|
173
|
+
failureMessage: 'Failed to approve comparison',
|
|
174
|
+
globalOptions,
|
|
175
|
+
options,
|
|
176
|
+
requestBody: createApprovalBody(options),
|
|
177
|
+
spinnerMessage: 'Approving comparison...',
|
|
178
|
+
writeJsonError: (output, error) => output.data({
|
|
179
|
+
approved: false,
|
|
180
|
+
comparisonId,
|
|
181
|
+
error: {
|
|
182
|
+
message: error.message,
|
|
183
|
+
code: error.code
|
|
184
|
+
}
|
|
185
|
+
}),
|
|
186
|
+
writeJsonSuccess: (output, response) => output.data({
|
|
187
|
+
approved: true,
|
|
188
|
+
comparisonId,
|
|
189
|
+
comparison: response.comparison
|
|
190
|
+
}),
|
|
191
|
+
writeHumanSuccess: output => {
|
|
192
|
+
output.complete(`Comparison ${comparisonId} approved`);
|
|
193
|
+
if (options.comment) {
|
|
194
|
+
output.hint(`Comment: "${options.comment}"`);
|
|
195
|
+
}
|
|
196
|
+
},
|
|
197
|
+
deps
|
|
198
|
+
});
|
|
199
|
+
}
|
|
92
200
|
|
|
93
201
|
/**
|
|
94
202
|
* Reject a comparison
|
|
@@ -99,82 +207,46 @@ export async function approveCommand(comparisonId, options = {}, globalOptions =
|
|
|
99
207
|
*/
|
|
100
208
|
export async function rejectCommand(comparisonId, options = {}, globalOptions = {}, deps = {}) {
|
|
101
209
|
let {
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
verbose: globalOptions.verbose,
|
|
110
|
-
color: !globalOptions.noColor
|
|
111
|
-
});
|
|
112
|
-
try {
|
|
113
|
-
let allOptions = {
|
|
114
|
-
...globalOptions,
|
|
115
|
-
...options
|
|
116
|
-
};
|
|
117
|
-
let config = await loadConfig(globalOptions.config, allOptions);
|
|
118
|
-
if (!config.apiKey) {
|
|
119
|
-
output.error('API token required');
|
|
120
|
-
output.hint('Use --token or set VIZZLY_TOKEN environment variable');
|
|
121
|
-
exit(1);
|
|
122
|
-
return;
|
|
123
|
-
}
|
|
124
|
-
if (!options.reason) {
|
|
125
|
-
output.error('Reason required when rejecting');
|
|
126
|
-
output.hint('Use --reason "explanation" to provide a reason');
|
|
127
|
-
exit(1);
|
|
128
|
-
return;
|
|
129
|
-
}
|
|
130
|
-
output.startSpinner('Rejecting comparison...');
|
|
131
|
-
let client = createApiClient({
|
|
132
|
-
baseUrl: config.apiUrl,
|
|
133
|
-
token: config.apiKey,
|
|
134
|
-
command: 'reject'
|
|
135
|
-
});
|
|
136
|
-
let response = await client.request(`/api/sdk/comparisons/${comparisonId}/reject`, {
|
|
137
|
-
method: 'POST',
|
|
138
|
-
body: JSON.stringify({
|
|
139
|
-
reason: options.reason
|
|
140
|
-
}),
|
|
141
|
-
headers: {
|
|
142
|
-
'Content-Type': 'application/json'
|
|
143
|
-
}
|
|
144
|
-
});
|
|
145
|
-
output.stopSpinner();
|
|
146
|
-
if (globalOptions.json) {
|
|
147
|
-
output.data({
|
|
148
|
-
rejected: true,
|
|
149
|
-
comparisonId,
|
|
150
|
-
reason: options.reason,
|
|
151
|
-
comparison: response.comparison
|
|
152
|
-
});
|
|
153
|
-
output.cleanup();
|
|
154
|
-
return;
|
|
155
|
-
}
|
|
156
|
-
output.complete(`Comparison ${comparisonId} rejected`);
|
|
157
|
-
output.hint(`Reason: "${options.reason}"`);
|
|
158
|
-
output.cleanup();
|
|
159
|
-
} catch (error) {
|
|
160
|
-
output.stopSpinner();
|
|
161
|
-
if (globalOptions.json) {
|
|
162
|
-
output.data({
|
|
163
|
-
rejected: false,
|
|
164
|
-
comparisonId,
|
|
165
|
-
error: {
|
|
166
|
-
message: error.message,
|
|
167
|
-
code: error.code
|
|
168
|
-
}
|
|
169
|
-
});
|
|
170
|
-
output.cleanup();
|
|
171
|
-
exit(1);
|
|
172
|
-
return;
|
|
173
|
-
}
|
|
174
|
-
output.error('Failed to reject comparison', error);
|
|
210
|
+
output,
|
|
211
|
+
exit
|
|
212
|
+
} = createReviewDeps(deps);
|
|
213
|
+
configureOutput(output, globalOptions);
|
|
214
|
+
if (!options.reason) {
|
|
215
|
+
output.error('Reason required when rejecting');
|
|
216
|
+
output.hint('Use --reason "explanation" to provide a reason');
|
|
175
217
|
output.cleanup();
|
|
176
218
|
exit(1);
|
|
219
|
+
return;
|
|
177
220
|
}
|
|
221
|
+
return await runReviewMutation({
|
|
222
|
+
command: 'reject',
|
|
223
|
+
endpoint: `/api/sdk/comparisons/${comparisonId}/reject`,
|
|
224
|
+
failureMessage: 'Failed to reject comparison',
|
|
225
|
+
globalOptions,
|
|
226
|
+
options,
|
|
227
|
+
requestBody: createRejectionBody(options),
|
|
228
|
+
spinnerMessage: 'Rejecting comparison...',
|
|
229
|
+
writeJsonError: (output, error) => output.data({
|
|
230
|
+
rejected: false,
|
|
231
|
+
comparisonId,
|
|
232
|
+
error: {
|
|
233
|
+
message: error.message,
|
|
234
|
+
code: error.code
|
|
235
|
+
}
|
|
236
|
+
}),
|
|
237
|
+
writeJsonSuccess: (output, response) => output.data({
|
|
238
|
+
rejected: true,
|
|
239
|
+
comparisonId,
|
|
240
|
+
reason: options.reason,
|
|
241
|
+
comparison: response.comparison
|
|
242
|
+
}),
|
|
243
|
+
writeHumanSuccess: output => {
|
|
244
|
+
output.complete(`Comparison ${comparisonId} rejected`);
|
|
245
|
+
output.hint(`Reason: "${options.reason}"`);
|
|
246
|
+
},
|
|
247
|
+
deps,
|
|
248
|
+
configure: false
|
|
249
|
+
});
|
|
178
250
|
}
|
|
179
251
|
|
|
180
252
|
/**
|
|
@@ -187,83 +259,45 @@ export async function rejectCommand(comparisonId, options = {}, globalOptions =
|
|
|
187
259
|
*/
|
|
188
260
|
export async function commentCommand(buildId, message, options = {}, globalOptions = {}, deps = {}) {
|
|
189
261
|
let {
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
json: globalOptions.json,
|
|
197
|
-
verbose: globalOptions.verbose,
|
|
198
|
-
color: !globalOptions.noColor
|
|
199
|
-
});
|
|
200
|
-
try {
|
|
201
|
-
let allOptions = {
|
|
202
|
-
...globalOptions,
|
|
203
|
-
...options
|
|
204
|
-
};
|
|
205
|
-
let config = await loadConfig(globalOptions.config, allOptions);
|
|
206
|
-
if (!config.apiKey) {
|
|
207
|
-
output.error('API token required');
|
|
208
|
-
output.hint('Use --token or set VIZZLY_TOKEN environment variable');
|
|
209
|
-
exit(1);
|
|
210
|
-
return;
|
|
211
|
-
}
|
|
212
|
-
if (!message || message.trim() === '') {
|
|
213
|
-
output.error('Comment message required');
|
|
214
|
-
exit(1);
|
|
215
|
-
return;
|
|
216
|
-
}
|
|
217
|
-
output.startSpinner('Adding comment...');
|
|
218
|
-
let client = createApiClient({
|
|
219
|
-
baseUrl: config.apiUrl,
|
|
220
|
-
token: config.apiKey,
|
|
221
|
-
command: 'comment'
|
|
222
|
-
});
|
|
223
|
-
let body = {
|
|
224
|
-
content: message,
|
|
225
|
-
type: options.type || 'general'
|
|
226
|
-
};
|
|
227
|
-
let response = await client.request(`/api/sdk/builds/${buildId}/comments`, {
|
|
228
|
-
method: 'POST',
|
|
229
|
-
body: JSON.stringify(body),
|
|
230
|
-
headers: {
|
|
231
|
-
'Content-Type': 'application/json'
|
|
232
|
-
}
|
|
233
|
-
});
|
|
234
|
-
output.stopSpinner();
|
|
235
|
-
if (globalOptions.json) {
|
|
236
|
-
output.data({
|
|
237
|
-
created: true,
|
|
238
|
-
buildId,
|
|
239
|
-
comment: response.comment
|
|
240
|
-
});
|
|
241
|
-
output.cleanup();
|
|
242
|
-
return;
|
|
243
|
-
}
|
|
244
|
-
output.complete('Comment added');
|
|
245
|
-
output.labelValue('Build', buildId);
|
|
246
|
-
output.labelValue('Message', message);
|
|
247
|
-
output.cleanup();
|
|
248
|
-
} catch (error) {
|
|
249
|
-
output.stopSpinner();
|
|
250
|
-
if (globalOptions.json) {
|
|
251
|
-
output.data({
|
|
252
|
-
created: false,
|
|
253
|
-
buildId,
|
|
254
|
-
error: {
|
|
255
|
-
message: error.message,
|
|
256
|
-
code: error.code
|
|
257
|
-
}
|
|
258
|
-
});
|
|
259
|
-
output.cleanup();
|
|
260
|
-
exit(1);
|
|
261
|
-
return;
|
|
262
|
-
}
|
|
263
|
-
output.error('Failed to add comment', error);
|
|
262
|
+
output,
|
|
263
|
+
exit
|
|
264
|
+
} = createReviewDeps(deps);
|
|
265
|
+
configureOutput(output, globalOptions);
|
|
266
|
+
if (!message || message.trim() === '') {
|
|
267
|
+
output.error('Comment message required');
|
|
264
268
|
output.cleanup();
|
|
265
269
|
exit(1);
|
|
270
|
+
return;
|
|
266
271
|
}
|
|
272
|
+
return await runReviewMutation({
|
|
273
|
+
command: 'comment',
|
|
274
|
+
endpoint: `/api/sdk/builds/${buildId}/comments`,
|
|
275
|
+
failureMessage: 'Failed to add comment',
|
|
276
|
+
globalOptions,
|
|
277
|
+
options,
|
|
278
|
+
requestBody: createCommentBody(message, options),
|
|
279
|
+
spinnerMessage: 'Adding comment...',
|
|
280
|
+
writeJsonError: (output, error) => output.data({
|
|
281
|
+
created: false,
|
|
282
|
+
buildId,
|
|
283
|
+
error: {
|
|
284
|
+
message: error.message,
|
|
285
|
+
code: error.code
|
|
286
|
+
}
|
|
287
|
+
}),
|
|
288
|
+
writeJsonSuccess: (output, response) => output.data({
|
|
289
|
+
created: true,
|
|
290
|
+
buildId,
|
|
291
|
+
comment: response.comment
|
|
292
|
+
}),
|
|
293
|
+
writeHumanSuccess: output => {
|
|
294
|
+
output.complete('Comment added');
|
|
295
|
+
output.labelValue('Build', buildId);
|
|
296
|
+
output.labelValue('Message', message);
|
|
297
|
+
},
|
|
298
|
+
deps,
|
|
299
|
+
configure: false
|
|
300
|
+
});
|
|
267
301
|
}
|
|
268
302
|
|
|
269
303
|
/**
|