@docupace/pipeline 1.0.26-alpha-3 โ 1.0.26
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/.prettierrc.cjs +12 -12
- package/bin/next-changeset-validate.sh +8 -8
- package/next/changeset.sh +75 -75
- package/next/copy.sh +34 -34
- package/next/deploy.sh +40 -40
- package/next/execute.sh +117 -117
- package/next/sonar.sh +23 -23
- package/package.json +2 -1
- package/src/auth0/alias.js +75 -72
- package/src/auth0/cli.js +41 -56
- package/src/auth0/configure.js +482 -258
- package/src/auth0/vault.js +107 -107
- package/src/changeset/cli.js +281 -281
- package/src/changeset/validate.js +47 -47
- package/src/jenkins/setParams.groovy +59 -59
- package/src/next/alias.js +53 -53
- package/src/next/apache.js +40 -40
- package/src/next/cli.js +185 -173
- package/src/next/connect.js +157 -162
- package/src/next/copy.js +52 -30
- package/src/next/deploy.js +218 -43
- package/src/next/jenkins.js +123 -122
- package/src/next/pipline.js +114 -115
- package/src/next/publish.js +48 -48
- package/src/next/pull.js +7 -7
- package/src/next/sonar.js +23 -23
- package/src/next/vault.js +43 -43
- package/terraform/apply.sh +26 -26
- package/terraform/init.sh +48 -60
- package/terraform/plan.sh +54 -61
- package/terraform/validate.sh +17 -17
package/src/next/deploy.js
CHANGED
|
@@ -4,10 +4,9 @@ import yaml from 'js-yaml';
|
|
|
4
4
|
import { $ } from 'zx';
|
|
5
5
|
import lodash from 'lodash';
|
|
6
6
|
import { appInfo, environmentConfig, getRepUrl } from './config.js';
|
|
7
|
-
import {
|
|
7
|
+
import { copy2 } from './copy.js';
|
|
8
8
|
import axios from 'axios';
|
|
9
|
-
import {
|
|
10
|
-
import { deployCore } from './jenkins.js';
|
|
9
|
+
import { deployCore, deployConnect } from './jenkins.js';
|
|
11
10
|
|
|
12
11
|
/**
|
|
13
12
|
* Clone the repository, read the YAML file, and return the parsed data and file paths.
|
|
@@ -22,6 +21,80 @@ function getRepoLocalPath(env) {
|
|
|
22
21
|
return { repoPath, repoName };
|
|
23
22
|
}
|
|
24
23
|
|
|
24
|
+
async function updateAndCommitConnectVersion(
|
|
25
|
+
toEnv,
|
|
26
|
+
toSite,
|
|
27
|
+
getComparedVersion,
|
|
28
|
+
connectDeployPath,
|
|
29
|
+
) {
|
|
30
|
+
const filePath = path.join(
|
|
31
|
+
connectDeployPath,
|
|
32
|
+
'envs',
|
|
33
|
+
toEnv,
|
|
34
|
+
toSite,
|
|
35
|
+
'dock.sh',
|
|
36
|
+
);
|
|
37
|
+
|
|
38
|
+
try {
|
|
39
|
+
let content = fs.readFileSync(filePath, 'utf8');
|
|
40
|
+
content = content.replace(
|
|
41
|
+
/IMAGE_VERSION=.*/,
|
|
42
|
+
`IMAGE_VERSION=git-commit-${getComparedVersion}`,
|
|
43
|
+
);
|
|
44
|
+
fs.writeFileSync(filePath, content, 'utf8');
|
|
45
|
+
|
|
46
|
+
// Git commands to stage, commit and push changes
|
|
47
|
+
await $`cd ${connectDeployPath} && git config user.email "gitops@docupace.com"`;
|
|
48
|
+
await $`cd ${connectDeployPath} && git add .`;
|
|
49
|
+
await $`cd ${connectDeployPath} && git commit -m "Update Connect version for ${toSite} in ${toEnv} to ${getComparedVersion}"`;
|
|
50
|
+
await $`cd ${connectDeployPath} && git push`;
|
|
51
|
+
|
|
52
|
+
console.log('๐งน Cleaning up...');
|
|
53
|
+
await $`rm -rf ${connectDeployPath}`;
|
|
54
|
+
console.log('โ
Cleanup complete.');
|
|
55
|
+
} catch (error) {
|
|
56
|
+
console.error('Error updating Connect version:', error);
|
|
57
|
+
throw error;
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
async function fetchLoginFooter(env, site, isNewUrl) {
|
|
62
|
+
const url = isNewUrl
|
|
63
|
+
? environmentConfig[env].newUrl(site)
|
|
64
|
+
: environmentConfig[env].oldUrl(site);
|
|
65
|
+
const endpoint = isNewUrl ? '/connect/loginFooter' : '_ui/loginFooter';
|
|
66
|
+
return await axios.get(`${url}${endpoint}`);
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
async function compareGetConnectSiteVersions(fromEnv, fromSite, toEnv, toSite) {
|
|
70
|
+
try {
|
|
71
|
+
let fromResponse, toResponse;
|
|
72
|
+
try {
|
|
73
|
+
fromResponse = await fetchLoginFooter(fromEnv, fromSite, true);
|
|
74
|
+
} catch {
|
|
75
|
+
fromResponse = await fetchLoginFooter(fromEnv, fromSite, false);
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
try {
|
|
79
|
+
toResponse = await fetchLoginFooter(toEnv, toSite, true);
|
|
80
|
+
} catch {
|
|
81
|
+
toResponse = await fetchLoginFooter(toEnv, toSite, false);
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
const fromMatch = fromResponse.data.match(/UI Build: ([a-f0-9]*)/);
|
|
85
|
+
const toMatch = toResponse.data.match(/UI Build: ([a-f0-9]*)/);
|
|
86
|
+
|
|
87
|
+
if (fromMatch && fromMatch[1] && toMatch && toMatch[1]) {
|
|
88
|
+
if (fromMatch[1] !== toMatch[1]) {
|
|
89
|
+
return fromMatch[1];
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
return false;
|
|
93
|
+
} catch (error) {
|
|
94
|
+
console.error('Error fetching Connect versions:', error);
|
|
95
|
+
throw error;
|
|
96
|
+
}
|
|
97
|
+
}
|
|
25
98
|
function getRepoLocalPathByRepoSlug(repoSlug) {
|
|
26
99
|
const repoName = `${repoSlug}`;
|
|
27
100
|
const repoPath = path.join(process.cwd(), repoName);
|
|
@@ -34,7 +107,7 @@ function cleanUpRepoPath(repoPath) {
|
|
|
34
107
|
console.log(`${repoPath} directory exists. Removing it...`);
|
|
35
108
|
fs.rmSync(repoPath, {
|
|
36
109
|
recursive: true,
|
|
37
|
-
force: true
|
|
110
|
+
force: true,
|
|
38
111
|
});
|
|
39
112
|
}
|
|
40
113
|
}
|
|
@@ -53,7 +126,7 @@ export async function cloneRepository(repoSlug) {
|
|
|
53
126
|
const { repoPath, repoName } = getRepoLocalPathByRepoSlug(repoSlug);
|
|
54
127
|
const repoUrl = getRepUrl(repoName);
|
|
55
128
|
|
|
56
|
-
await cleanUpRepoPath(repoPath)
|
|
129
|
+
await cleanUpRepoPath(repoPath);
|
|
57
130
|
|
|
58
131
|
console.log(`Cloning repository: ${repoName}`);
|
|
59
132
|
await $`git clone --depth 1 ${repoUrl}`;
|
|
@@ -71,6 +144,23 @@ function getConfigPath(application, env, site, name) {
|
|
|
71
144
|
return { repoPath, deployConfigFilePath };
|
|
72
145
|
}
|
|
73
146
|
|
|
147
|
+
function getAppTypesFromRepo(env, site) {
|
|
148
|
+
const { repoPath } = getRepoLocalPath(env);
|
|
149
|
+
const deployConfigFilePath = path.join(repoPath, `dp/${site}`);
|
|
150
|
+
const applications = [];
|
|
151
|
+
if (fs.existsSync(deployConfigFilePath)) {
|
|
152
|
+
const files = fs.readdirSync(deployConfigFilePath);
|
|
153
|
+
files.forEach((file) => {
|
|
154
|
+
if (file.includes('.values.yaml')) {
|
|
155
|
+
const appName = file.split('.')[0];
|
|
156
|
+
applications.push(appName);
|
|
157
|
+
}
|
|
158
|
+
});
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
return { applications };
|
|
162
|
+
}
|
|
163
|
+
|
|
74
164
|
export async function readDeployConfig(application, env, site, name) {
|
|
75
165
|
const { deployConfigFilePath } = getConfigPath(application, env, site, name);
|
|
76
166
|
|
|
@@ -266,12 +356,72 @@ async function getCoreBranchName(fromEnv, fromSite) {
|
|
|
266
356
|
return branchName;
|
|
267
357
|
}
|
|
268
358
|
|
|
359
|
+
export async function deployApp(
|
|
360
|
+
application,
|
|
361
|
+
appDetails,
|
|
362
|
+
fromEnv,
|
|
363
|
+
fromSite,
|
|
364
|
+
toEnv,
|
|
365
|
+
toSite,
|
|
366
|
+
) {
|
|
367
|
+
let changesMade = false;
|
|
368
|
+
console.log(`Processing application: ${application}`);
|
|
369
|
+
|
|
370
|
+
// Read the deployment configuration for the source environment and site
|
|
371
|
+
const { deployConfig: fromDeployConfig } = await readDeployConfig(
|
|
372
|
+
application,
|
|
373
|
+
fromEnv,
|
|
374
|
+
fromSite,
|
|
375
|
+
'values',
|
|
376
|
+
);
|
|
377
|
+
|
|
378
|
+
if (fromEnv !== toEnv) {
|
|
379
|
+
await copy2(
|
|
380
|
+
appDetails.repositoryName,
|
|
381
|
+
fromEnv,
|
|
382
|
+
toEnv,
|
|
383
|
+
fromDeployConfig.image.tag,
|
|
384
|
+
);
|
|
385
|
+
}
|
|
386
|
+
|
|
387
|
+
// Read the deployment configuration for the target environment and site
|
|
388
|
+
const {
|
|
389
|
+
deployConfig: toDeployConfig,
|
|
390
|
+
deployConfigFilePath: toDeployConfigFilePath,
|
|
391
|
+
} = await readDeployConfig(application, toEnv, toSite, 'values');
|
|
392
|
+
|
|
393
|
+
// Update target configuration using attributes specified in appInfo
|
|
394
|
+
for (const attribute of appDetails.deployAttributes) {
|
|
395
|
+
const sourceValue = lodash.get(fromDeployConfig, attribute);
|
|
396
|
+
|
|
397
|
+
if (sourceValue !== undefined) {
|
|
398
|
+
// Update the target configuration with the source value
|
|
399
|
+
lodash.set(toDeployConfig, attribute, sourceValue);
|
|
400
|
+
changesMade = true;
|
|
401
|
+
}
|
|
402
|
+
}
|
|
403
|
+
|
|
404
|
+
const {
|
|
405
|
+
deployConfig: toDeployAppConfig,
|
|
406
|
+
deployConfigFilePath: toDeployAppConfigFilePath,
|
|
407
|
+
} = await readDeployConfig(application, toEnv, toSite, 'app');
|
|
408
|
+
|
|
409
|
+
toDeployAppConfig.revision = fromDeployConfig.image.tag;
|
|
410
|
+
|
|
411
|
+
// Write updated configuration to the target YAML file
|
|
412
|
+
writeDeployConfig(toDeployConfigFilePath, toDeployConfig);
|
|
413
|
+
|
|
414
|
+
writeDeployConfig(toDeployAppConfigFilePath, toDeployAppConfig);
|
|
415
|
+
return changesMade;
|
|
416
|
+
}
|
|
417
|
+
|
|
269
418
|
export async function deployFromSite(
|
|
270
419
|
fromEnv,
|
|
271
420
|
fromSite,
|
|
272
421
|
toEnv,
|
|
273
422
|
toSite,
|
|
274
423
|
isDeployCore,
|
|
424
|
+
isDeployConnect,
|
|
275
425
|
) {
|
|
276
426
|
if (isDeployCore === 'true') {
|
|
277
427
|
const branchName = await getCoreBranchName(fromEnv, fromSite);
|
|
@@ -288,6 +438,30 @@ export async function deployFromSite(
|
|
|
288
438
|
});*/
|
|
289
439
|
}
|
|
290
440
|
|
|
441
|
+
if (isDeployConnect === 'true') {
|
|
442
|
+
const branch = '';
|
|
443
|
+
const getComparedVersion = await compareGetConnectSiteVersions(
|
|
444
|
+
fromEnv,
|
|
445
|
+
fromSite,
|
|
446
|
+
toEnv,
|
|
447
|
+
toSite,
|
|
448
|
+
);
|
|
449
|
+
if (getComparedVersion) {
|
|
450
|
+
console.log('Version to deploy is: ', getComparedVersion);
|
|
451
|
+
const connectDeployPath = await cloneRepository('connect-deploy');
|
|
452
|
+
// update target version set to git-commit-${getCommparedVersion}}
|
|
453
|
+
await updateAndCommitConnectVersion(
|
|
454
|
+
toEnv,
|
|
455
|
+
toSite,
|
|
456
|
+
getComparedVersion,
|
|
457
|
+
connectDeployPath,
|
|
458
|
+
);
|
|
459
|
+
// save and deploy
|
|
460
|
+
const runLiquibase = true;
|
|
461
|
+
await deployConnect(toEnv, toSite, runLiquibase, branch);
|
|
462
|
+
}
|
|
463
|
+
}
|
|
464
|
+
|
|
291
465
|
// Clone repositories for source and target environments
|
|
292
466
|
const fromRepoPath = await cloneEnvRepository(fromEnv);
|
|
293
467
|
const toRepoPath =
|
|
@@ -295,52 +469,53 @@ export async function deployFromSite(
|
|
|
295
469
|
|
|
296
470
|
// Initialize a flag to track changes
|
|
297
471
|
let changesMade = false;
|
|
298
|
-
|
|
472
|
+
const applications = await getAppTypesFromRepo(toEnv, toSite);
|
|
473
|
+
console.log(applications);
|
|
299
474
|
// Iterate over applications in appInfo
|
|
300
|
-
for (const [application, appDetails] of Object.entries(appInfo)) {
|
|
301
|
-
console.log(`Processing application: ${application}`);
|
|
302
475
|
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
application
|
|
306
|
-
|
|
476
|
+
let appInfoLocal = Object.fromEntries(
|
|
477
|
+
applications.applications
|
|
478
|
+
.filter((application) =>
|
|
479
|
+
Object.prototype.hasOwnProperty.call(appInfo, application),
|
|
480
|
+
)
|
|
481
|
+
.map((application) => [application, appInfo[application]]),
|
|
482
|
+
);
|
|
483
|
+
|
|
484
|
+
// let appInfoLocal = {};
|
|
485
|
+
// for (const application of applications.applications) {
|
|
486
|
+
// if (Object.prototype.hasOwnProperty.call(appInfo, application)) {
|
|
487
|
+
// appInfoLocal[application] = appInfo[application];
|
|
488
|
+
// }
|
|
489
|
+
// }
|
|
490
|
+
|
|
491
|
+
if (Object.keys(appInfoLocal).length === 0) {
|
|
492
|
+
const { deployConfig: toDeployAppConfig } = await readDeployConfig(
|
|
307
493
|
fromSite,
|
|
308
|
-
|
|
494
|
+
toEnv,
|
|
495
|
+
toSite,
|
|
496
|
+
'app',
|
|
309
497
|
);
|
|
310
498
|
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
const {
|
|
317
|
-
deployConfig: toDeployConfig,
|
|
318
|
-
deployConfigFilePath: toDeployConfigFilePath,
|
|
319
|
-
} = await readDeployConfig(application, toEnv, toSite, 'values');
|
|
499
|
+
appInfoLocal[fromSite] = {
|
|
500
|
+
repositoryName: toDeployAppConfig.repo,
|
|
501
|
+
deployAttributes: ['image.tag'],
|
|
502
|
+
};
|
|
503
|
+
}
|
|
320
504
|
|
|
321
|
-
|
|
322
|
-
for (const attribute of appDetails.deployAttributes) {
|
|
323
|
-
const sourceValue = lodash.get(fromDeployConfig, attribute);
|
|
505
|
+
console.log('appinfoLocal', appInfoLocal);
|
|
324
506
|
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
507
|
+
for (const [application, appDetails] of Object.entries(appInfoLocal)) {
|
|
508
|
+
let cm = await deployApp(
|
|
509
|
+
application,
|
|
510
|
+
appDetails,
|
|
511
|
+
fromEnv,
|
|
512
|
+
fromSite,
|
|
513
|
+
toEnv,
|
|
514
|
+
toSite,
|
|
515
|
+
);
|
|
516
|
+
if (cm) {
|
|
517
|
+
changesMade = true;
|
|
330
518
|
}
|
|
331
|
-
|
|
332
|
-
const {
|
|
333
|
-
deployConfig: toDeployAppConfig,
|
|
334
|
-
deployConfigFilePath: toDeployAppConfigFilePath,
|
|
335
|
-
} = await readDeployConfig(application, toEnv, toSite, 'app');
|
|
336
|
-
|
|
337
|
-
toDeployAppConfig.revision = fromDeployConfig.image.tag;
|
|
338
|
-
|
|
339
|
-
// Write updated configuration to the target YAML file
|
|
340
|
-
writeDeployConfig(toDeployConfigFilePath, toDeployConfig);
|
|
341
|
-
|
|
342
|
-
writeDeployConfig(toDeployAppConfigFilePath, toDeployAppConfig);
|
|
343
|
-
|
|
344
519
|
}
|
|
345
520
|
|
|
346
521
|
// Push all changes if any updates were made
|
package/src/next/jenkins.js
CHANGED
|
@@ -1,122 +1,123 @@
|
|
|
1
|
-
import axios from 'axios';
|
|
2
|
-
|
|
3
|
-
const CORE_JENKINS_URL = 'http://devops.corp.docupace.com';
|
|
4
|
-
const CORE_JOB_NAME = 'auto-deploy-site';
|
|
5
|
-
const CORE_USERNAME = process.env.CORE_JENKINS_USERNAME;
|
|
6
|
-
const CORE_API_TOKEN = process.env.CORE_JENKINS_API_TOKEN;
|
|
7
|
-
|
|
8
|
-
const CONNECT_JENKINS_URL = 'http://usdoc-s-buildui.corp.docupace.com/jenkins';
|
|
9
|
-
const CONNECT_JOB_NAME = 'docupace_build_and_run_site_v2';
|
|
10
|
-
const CONNECT_USERNAME = process.env.CONNECT_JENKINS_USERNAME;
|
|
11
|
-
const CONNECT_API_TOKEN = process.env.CONNECT_JENKINS_API_TOKEN;
|
|
12
|
-
|
|
13
|
-
export async function deployCore(env, site, liquibase, gitBranch) {
|
|
14
|
-
const parameters = {
|
|
15
|
-
environment: env,
|
|
16
|
-
site: site.toUpperCase(),
|
|
17
|
-
runLiquibase: liquibase,
|
|
18
|
-
gitBranch,
|
|
19
|
-
};
|
|
20
|
-
|
|
21
|
-
return callJenkinsJob({
|
|
22
|
-
jenkinsUrl: CORE_JENKINS_URL,
|
|
23
|
-
jobName: CORE_JOB_NAME,
|
|
24
|
-
auth: { username: CORE_USERNAME, password: CORE_API_TOKEN },
|
|
25
|
-
parameters,
|
|
26
|
-
});
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
const
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
}
|
|
1
|
+
import axios from 'axios';
|
|
2
|
+
|
|
3
|
+
const CORE_JENKINS_URL = 'http://devops.corp.docupace.com';
|
|
4
|
+
const CORE_JOB_NAME = 'auto-deploy-site';
|
|
5
|
+
const CORE_USERNAME = process.env.CORE_JENKINS_USERNAME;
|
|
6
|
+
const CORE_API_TOKEN = process.env.CORE_JENKINS_API_TOKEN;
|
|
7
|
+
|
|
8
|
+
const CONNECT_JENKINS_URL = 'http://usdoc-s-buildui.corp.docupace.com/jenkins';
|
|
9
|
+
const CONNECT_JOB_NAME = 'docupace_build_and_run_site_v2';
|
|
10
|
+
const CONNECT_USERNAME = process.env.CONNECT_JENKINS_USERNAME;
|
|
11
|
+
const CONNECT_API_TOKEN = process.env.CONNECT_JENKINS_API_TOKEN;
|
|
12
|
+
|
|
13
|
+
export async function deployCore(env, site, liquibase, gitBranch) {
|
|
14
|
+
const parameters = {
|
|
15
|
+
environment: env,
|
|
16
|
+
site: site.toUpperCase(),
|
|
17
|
+
runLiquibase: liquibase,
|
|
18
|
+
gitBranch,
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
return callJenkinsJob({
|
|
22
|
+
jenkinsUrl: CORE_JENKINS_URL,
|
|
23
|
+
jobName: CORE_JOB_NAME,
|
|
24
|
+
auth: { username: CORE_USERNAME, password: CORE_API_TOKEN },
|
|
25
|
+
parameters,
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
// eslint-disable-next-line no-unused-vars
|
|
30
|
+
export async function deployConnect(env, site, liquibase, branch) {
|
|
31
|
+
const parameters = {
|
|
32
|
+
BUILD_ENVIRONMENT: env,
|
|
33
|
+
BUILD_SITE: site,
|
|
34
|
+
RUN_LIQUIBASE: liquibase,
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
return callJenkinsJob({
|
|
38
|
+
jenkinsUrl: CONNECT_JENKINS_URL,
|
|
39
|
+
jobName: CONNECT_JOB_NAME,
|
|
40
|
+
auth: { username: CONNECT_USERNAME, password: CONNECT_API_TOKEN },
|
|
41
|
+
parameters,
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
export async function callJenkinsJob({
|
|
46
|
+
jenkinsUrl,
|
|
47
|
+
jobName,
|
|
48
|
+
auth,
|
|
49
|
+
parameters,
|
|
50
|
+
}) {
|
|
51
|
+
try {
|
|
52
|
+
// Trigger the job
|
|
53
|
+
console.log('Triggering Jenkins job...');
|
|
54
|
+
const buildResponse = await axios.post(
|
|
55
|
+
`${jenkinsUrl}/job/${jobName}/buildWithParameters`,
|
|
56
|
+
new URLSearchParams(parameters),
|
|
57
|
+
{
|
|
58
|
+
auth,
|
|
59
|
+
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
|
|
60
|
+
validateStatus: (status) => status === 201 || status === 302, // Accept 201 and 302 as valid statuses
|
|
61
|
+
},
|
|
62
|
+
);
|
|
63
|
+
|
|
64
|
+
const queueUrl = buildResponse.headers.location;
|
|
65
|
+
console.log(`Job queued at: ${queueUrl}`);
|
|
66
|
+
|
|
67
|
+
// Poll queue for executable URL
|
|
68
|
+
let jobUrl = null;
|
|
69
|
+
while (!jobUrl) {
|
|
70
|
+
const queueResponse = await axios.get(`${queueUrl}api/json`, {
|
|
71
|
+
auth,
|
|
72
|
+
});
|
|
73
|
+
jobUrl = queueResponse.data.executable?.url || null;
|
|
74
|
+
|
|
75
|
+
if (!jobUrl) {
|
|
76
|
+
console.log('Waiting for job to start...');
|
|
77
|
+
await new Promise((resolve) => setTimeout(resolve, 5000));
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
jobUrl = jobUrl.replaceAll('https', 'http');
|
|
82
|
+
|
|
83
|
+
console.log(`Job started at: ${jobUrl}`);
|
|
84
|
+
|
|
85
|
+
// Stream console output
|
|
86
|
+
const consoleUrl = `${jobUrl}consoleText`;
|
|
87
|
+
let lastSize = 0;
|
|
88
|
+
|
|
89
|
+
console.log('Streaming job output...');
|
|
90
|
+
while (true) {
|
|
91
|
+
const consoleResponse = await axios.get(consoleUrl, {
|
|
92
|
+
auth,
|
|
93
|
+
responseType: 'text',
|
|
94
|
+
});
|
|
95
|
+
|
|
96
|
+
const consoleText = consoleResponse.data;
|
|
97
|
+
const newOutput = consoleText.slice(lastSize);
|
|
98
|
+
process.stdout.write(newOutput); // Write new output to console
|
|
99
|
+
lastSize = consoleText.length;
|
|
100
|
+
|
|
101
|
+
// Check job status
|
|
102
|
+
const jobResponse = await axios.get(`${jobUrl}api/json`, {
|
|
103
|
+
auth,
|
|
104
|
+
});
|
|
105
|
+
const result = jobResponse.data.result;
|
|
106
|
+
|
|
107
|
+
if (result) {
|
|
108
|
+
console.log(`\nJob completed with result: ${result}`);
|
|
109
|
+
if (result === 'SUCCESS') {
|
|
110
|
+
return;
|
|
111
|
+
} else {
|
|
112
|
+
throw new Error('Jenkins job failed');
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
// Wait before polling again
|
|
117
|
+
await new Promise((resolve) => setTimeout(resolve, 5000));
|
|
118
|
+
}
|
|
119
|
+
} catch (error) {
|
|
120
|
+
console.error('Error:', error.message);
|
|
121
|
+
throw error;
|
|
122
|
+
}
|
|
123
|
+
}
|