UNPKG

5.52 kBJavaScriptView Raw
1"use strict";
2Object.defineProperty(exports, "__esModule", { value: true });
3const tslib_1 = require("tslib");
4const archiver = require("archiver");
5const axios_1 = require("axios");
6const fs = require("fs-extra");
7const globby = require("globby");
8const Listr = require("listr");
9const base_command_1 = require("../base-command");
10const decorators_1 = require("../utils/decorators");
11const helpers_1 = require("../utils/helpers");
12const locator_1 = require("../utils/locator");
13class Push extends base_command_1.default {
14 async run() {
15 helpers_1.ensureFolderExists(this.locator.buildArtifactDir, true);
16 const archivePath = this.locator.buildArtifactResourcePath('integration.zip');
17 const tasks = [
18 {
19 title: 'Generate bundle',
20 task: async (_ctx) => this.archive(archivePath)
21 },
22 {
23 title: 'Transfer bundle',
24 task: async (_ctx) => this.transfer(archivePath)
25 }
26 ];
27 try {
28 await new Listr(tasks).run();
29 this.success(`🐻 Integration successfully pushed.\n`);
30 this.log(
31 // tslint:disable-next-line:prefer-template
32 `Your Integration will be available shortly here: ` +
33 this.colors.bold(`${this.constants.DeveloperPortalUrl}integrations/${this.bearerConfig.bearerUid}`));
34 this.log(
35 // tslint:disable-next-line:prefer-template
36 `\nIn the meantime you can follow the deployment here: ` +
37 this.colors.bold(`${this.constants.DeveloperPortalUrl}integrations/${this.bearerConfig.bearerUid}/logs`));
38 }
39 catch (e) {
40 this.error(e);
41 }
42 }
43 async archive(archivePath) {
44 return new Promise(async (resolve, reject) => {
45 const output = fs.createWriteStream(archivePath);
46 const archive = archiver('zip', {
47 zlib: { level: 9 } // Sets the compression level.
48 });
49 // pipe archive data to the file
50 archive.pipe(output);
51 const files = await globby([
52 'views/**/*',
53 'functions/**/*.ts',
54 'functions/tsconfig.json',
55 'yarn.lock',
56 'package-json.lock',
57 'spec.ts',
58 'package.json',
59 locator_1.AUTH_CONFIG_FILENAME
60 ]);
61 this.debug('Files to upload', files.join('\n'));
62 if (files.length >= 100) {
63 return reject(new Error('Too many files to bundle. Please re-run this command this DEBUG=*'));
64 }
65 output.on('close', () => {
66 this.debug(`Archive created: ${archive.pointer() / 1024} Kb / ${archivePath}`);
67 resolve(archivePath);
68 });
69 archive.on('error', (err) => {
70 reject(err);
71 });
72 archive.on('warning', (err) => {
73 if (err.code === 'ENOENT') {
74 reject(err);
75 }
76 else {
77 this.debug(err);
78 }
79 });
80 files.map(file => {
81 archive.file(file, { name: file });
82 });
83 archive.finalize();
84 });
85 }
86 async getSignedUrl() {
87 try {
88 const { data } = await this.devPortalClient.request({
89 query: QUERY,
90 variables: { buid: this.bearerConfig.BUID }
91 });
92 if (!(data.data && data.data.integration)) {
93 this.debug('received: %j', data);
94 this.error(new Error(`Integration not found. Please make sure you have correctly linked your integration and visit ${this.constants.DeveloperPortalUrl}integrations/${this.bearerConfig.bearerUid} to confirm you have access to ${this.colors.bold(this.bearerConfig.bearerUid)} integration.`));
95 }
96 return data.data.integration.url;
97 }
98 catch (e) {
99 this.error(e);
100 throw e;
101 }
102 }
103 async transfer(archivePath) {
104 try {
105 const url = await this.getSignedUrl();
106 this.debug(url);
107 const file = fs.readFileSync(archivePath);
108 await axios_1.default.put(url, file, { headers: { 'Content-Type': 'application/zip' } });
109 return true;
110 }
111 catch (e) {
112 if (e.response) {
113 this.debug(e.response);
114 switch (e.response.status) {
115 case 403:
116 case 401: {
117 this.error(`Unauthorized to push. Please visit ${this.constants.DeveloperPortalUrl}integrations/${this.bearerConfig.bearerUid} to confirm you have access to ${this.colors.bold(this.bearerConfig.bearerUid)} integration.`);
118 }
119 default: {
120 this.log(e.response.data);
121 }
122 }
123 }
124 this.error(e);
125 return false;
126 }
127 }
128}
129Push.description = 'deploy integration to Bearer';
130Push.flags = Object.assign({}, base_command_1.default.flags);
131Push.args = [];
132tslib_1.__decorate([
133 decorators_1.RequireIntegrationFolder(),
134 decorators_1.RequireLinkedIntegration()
135], Push.prototype, "run", null);
136exports.default = Push;
137const QUERY = `
138query CLIGetIntegrationUploadUrl($buid: String!) {
139 integration(buid: $buid) {
140 url: archiveUploadUrl
141 }
142}
143`;