build-strap 4.0.0-dev.46 → 4.0.0-dev.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.
Files changed (107) hide show
  1. package/README.md +3 -34
  2. package/ant.d.ts +19 -0
  3. package/ant.js +12 -37
  4. package/cert.d.ts +12 -0
  5. package/cert.js +89 -151
  6. package/clean.d.ts +4 -0
  7. package/clean.js +7 -16
  8. package/copy.d.ts +7 -0
  9. package/copy.js +49 -76
  10. package/cp.d.ts +17 -0
  11. package/cp.js +85 -170
  12. package/docker.container.d.ts +73 -0
  13. package/docker.container.js +219 -362
  14. package/docker.d.ts +68 -0
  15. package/docker.js +167 -344
  16. package/docker.network.d.ts +42 -0
  17. package/docker.network.js +69 -144
  18. package/docker.volume.d.ts +26 -0
  19. package/docker.volume.js +52 -126
  20. package/dockerCleanup.d.ts +38 -0
  21. package/dockerCleanup.js +66 -141
  22. package/dockerCompose.d.ts +154 -0
  23. package/dockerCompose.js +400 -727
  24. package/fs.d.ts +5 -0
  25. package/fs.js +38 -95
  26. package/git.d.ts +9 -0
  27. package/git.js +19 -30
  28. package/index.d.ts +20 -0
  29. package/index.js +20 -27
  30. package/maps.d.ts +33 -0
  31. package/maps.js +16 -87
  32. package/npm.d.ts +48 -0
  33. package/npm.js +131 -135
  34. package/package.json +23 -19
  35. package/pkg.d.ts +39 -0
  36. package/pkg.js +26 -74
  37. package/publish.d.ts +27 -0
  38. package/publish.js +52 -140
  39. package/run.d.ts +13 -0
  40. package/run.js +39 -85
  41. package/tgz.d.ts +13 -0
  42. package/tgz.js +61 -96
  43. package/version.d.ts +34 -0
  44. package/version.js +86 -128
  45. package/yarn.d.ts +44 -0
  46. package/yarn.js +150 -119
  47. package/ant.js.flow +0 -42
  48. package/artifactory.js +0 -617
  49. package/artifactory.js.flow +0 -616
  50. package/cert.conf +0 -20
  51. package/cert.js.flow +0 -152
  52. package/clean.js.flow +0 -19
  53. package/copy.js.flow +0 -79
  54. package/cp.js.flow +0 -172
  55. package/docker.container.js.flow +0 -389
  56. package/docker.js.flow +0 -364
  57. package/docker.network.js.flow +0 -159
  58. package/docker.volume.js.flow +0 -136
  59. package/dockerCleanup.js.flow +0 -151
  60. package/dockerCompose.js.flow +0 -765
  61. package/flow.js +0 -21
  62. package/flow.js.flow +0 -20
  63. package/fs.js.flow +0 -96
  64. package/git.js.flow +0 -34
  65. package/hg.js +0 -35
  66. package/hg.js.flow +0 -34
  67. package/index.js.flow +0 -26
  68. package/inline-resources.js +0 -158
  69. package/inline-resources.js.flow +0 -157
  70. package/maps.js.flow +0 -111
  71. package/npm.js.flow +0 -144
  72. package/pkg.js.flow +0 -80
  73. package/publish.js.flow +0 -144
  74. package/run.js.flow +0 -89
  75. package/src/ant.js +0 -42
  76. package/src/artifactory.js +0 -616
  77. package/src/cert.conf +0 -20
  78. package/src/cert.js +0 -152
  79. package/src/clean.js +0 -19
  80. package/src/copy.js +0 -79
  81. package/src/cp.js +0 -172
  82. package/src/docker.container.js +0 -389
  83. package/src/docker.js +0 -364
  84. package/src/docker.network.js +0 -159
  85. package/src/docker.volume.js +0 -136
  86. package/src/dockerCleanup.js +0 -151
  87. package/src/dockerCompose.js +0 -765
  88. package/src/flow.js +0 -20
  89. package/src/fs.js +0 -96
  90. package/src/git.js +0 -34
  91. package/src/hg.js +0 -34
  92. package/src/index.js +0 -26
  93. package/src/inline-resources.js +0 -157
  94. package/src/maps.js +0 -111
  95. package/src/npm.js +0 -144
  96. package/src/pkg.js +0 -80
  97. package/src/publish.js +0 -144
  98. package/src/run.js +0 -89
  99. package/src/test.js +0 -55
  100. package/src/tgz.js +0 -101
  101. package/src/version.js +0 -142
  102. package/src/yarn.js +0 -123
  103. package/test.js +0 -56
  104. package/test.js.flow +0 -55
  105. package/tgz.js.flow +0 -101
  106. package/version.js.flow +0 -142
  107. package/yarn.js.flow +0 -123
package/dockerCompose.js CHANGED
@@ -1,766 +1,439 @@
1
- "use strict";Object.defineProperty(exports, "__esModule", { value: true });exports.dockerComposeCreateVolumes = exports.dockerComposeCreateResourceTracker = exports.dockerComposeCreateNetworks = exports.DockerComposeService = void 0;exports.dockerComposeGetAllServices = dockerComposeGetAllServices;exports.dockerComposeParse = exports.dockerComposeGetMain = void 0;exports.dockerComposeRunService = dockerComposeRunService;exports.dockerComposeTeardown = dockerComposeTeardown;
2
- var _fsExtra = _interopRequireDefault(require("fs-extra"));
3
- var _jsYaml = _interopRequireDefault(require("js-yaml"));
4
- var _path = _interopRequireDefault(require("path"));
5
- var _getPort = _interopRequireDefault(require("get-port"));
6
- var _maps = require("./maps");
7
-
8
- var _run = require("./run");
9
- var _docker = require("./docker");
10
- var _docker2 = require("./docker.container");
11
-
12
-
13
-
14
-
15
- var _docker3 = require("./docker.network");
16
-
17
-
18
-
19
-
20
-
21
- var _docker4 = require("./docker.volume");function _interopRequireDefault(obj) {return obj && obj.__esModule ? obj : { default: obj };}function _classPrivateFieldInitSpec(obj, privateMap, value) {_checkPrivateRedeclaration(obj, privateMap);privateMap.set(obj, value);}function _checkPrivateRedeclaration(obj, privateCollection) {if (privateCollection.has(obj)) {throw new TypeError("Cannot initialize the same private elements twice on an object");}}function _classPrivateFieldGet(receiver, privateMap) {var descriptor = _classExtractFieldDescriptor(receiver, privateMap, "get");return _classApplyDescriptorGet(receiver, descriptor);}function _classApplyDescriptorGet(receiver, descriptor) {if (descriptor.get) {return descriptor.get.call(receiver);}return descriptor.value;}function _classPrivateFieldSet(receiver, privateMap, value) {var descriptor = _classExtractFieldDescriptor(receiver, privateMap, "set");_classApplyDescriptorSet(receiver, descriptor, value);return value;}function _classExtractFieldDescriptor(receiver, privateMap, action) {if (!privateMap.has(receiver)) {throw new TypeError("attempted to " + action + " private field on non-instance");}return privateMap.get(receiver);}function _classApplyDescriptorSet(receiver, descriptor, value) {if (descriptor.set) {descriptor.set.call(receiver, value);} else {if (!descriptor.writable) {throw new TypeError("attempted to set read only private field");}descriptor.value = value;}}
22
-
23
-
24
-
25
-
26
-
27
-
28
-
29
-
30
-
31
-
32
-
33
-
34
-
35
- const dockerComposeCreateResourceTracker = () => ({
36
- networks: new Map(),
37
- services: new Map(),
38
- containers: new Map(),
39
- volumes: new Map(),
40
- cleaning: null });exports.dockerComposeCreateResourceTracker = dockerComposeCreateResourceTracker;
41
-
42
-
1
+ var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
2
+ if (kind === "m") throw new TypeError("Private method is not writable");
3
+ if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
4
+ if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
5
+ return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
6
+ };
7
+ var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
8
+ if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
9
+ if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
10
+ return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
11
+ };
12
+ var _DockerComposeService_name, _DockerComposeService_svcDef, _DockerComposeService_dockerCompose, _DockerComposeService_tracker, _DockerComposeService_parsedPorts, _DockerComposeService_parsedNetworks, _DockerComposeService_parsedVolumes, _DockerComposeService_baseRunArgs;
13
+ import fs from 'fs-extra';
14
+ import getPort from 'get-port';
15
+ import yaml from 'js-yaml';
16
+ import path from 'path';
17
+ import { dockerContainerFind, dockerContainerRunDaemon, } from './docker.container.js';
18
+ import { dockerPull } from './docker.js';
19
+ import { dockerNetworkCreate, dockerNetworkDelete, } from './docker.network.js';
20
+ import { dockerVolumeCreate, dockerVolumeRm, } from './docker.volume.js';
21
+ import { mapValuesAsync } from './maps.js';
22
+ import { buildLog } from './run.js';
23
+ export const dockerComposeCreateResourceTracker = () => ({
24
+ cleaning: null,
25
+ containers: new Map(),
26
+ networks: new Map(),
27
+ services: new Map(),
28
+ volumes: new Map(),
29
+ });
43
30
  const defaultTracker = dockerComposeCreateResourceTracker();
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
31
  /**
88
32
  * Parse a docker-compose.yml file into a pojo representation
89
33
  * @param {string} filePath Path to the docker-compose.yml file
90
34
  */
91
- const dockerComposeParse = async (
92
- filePath = './docker-compose.yml') =>
93
- _jsYaml.default.load(await _fsExtra.default.readFile(filePath));exports.dockerComposeParse = dockerComposeParse;
94
-
35
+ export const dockerComposeParse = async (filePath = './docker-compose.yml') => yaml.load(await fs.readFile(filePath, 'utf8'));
95
36
  let dc = null;
96
-
97
37
  /**
98
38
  * Get the main docker-compose.yml from the root of the repo
99
39
  * @param {boolean} force Force reload from file
100
40
  */
101
- const dockerComposeGetMain = async (
102
- force = false) =>
103
- {
104
- if (force || !dc) {
105
- dc = await dockerComposeParse();
106
- }
107
- return dc;
41
+ export const dockerComposeGetMain = async (force = false) => {
42
+ if (force || !dc) {
43
+ dc = await dockerComposeParse();
44
+ }
45
+ return dc;
108
46
  };
109
-
110
47
  // Function that handles passed dockerCompose as either a file path or `DockerCompose` object.
111
48
  // If not passed, defaults to the main docker-compose.yml from the root of the repo
112
- exports.dockerComposeGetMain = dockerComposeGetMain;const dockerComposeResolve = async (
113
- dockerCompose,
114
- force) =>
115
-
116
- typeof dockerCompose === 'string' ?
117
- dockerComposeParse(dockerCompose) :
118
- dockerCompose || dockerComposeGetMain(force);
119
-
49
+ const dockerComposeResolve = async (dockerCompose, force) => typeof dockerCompose === 'string'
50
+ ? dockerComposeParse(dockerCompose)
51
+ : dockerCompose || dockerComposeGetMain(force);
120
52
  // Determines an unnamed resource's name from the dirname combined with the key
121
- const prefixName = (name) => `${_path.default.basename(__dirname)}_${name}`;
122
-
123
- const getServiceDef = async (
124
- name,
125
- force,
126
- dockerCompose) => {var _await$dockerComposeR;return (
127
-
128
- ((_await$dockerComposeR = (await dockerComposeResolve(dockerCompose, force)).services) === null || _await$dockerComposeR === void 0 ? void 0 : _await$dockerComposeR[name]) || null);};
129
-
130
-
131
-
132
-
133
-
134
-
135
-
136
-
137
-
138
-
139
-
140
-
141
-
142
-
143
-
144
-
145
-
146
- const parsePorts = async (
147
- portsCfg = [],
148
- avoidConflicts = true,
149
- mapLocal = true,
150
- host = '0.0.0.0') =>
151
- {
152
- const ports = [];
153
- const runArgs = await portsCfg.reduce(async (args, portStr) => {
154
- const [lp, dp] = portStr.split(':');
155
- const localDefault = parseInt(lp, 10);
156
- const docker = parseInt(dp, 10);
157
- const local = mapLocal ?
158
- avoidConflicts ?
159
- await (0, _getPort.default)({ port: localDefault, host }) :
160
- localDefault :
161
- null;
162
- ports.push({ local, localDefault, docker });
163
- return local ? [...(await args), '-p', `${local}:${docker}`] : args;
164
- }, []);
165
- return { runArgs, ports };
53
+ const prefixName = (name) => `${path.basename(__dirname)}_${name}`;
54
+ const getServiceDef = async (name, force, dockerCompose) => (await dockerComposeResolve(dockerCompose, force)).services?.[name] || null;
55
+ const parsePorts = async (portsCfg = [], avoidConflicts = true, mapLocal = true, host = '0.0.0.0') => {
56
+ const ports = [];
57
+ const runArgs = await portsCfg.reduce(async (args, portStr) => {
58
+ const [lp, dp] = portStr.split(':');
59
+ const localDefault = parseInt(lp, 10);
60
+ const docker = parseInt(dp, 10);
61
+ const local = mapLocal
62
+ ? avoidConflicts
63
+ ? await getPort({ host, port: localDefault })
64
+ : localDefault
65
+ : null;
66
+ ports.push({ docker, local, localDefault });
67
+ return local ? [...(await args), '-p', `${local}:${docker}`] : args;
68
+ }, Promise.resolve([]));
69
+ return { ports, runArgs };
166
70
  };
167
-
168
- const parseEnv = (env = []) =>
169
- Array.isArray(env) ?
170
- env.flatMap((e) => ['-e', e]) :
171
- (0, _maps.entries)(env).flatMap(([k, v]) => ['-e', `${k}=${v}`]);
172
-
173
- const parseULimits = (ul = {}) =>
174
- (0, _maps.entries)(ul).flatMap(([k, v]) => [
175
- '--ulimit',
176
- `${k}=${
177
- typeof v === 'number' ? v : `${v.soft}${v.hard ? `:${v.hard}` : ''}`
178
- }`]);
179
-
180
-
181
-
182
-
183
-
184
-
185
-
186
- const parseVolumes = async (
187
- volCfg = [],
188
- nameSuffix = '',
189
- dockerCompose) =>
190
- {
191
- const { volumes: volMap } = await dockerComposeResolve(dockerCompose);
192
- const volumes = [];
193
- const runArgs = volCfg.
194
- map((v) => {
195
- const [src, ...rest] = v.split(':');
196
- const name = volMap !== null && volMap !== void 0 && volMap[src] ?
197
- `${volMap[src].name || prefixName(src)}${nameSuffix}` :
198
- null;
199
- if (name) {
200
- volumes.push(name);
201
- }
202
- const realSrc = name || _path.default.resolve(src);
203
- return [realSrc, ...rest].join(':');
204
- }).
205
- flatMap((v) => ['-v', v]);
206
- return { runArgs, volumes };
71
+ const parseEnv = (env = []) => Array.isArray(env)
72
+ ? env.flatMap((e) => ['-e', e])
73
+ : Object.entries(env).flatMap(([k, v]) => ['-e', `${k}=${v}`]);
74
+ const parseULimits = (ul = {}) => Object.entries(ul).flatMap(([k, v]) => [
75
+ '--ulimit',
76
+ `${k}=${typeof v === 'number' ? v : `${v.soft}${v.hard ? `:${v.hard}` : ''}`}`,
77
+ ]);
78
+ const parseVolumes = async (volCfg = [], nameSuffix = '', dockerCompose = null) => {
79
+ const { volumes: volMap } = await dockerComposeResolve(dockerCompose);
80
+ const volumes = [];
81
+ const runArgs = volCfg
82
+ .map((v) => {
83
+ const [src, ...rest] = v.split(':');
84
+ const name = volMap?.[src]
85
+ ? `${volMap[src].name || prefixName(src)}${nameSuffix}`
86
+ : null;
87
+ if (name) {
88
+ volumes.push(name);
89
+ }
90
+ const realSrc = name || path.resolve(src);
91
+ return [realSrc, ...rest].join(':');
92
+ })
93
+ .flatMap((v) => ['-v', v]);
94
+ return { runArgs, volumes };
95
+ };
96
+ const parseNetworks = async (netCfg = [], dockerCompose = null) => {
97
+ const { networks: netMap } = await dockerComposeResolve(dockerCompose);
98
+ const networks = netCfg.map((n) => netMap?.[n].name || prefixName(n));
99
+ return {
100
+ networks,
101
+ runArgs: networks.flatMap((n) => ['--network', n]),
102
+ };
207
103
  };
208
-
209
-
210
-
211
-
212
-
213
-
214
- const parseNetworks = async (
215
- netCfg = [],
216
- dockerCompose) =>
217
- {
218
- const { networks: netMap } = await dockerComposeResolve(dockerCompose);
219
- const networks = netCfg.map((n) => (netMap === null || netMap === void 0 ? void 0 : netMap[n].name) || prefixName(n));
220
- return {
221
- networks,
222
- runArgs: networks.flatMap((n) => ['--network', n]) };
223
-
104
+ export const dockerComposeCreateNetworks = async (names, dockerCompose, tracker = defaultTracker) => {
105
+ const { networks = {} } = await dockerComposeResolve(dockerCompose);
106
+ await Promise.all(Object.entries(networks).map(async ([key, val]) => {
107
+ const name = val?.name || prefixName(key);
108
+ if (names?.includes(name)) {
109
+ const network = await dockerNetworkCreate(name, val);
110
+ if (network) {
111
+ tracker.networks.set(name, network);
112
+ }
113
+ }
114
+ }));
115
+ };
116
+ export const dockerComposeCreateVolumes = async (names, dockerCompose, tracker = defaultTracker) => {
117
+ const { volumes = {} } = await dockerComposeResolve(dockerCompose);
118
+ await Promise.all(Object.entries(volumes).map(async ([key, val]) => {
119
+ const name = val?.name || prefixName(key);
120
+ if (!names || names.includes(name)) {
121
+ const volume = await dockerVolumeCreate(name, val);
122
+ if (volume) {
123
+ tracker.volumes.set(name, volume);
124
+ }
125
+ }
126
+ }));
224
127
  };
225
-
226
- const dockerComposeCreateNetworks = async (
227
- names,
228
- dockerCompose,
229
- tracker = defaultTracker) =>
230
- {
231
- const { networks = {} } = await dockerComposeResolve(dockerCompose);
232
- await Promise.all(
233
- (0, _maps.entries)(networks).map(async ([key, val]) => {
234
- const name = (val === null || val === void 0 ? void 0 : val.name) || prefixName(key);
235
- if (!names || names.includes(name)) {
236
- const network = await (0, _docker3.dockerNetworkCreate)(name, val || {});
237
- if (network) {
238
- tracker.networks.set(name, network);
239
- }
128
+ export class DockerComposeService {
129
+ constructor(name, serviceDef, dockerCompose) {
130
+ _DockerComposeService_name.set(this, void 0);
131
+ _DockerComposeService_svcDef.set(this, void 0);
132
+ _DockerComposeService_dockerCompose.set(this, void 0);
133
+ _DockerComposeService_tracker.set(this, dockerComposeCreateResourceTracker());
134
+ // lazily computed
135
+ _DockerComposeService_parsedPorts.set(this, null);
136
+ _DockerComposeService_parsedNetworks.set(this, null);
137
+ _DockerComposeService_parsedVolumes.set(this, null);
138
+ _DockerComposeService_baseRunArgs.set(this, null);
139
+ __classPrivateFieldSet(this, _DockerComposeService_name, name, "f");
140
+ __classPrivateFieldSet(this, _DockerComposeService_svcDef, serviceDef, "f");
141
+ __classPrivateFieldSet(this, _DockerComposeService_dockerCompose, dockerCompose || null, "f");
240
142
  }
241
- }));
242
-
243
- };exports.dockerComposeCreateNetworks = dockerComposeCreateNetworks;
244
-
245
- const dockerComposeCreateVolumes = async (
246
- names,
247
- dockerCompose,
248
- tracker = defaultTracker) =>
249
- {
250
- const { volumes = {} } = await dockerComposeResolve(dockerCompose);
251
- await Promise.all(
252
- (0, _maps.entries)(volumes).map(async ([key, val]) => {
253
- const name = (val === null || val === void 0 ? void 0 : val.name) || prefixName(key);
254
- if (!names || names.includes(name)) {
255
- const volume = await (0, _docker4.dockerVolumeCreate)(name, val || {});
256
- if (volume) {
257
- tracker.volumes.set(name, volume);
258
- }
143
+ get name() {
144
+ return __classPrivateFieldGet(this, _DockerComposeService_name, "f");
259
145
  }
260
- }));
261
-
262
- };exports.dockerComposeCreateVolumes = dockerComposeCreateVolumes;var _name = /*#__PURE__*/new WeakMap();var _svcDef = /*#__PURE__*/new WeakMap();var _dockerCompose = /*#__PURE__*/new WeakMap();var _tracker = /*#__PURE__*/new WeakMap();var _parsedPorts = /*#__PURE__*/new WeakMap();var _parsedNetworks = /*#__PURE__*/new WeakMap();var _parsedVolumes = /*#__PURE__*/new WeakMap();var _baseRunArgs = /*#__PURE__*/new WeakMap();
263
-
264
-
265
-
266
-
267
-
268
-
269
-
270
-
271
-
272
-
273
-
274
-
275
-
276
-
277
-
278
-
279
-
280
-
281
-
282
-
283
-
284
-
285
-
286
-
287
-
288
-
289
-
290
-
291
- class DockerComposeService {
292
-
293
-
294
-
295
-
296
-
297
- // lazily computed
298
-
299
-
300
-
301
-
302
-
303
- constructor(
304
- name,
305
- serviceDef,
306
- dockerCompose)
307
- {_classPrivateFieldInitSpec(this, _name, { writable: true, value: void 0 });_classPrivateFieldInitSpec(this, _svcDef, { writable: true, value: void 0 });_classPrivateFieldInitSpec(this, _dockerCompose, { writable: true, value: void 0 });_classPrivateFieldInitSpec(this, _tracker, { writable: true, value: dockerComposeCreateResourceTracker() });_classPrivateFieldInitSpec(this, _parsedPorts, { writable: true, value: null });_classPrivateFieldInitSpec(this, _parsedNetworks, { writable: true, value: null });_classPrivateFieldInitSpec(this, _parsedVolumes, { writable: true, value: null });_classPrivateFieldInitSpec(this, _baseRunArgs, { writable: true, value: null });
308
- _classPrivateFieldSet(this, _name, name);
309
- _classPrivateFieldSet(this, _svcDef, serviceDef);
310
- _classPrivateFieldSet(this, _dockerCompose, dockerCompose || null);
311
- }
312
-
313
- get name() {
314
- return _classPrivateFieldGet(this, _name);
315
- }
316
-
317
- get serviceDef() {
318
- return _classPrivateFieldGet(this, _svcDef);
319
- }
320
-
321
- get image() {
322
- return _classPrivateFieldGet(this, _svcDef).image || null;
323
- }
324
-
325
- get defaultContainerName() {
326
- return _classPrivateFieldGet(this, _svcDef).container_name || _classPrivateFieldGet(this, _name);
327
- }
328
-
329
- get cmd() {
330
- return _classPrivateFieldGet(this, _svcDef).command || [];
331
- }
332
-
333
- get envArgs() {
334
- return parseEnv(_classPrivateFieldGet(this, _svcDef).environment);
335
- }
336
-
337
- /**
338
- * Find (available) container name and alias(es)
339
- * @param {boolean} avoidConflicts if `true`, find a container name that is unused
340
- * @param {number} max maximum number of names to try
341
- */
342
- async getNames(
343
- avoidConflicts = false,
344
- max = 100)
345
- {
346
- /* eslint-disable no-await-in-loop */
347
- for (let i = 0; i < max; i += 1) {
348
- const suffix = i ? `-${i}` : '';
349
- const testName = `${this.defaultContainerName}${suffix}`;
350
- const container = await (0, _docker2.dockerContainerFind)(testName, { all: true });
351
- if (!avoidConflicts || !container) {
352
- return {
353
- name: testName,
354
- aliases: [`${this.name}${suffix}`],
355
- suffix };
356
-
357
- }
146
+ get serviceDef() {
147
+ return __classPrivateFieldGet(this, _DockerComposeService_svcDef, "f");
358
148
  }
359
- /* eslint-enable no-await-in-loop */
360
- throw new Error(
361
- `Failed to find available container name for ${this.defaultContainerName}`);
362
-
363
- }
364
-
365
- // Get (available) port mappings
366
- async getPorts(
367
- avoidConflicts = false,
368
- mapLocal = true)
369
- {
370
- return parsePorts(_classPrivateFieldGet(this, _svcDef).ports, avoidConflicts, mapLocal);
371
- }
372
-
373
- async getDefaultPortInfo() {
374
- if (!_classPrivateFieldGet(this, _parsedPorts)) {
375
- _classPrivateFieldSet(this, _parsedPorts, await this.getPorts());
149
+ get image() {
150
+ return __classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").image || null;
376
151
  }
377
- return _classPrivateFieldGet(this, _parsedPorts);
378
- }
379
-
380
- async getDefaultPorts() {
381
- const { ports } = await this.getDefaultPortInfo();
382
- return ports;
383
- }
384
-
385
- async getDefaultPortArgs() {
386
- const { runArgs } = await this.getDefaultPortInfo();
387
- return runArgs;
388
- }
389
-
390
- async getDefaultUrls() {
391
- return this.constructor.getUrls(
392
- await this.getDefaultPorts(),
393
- this.defaultContainerName);
394
-
395
- }
396
-
397
- async getDefaultNetworkInfo() {
398
- if (!_classPrivateFieldGet(this, _parsedNetworks)) {
399
- _classPrivateFieldSet(this, _parsedNetworks, await parseNetworks(_classPrivateFieldGet(this, _svcDef).networks));
152
+ get defaultContainerName() {
153
+ return __classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").container_name || __classPrivateFieldGet(this, _DockerComposeService_name, "f");
400
154
  }
401
- return _classPrivateFieldGet(this, _parsedNetworks);
402
- }
403
-
404
- async getDefaultNetworks() {
405
- const { networks } = await this.getDefaultNetworkInfo();
406
- return networks;
407
- }
408
-
409
- async getDefaultNetworkArgs() {
410
- const { runArgs } = await this.getDefaultNetworkInfo();
411
- return runArgs;
412
- }
413
-
414
- async getDefaultVolumeInfo() {
415
- if (!_classPrivateFieldGet(this, _parsedVolumes)) {
416
- _classPrivateFieldSet(this, _parsedVolumes, await parseVolumes(_classPrivateFieldGet(this, _svcDef).networks));
155
+ get cmd() {
156
+ return __classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").command || [];
417
157
  }
418
- return _classPrivateFieldGet(this, _parsedVolumes);
419
- }
420
-
421
- async getDefaultVolumes() {
422
- const { volumes } = await this.getDefaultVolumeInfo();
423
- return volumes;
424
- }
425
-
426
- async getDefaultVolumeArgs() {
427
- const { runArgs } = await this.getDefaultVolumeInfo();
428
- return runArgs;
429
- }
430
-
431
- async pull() {
432
- if (!this.image) {
433
- throw new Error(`Cannot pull '${this.name}', no image configured.`);
158
+ get envArgs() {
159
+ return parseEnv(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").environment);
434
160
  }
435
- await (0, _docker.dockerPull)({ image: this.image });
436
- }
437
-
438
- async getBaseRunArgs() {
439
- if (!_classPrivateFieldGet(this, _baseRunArgs)) {
440
- const envArgs = parseEnv(_classPrivateFieldGet(this, _svcDef).environment);
441
- const ulArgs = parseULimits(_classPrivateFieldGet(this, _svcDef).ulimits);
442
- const netArgs = await this.getDefaultNetworkArgs();
443
-
444
- _classPrivateFieldSet(this, _baseRunArgs, ['--rm', ...envArgs, ...netArgs, ...ulArgs]);
161
+ /**
162
+ * Find (available) container name and alias(es)
163
+ * @param {boolean} avoidConflicts if `true`, find a container name that is unused
164
+ * @param {number} max maximum number of names to try
165
+ */
166
+ async getNames(avoidConflicts = false, max = 100) {
167
+ /* eslint-disable no-await-in-loop */
168
+ for (let i = 0; i < max; i += 1) {
169
+ const suffix = i ? `-${i}` : '';
170
+ const testName = `${this.defaultContainerName}${suffix}`;
171
+ const container = await dockerContainerFind(testName, { all: true });
172
+ if (!avoidConflicts || !container) {
173
+ return {
174
+ aliases: [`${this.name}${suffix}`],
175
+ name: testName,
176
+ suffix,
177
+ };
178
+ }
179
+ }
180
+ /* eslint-enable no-await-in-loop */
181
+ throw new Error(`Failed to find available container name for ${this.defaultContainerName}`);
445
182
  }
446
- return _classPrivateFieldGet(this, _baseRunArgs);
447
- }
448
-
449
- async assembleRunArgs(
450
- containerName = this.defaultContainerName,
451
- aliases = [this.name],
452
- additionalArgs)
453
- {
454
- const additional = additionalArgs || [
455
- ...(await this.getDefaultPortArgs()),
456
- ...(await this.getDefaultVolumeArgs())];
457
-
458
- return [
459
- ...(await this.getBaseRunArgs()),
460
- ...(containerName ? ['--name', containerName] : []),
461
- ...aliases.flatMap((a) => a ? ['--network-alias', a] : []),
462
- ...additional];
463
-
464
- }
465
-
466
- async getRunArgs(
467
- avoidConflicts = false,
468
- mapLocalPorts = true)
469
- {
470
- const { name: cName, aliases, suffix } = await this.getNames(
471
- avoidConflicts);
472
-
473
- const { runArgs: pArgs } = await this.getPorts(
474
- avoidConflicts,
475
- mapLocalPorts);
476
-
477
- const { runArgs: vArgs } = await parseVolumes(_classPrivateFieldGet(this, _svcDef).volumes, suffix);
478
- return this.assembleRunArgs(cName, aliases, [...pArgs, ...vArgs]);
479
- }
480
-
481
- async up({
482
- healthCheck,
483
- avoidConflicts = false,
484
- mapVolumes = true,
485
- mapPorts = true,
486
- cmd = this.cmd,
487
- tracker = defaultTracker } =
488
- {}) {
489
- const { image } = this;
490
- if (!image) {
491
- throw new Error(
492
- `Cannot bring up service '${this.name}', no image defined.`);
493
-
183
+ // Get (available) port mappings
184
+ async getPorts(avoidConflicts = false, mapLocal = true) {
185
+ return parsePorts(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").ports, avoidConflicts, mapLocal);
494
186
  }
495
- if (_classPrivateFieldGet(this, _tracker).containers.size) {
496
- (0, _run.buildLog)(
497
- `Warning: up called on service '${this.name}' with already running container`);
498
-
187
+ async getDefaultPortInfo() {
188
+ if (!__classPrivateFieldGet(this, _DockerComposeService_parsedPorts, "f")) {
189
+ __classPrivateFieldSet(this, _DockerComposeService_parsedPorts, await this.getPorts(), "f");
190
+ }
191
+ return __classPrivateFieldGet(this, _DockerComposeService_parsedPorts, "f");
499
192
  }
500
- const { name: containerName, aliases, suffix } = await this.getNames(
501
- avoidConflicts);
502
-
503
- const { runArgs: pArgs, ports } = await this.getPorts(
504
- avoidConflicts,
505
- mapPorts);
506
-
507
- const { runArgs: vArgs, volumes } = mapVolumes ?
508
- await parseVolumes(_classPrivateFieldGet(this, _svcDef).volumes, suffix) :
509
- { runArgs: [], volumes: [] };
510
-
511
- let container = await (0, _docker2.dockerContainerFind)(containerName, { all: true });
512
- if (container && !(await container.isRunning())) {
513
- await container.start();
193
+ async getDefaultPorts() {
194
+ const { ports } = await this.getDefaultPortInfo();
195
+ return ports;
514
196
  }
515
- if (!container) {
516
- await this.pull();
517
- await dockerComposeCreateNetworks(
518
- await this.getDefaultNetworks(), _classPrivateFieldGet(
519
- this, _dockerCompose), _classPrivateFieldGet(
520
- this, _tracker));
521
-
522
- await dockerComposeCreateVolumes(
523
- volumes, _classPrivateFieldGet(
524
- this, _dockerCompose), _classPrivateFieldGet(
525
- this, _tracker));
526
-
527
- const runArgs = await this.assembleRunArgs(containerName, aliases, [
528
- ...pArgs,
529
- ...vArgs]);
530
-
531
- container = await (0, _docker2.dockerContainerRunDaemon)({
532
- image,
533
- runArgs,
534
- cmd });
535
-
536
- } else {
537
- (0, _run.buildLog)(`Reusing existing container for '${this.name}' service.`);
197
+ async getDefaultPortArgs() {
198
+ const { runArgs } = await this.getDefaultPortInfo();
199
+ return runArgs;
538
200
  }
539
- // This service tracks the things it created
540
- _classPrivateFieldGet(this, _tracker).containers.set(containerName, container);
541
- // The passed tracker needs to track this service
542
- tracker.services.set(this.name, this);
543
-
544
- const idAlias = container.id.slice(0, 12);
545
- aliases.push(idAlias);
546
- const urls = this.constructor.getUrls(ports, idAlias);
547
-
548
- const info = {
549
- service: this,
550
- container,
551
- containerName,
552
- aliases,
553
- ports,
554
- volumes,
555
- urls };
556
-
557
- await (healthCheck === null || healthCheck === void 0 ? void 0 : healthCheck(info));
558
- return info;
559
- }
560
-
561
- async down({
562
- includeDefaults = false,
563
- includeVolumes = false,
564
- includeNetworks = false } =
565
-
566
-
567
-
568
-
569
- {}) {
570
- (0, _run.buildLog)(`Bringing down <${this.name}> service...`);
571
- await dockerComposeTeardown({
572
- tracker: _classPrivateFieldGet(this, _tracker),
573
- includeVolumes,
574
- includeNetworks });
575
-
576
- if (includeDefaults) {
577
- const container = await (0, _docker2.dockerContainerFind)(this.defaultContainerName);
578
- if (container) {
579
- await container.teardown(true);
580
- }
201
+ async getDefaultUrls() {
202
+ return DockerComposeService.getUrls(await this.getDefaultPorts(), this.defaultContainerName);
581
203
  }
582
- }
583
-
584
- static async parse(
585
- name,
586
- force = true,
587
- dockerCompose)
588
- {
589
- const svcDef = await getServiceDef(name, force, dockerCompose);
590
- return svcDef ? new this(name, svcDef, dockerCompose) : null;
591
- }
592
-
593
- static getUrls(ports, alias) {
594
- return ports.map(({ local, docker }) => ({
595
- local: local ? `http://localhost:${local}` : null,
596
- docker: docker ? `http://${alias}:${docker}` : null }));
597
-
598
- }}exports.DockerComposeService = DockerComposeService;
599
-
600
-
601
- async function dockerComposeGetAllServices(
602
- dockerCompose)
603
- {
604
- const { services } = await dockerComposeResolve(dockerCompose);
605
- return (0, _maps.mapValuesAsync)(services, (s, name) =>
606
- DockerComposeService.parse(name));
607
-
608
- }
609
-
610
- async function dockerComposeTeardown({
611
- includeDefaults = false,
612
- includeVolumes = false,
613
- includeNetworks = false,
614
- dockerCompose,
615
- tracker = defaultTracker } =
616
-
617
-
618
-
619
-
620
-
621
-
622
- {}) {
623
- if (!tracker.cleaning) {
624
- // eslint-disable-next-line no-param-reassign
625
- tracker.cleaning = (async () => {
626
- if (tracker.services.size) {
627
- (0, _run.buildLog)('Bringing down started docker services...');
628
- const promises = Promise.all(
629
- Array.from(tracker.services.values()).map(async (s) =>
630
- s.down({ includeVolumes, includeNetworks })));
631
-
632
-
633
- tracker.services.clear();
634
- await promises;
635
- }
636
- if (includeDefaults) {
637
- const { services } = await dockerComposeResolve(dockerCompose);
638
- const svcNames = (0, _maps.keys)(services);
639
- if (svcNames.length) {
640
- (0, _run.buildLog)('Bringing down default docker services...');
641
- await Promise.all(
642
- svcNames.map(async (s) => {var _await$DockerComposeS;return (_await$DockerComposeS =
643
- await DockerComposeService.parse(s)) === null || _await$DockerComposeS === void 0 ? void 0 : _await$DockerComposeS.down({
644
- includeDefaults,
645
- includeVolumes,
646
- includeNetworks });}));
647
-
648
-
649
-
204
+ async getDefaultNetworkInfo() {
205
+ if (!__classPrivateFieldGet(this, _DockerComposeService_parsedNetworks, "f")) {
206
+ __classPrivateFieldSet(this, _DockerComposeService_parsedNetworks, await parseNetworks(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").networks), "f");
650
207
  }
651
- }
652
-
653
- if (tracker.containers.size) {
654
- (0, _run.buildLog)('Stopping created docker containers...');
655
- const promises = Promise.all(
656
- Array.from(tracker.containers.values()).map(async (c) =>
657
- c.teardown(true)));
658
-
659
-
660
- tracker.containers.clear();
661
- await promises;
662
- }
663
-
664
- if (includeVolumes) {
665
- if (tracker.volumes.size) {
666
- (0, _run.buildLog)('Removing created docker volumes...');
667
- const promises = Promise.all(
668
- Array.from(tracker.volumes.values()).map(async (v) => v.rm()));
669
-
670
- tracker.volumes.clear();
671
- await promises;
208
+ return __classPrivateFieldGet(this, _DockerComposeService_parsedNetworks, "f");
209
+ }
210
+ async getDefaultNetworks() {
211
+ const { networks } = await this.getDefaultNetworkInfo();
212
+ return networks;
213
+ }
214
+ async getDefaultNetworkArgs() {
215
+ const { runArgs } = await this.getDefaultNetworkInfo();
216
+ return runArgs;
217
+ }
218
+ async getDefaultVolumeInfo() {
219
+ if (!__classPrivateFieldGet(this, _DockerComposeService_parsedVolumes, "f")) {
220
+ __classPrivateFieldSet(this, _DockerComposeService_parsedVolumes, await parseVolumes(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").networks), "f");
672
221
  }
673
- if (includeDefaults) {
674
- (0, _run.buildLog)('Removing default docker volumes...');
675
- const { volumes } = await dockerComposeResolve(dockerCompose);
676
- await Promise.all(
677
- (0, _maps.entries)(volumes).map(async ([key, val]) => {
678
- const name = (val === null || val === void 0 ? void 0 : val.name) || prefixName(key);
679
- await (0, _docker4.dockerVolumeRm)(name, true);
680
- }));
681
-
222
+ return __classPrivateFieldGet(this, _DockerComposeService_parsedVolumes, "f");
223
+ }
224
+ async getDefaultVolumes() {
225
+ const { volumes } = await this.getDefaultVolumeInfo();
226
+ return volumes;
227
+ }
228
+ async getDefaultVolumeArgs() {
229
+ const { runArgs } = await this.getDefaultVolumeInfo();
230
+ return runArgs;
231
+ }
232
+ async pull() {
233
+ if (!this.image) {
234
+ throw new Error(`Cannot pull '${this.name}', no image configured.`);
682
235
  }
683
- }
684
-
685
- if (includeNetworks) {
686
- if (tracker.networks.size) {
687
- (0, _run.buildLog)('Removing created docker networks...');
688
- const promises = Promise.all(
689
- Array.from(tracker.networks.values()).map(async (n) => n.rm()));
690
-
691
- tracker.networks.clear();
692
- await promises;
236
+ await dockerPull({ image: this.image });
237
+ }
238
+ async getBaseRunArgs() {
239
+ if (!__classPrivateFieldGet(this, _DockerComposeService_baseRunArgs, "f")) {
240
+ const envArgs = parseEnv(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").environment);
241
+ const ulArgs = parseULimits(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").ulimits);
242
+ const netArgs = await this.getDefaultNetworkArgs();
243
+ __classPrivateFieldSet(this, _DockerComposeService_baseRunArgs, ['--rm', ...envArgs, ...netArgs, ...ulArgs], "f");
244
+ }
245
+ return __classPrivateFieldGet(this, _DockerComposeService_baseRunArgs, "f");
246
+ }
247
+ async assembleRunArgs(containerName = this.defaultContainerName, aliases = [this.name], additionalArgs = null) {
248
+ const additional = additionalArgs || [
249
+ ...(await this.getDefaultPortArgs()),
250
+ ...(await this.getDefaultVolumeArgs()),
251
+ ];
252
+ return [
253
+ ...(await this.getBaseRunArgs()),
254
+ ...(containerName ? ['--name', containerName] : []),
255
+ ...aliases.flatMap((a) => (a ? ['--network-alias', a] : [])),
256
+ ...additional,
257
+ ];
258
+ }
259
+ async getRunArgs(avoidConflicts = false, mapLocalPorts = true) {
260
+ const { aliases, name: cName, suffix, } = await this.getNames(avoidConflicts);
261
+ const { runArgs: pArgs } = await this.getPorts(avoidConflicts, mapLocalPorts);
262
+ const { runArgs: vArgs } = await parseVolumes(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").volumes, suffix);
263
+ return this.assembleRunArgs(cName, aliases, [...pArgs, ...vArgs]);
264
+ }
265
+ async up({ healthCheck, avoidConflicts = false, mapVolumes = true, mapPorts = true, cmd = this.cmd, tracker = defaultTracker, } = {}) {
266
+ const { image } = this;
267
+ if (!image) {
268
+ throw new Error(`Cannot bring up service '${this.name}', no image defined.`);
269
+ }
270
+ if (__classPrivateFieldGet(this, _DockerComposeService_tracker, "f").containers.size) {
271
+ buildLog(`Warning: up called on service '${this.name}' with already running container`);
693
272
  }
273
+ const { aliases, name: containerName, suffix, } = await this.getNames(avoidConflicts);
274
+ const { ports, runArgs: pArgs } = await this.getPorts(avoidConflicts, mapPorts);
275
+ const { runArgs: vArgs, volumes } = mapVolumes
276
+ ? await parseVolumes(__classPrivateFieldGet(this, _DockerComposeService_svcDef, "f").volumes, suffix)
277
+ : { runArgs: [], volumes: [] };
278
+ let container = await dockerContainerFind(containerName, { all: true });
279
+ if (container && !(await container.isRunning())) {
280
+ await container.start();
281
+ }
282
+ if (!container) {
283
+ await this.pull();
284
+ await dockerComposeCreateNetworks(await this.getDefaultNetworks(), __classPrivateFieldGet(this, _DockerComposeService_dockerCompose, "f"), __classPrivateFieldGet(this, _DockerComposeService_tracker, "f"));
285
+ await dockerComposeCreateVolumes(volumes, __classPrivateFieldGet(this, _DockerComposeService_dockerCompose, "f"), __classPrivateFieldGet(this, _DockerComposeService_tracker, "f"));
286
+ const runArgs = await this.assembleRunArgs(containerName, aliases, [
287
+ ...pArgs,
288
+ ...vArgs,
289
+ ]);
290
+ container = await dockerContainerRunDaemon({
291
+ cmd,
292
+ image,
293
+ runArgs,
294
+ });
295
+ }
296
+ else {
297
+ buildLog(`Reusing existing container for '${this.name}' service.`);
298
+ }
299
+ // This service tracks the things it created
300
+ __classPrivateFieldGet(this, _DockerComposeService_tracker, "f").containers.set(containerName, container);
301
+ // The passed tracker needs to track this service
302
+ tracker.services.set(this.name, this);
303
+ const idAlias = container.id.slice(0, 12);
304
+ aliases.push(idAlias);
305
+ const urls = DockerComposeService.getUrls(ports, idAlias);
306
+ const info = {
307
+ aliases,
308
+ container,
309
+ containerName,
310
+ ports,
311
+ service: this,
312
+ urls,
313
+ volumes,
314
+ };
315
+ await healthCheck?.(info);
316
+ return info;
317
+ }
318
+ async down({ includeDefaults = false, includeNetworks = false, includeVolumes = false, } = {}) {
319
+ buildLog(`Bringing down <${this.name}> service...`);
320
+ await dockerComposeTeardown({
321
+ includeNetworks,
322
+ includeVolumes,
323
+ tracker: __classPrivateFieldGet(this, _DockerComposeService_tracker, "f"),
324
+ });
694
325
  if (includeDefaults) {
695
- (0, _run.buildLog)('Removing default docker networks...');
696
- const { networks } = await dockerComposeResolve(dockerCompose);
697
- await Promise.all(
698
- (0, _maps.entries)(networks).map(async ([key, val]) => {
699
- const name = (val === null || val === void 0 ? void 0 : val.name) || prefixName(key);
700
- try {
701
- await (0, _docker3.dockerNetworkDelete)(name);
702
- } catch (err) {
703
- (0, _run.buildLog)(`Error deleting network '${name}': ${err.message}`);
326
+ const container = await dockerContainerFind(this.defaultContainerName);
327
+ if (container) {
328
+ await container.teardown(true);
704
329
  }
705
- }));
706
-
707
330
  }
708
- }
709
- // eslint-disable-next-line no-param-reassign
710
- tracker.cleaning = null;
711
- })();
712
- }
713
- return tracker.cleaning;
331
+ }
332
+ static async parse(name, force = true, dockerCompose = null) {
333
+ const svcDef = await getServiceDef(name, force, dockerCompose);
334
+ return svcDef ? new this(name, svcDef, dockerCompose) : null;
335
+ }
336
+ static getUrls(ports, alias) {
337
+ return ports.map(({ docker, local }) => ({
338
+ docker: docker ? `http://${alias}:${docker}` : null,
339
+ local: local ? `http://localhost:${local}` : null,
340
+ }));
341
+ }
342
+ }
343
+ _DockerComposeService_name = new WeakMap(), _DockerComposeService_svcDef = new WeakMap(), _DockerComposeService_dockerCompose = new WeakMap(), _DockerComposeService_tracker = new WeakMap(), _DockerComposeService_parsedPorts = new WeakMap(), _DockerComposeService_parsedNetworks = new WeakMap(), _DockerComposeService_parsedVolumes = new WeakMap(), _DockerComposeService_baseRunArgs = new WeakMap();
344
+ export async function dockerComposeGetAllServices(dockerCompose) {
345
+ const { services } = await dockerComposeResolve(dockerCompose);
346
+ return mapValuesAsync(services, (s, name) => DockerComposeService.parse(name));
714
347
  }
715
-
716
-
717
-
718
-
719
-
720
-
721
-
722
-
723
-
724
-
725
-
726
-
727
-
728
-
729
- async function dockerComposeRunService(
730
- key,
731
- upOptions = {},
732
- dockerCompose)
733
- {
734
- const service = await DockerComposeService.parse(
735
- key,
736
- false,
737
- dockerCompose);
738
-
739
- if (!service) {
740
- throw new Error(`Failed to find service '${key}'`);
741
- }
742
- (0, _run.buildLog)(`Starting <${service.name}> service...`);
743
- const upResult = await service.up(upOptions);
744
- const {
745
- container,
746
- urls,
747
- urls: [{ local: url, docker: dockerUrl }],
748
- ports: [{ local: port, docker: dockerPort }] } =
749
- upResult;
750
- const { id, name, image } = container;
751
- urls.forEach(
752
- ({ local }) =>
753
- local && (0, _run.buildLog)(`<${service.name}> accessible at ${local}`));
754
-
755
- return {
756
- ...upResult,
757
- id,
758
- image,
759
- name,
760
- port,
761
- dockerPort,
762
- url,
763
- dockerUrl };
764
-
348
+ export async function dockerComposeTeardown({ includeDefaults = false, includeVolumes = false, includeNetworks = false, dockerCompose, tracker = defaultTracker, } = {}) {
349
+ if (!tracker.cleaning) {
350
+ // eslint-disable-next-line no-param-reassign
351
+ tracker.cleaning = (async () => {
352
+ if (tracker.services.size) {
353
+ buildLog('Bringing down started docker services...');
354
+ const promises = Promise.all(Array.from(tracker.services.values()).map(async (s) => s.down({ includeNetworks, includeVolumes })));
355
+ tracker.services.clear();
356
+ await promises;
357
+ }
358
+ if (includeDefaults) {
359
+ const { services } = await dockerComposeResolve(dockerCompose);
360
+ const svcNames = Object.keys(services ?? {});
361
+ if (svcNames.length) {
362
+ buildLog('Bringing down default docker services...');
363
+ await Promise.all(svcNames.map(async (s) => (await DockerComposeService.parse(s))?.down({
364
+ includeDefaults,
365
+ includeNetworks,
366
+ includeVolumes,
367
+ })));
368
+ }
369
+ }
370
+ if (tracker.containers.size) {
371
+ buildLog('Stopping created docker containers...');
372
+ const promises = Promise.all(Array.from(tracker.containers.values()).map(async (c) => c.teardown(true)));
373
+ tracker.containers.clear();
374
+ await promises;
375
+ }
376
+ if (includeVolumes) {
377
+ if (tracker.volumes.size) {
378
+ buildLog('Removing created docker volumes...');
379
+ const promises = Promise.all(Array.from(tracker.volumes.values()).map(async (v) => v.rm()));
380
+ tracker.volumes.clear();
381
+ await promises;
382
+ }
383
+ if (includeDefaults) {
384
+ buildLog('Removing default docker volumes...');
385
+ const { volumes } = await dockerComposeResolve(dockerCompose);
386
+ await Promise.all(Object.entries(volumes ?? {}).map(async ([key, val]) => {
387
+ const name = val?.name || prefixName(key);
388
+ await dockerVolumeRm(name, true);
389
+ }));
390
+ }
391
+ }
392
+ if (includeNetworks) {
393
+ if (tracker.networks.size) {
394
+ buildLog('Removing created docker networks...');
395
+ const promises = Promise.all(Array.from(tracker.networks.values()).map(async (n) => n.rm()));
396
+ tracker.networks.clear();
397
+ await promises;
398
+ }
399
+ if (includeDefaults) {
400
+ buildLog('Removing default docker networks...');
401
+ const { networks } = await dockerComposeResolve(dockerCompose);
402
+ await Promise.all(Object.entries(networks ?? {}).map(async ([key, val]) => {
403
+ const name = val?.name || prefixName(key);
404
+ try {
405
+ await dockerNetworkDelete(name);
406
+ }
407
+ catch (err) {
408
+ buildLog(`Error deleting network '${name}': ${err.message}`);
409
+ }
410
+ }));
411
+ }
412
+ }
413
+ // eslint-disable-next-line no-param-reassign
414
+ tracker.cleaning = null;
415
+ })();
416
+ }
417
+ return tracker.cleaning;
418
+ }
419
+ export async function dockerComposeRunService(key, upOptions = {}, dockerCompose = null) {
420
+ const service = await DockerComposeService.parse(key, false, dockerCompose);
421
+ if (!service) {
422
+ throw new Error(`Failed to find service '${key}'`);
423
+ }
424
+ buildLog(`Starting <${service.name}> service...`);
425
+ const upResult = await service.up(upOptions);
426
+ const { container, urls, urls: [{ docker: dockerUrl, local: url }], ports: [{ docker: dockerPort, local: port }], } = upResult;
427
+ const { id, image, name } = container;
428
+ urls.forEach(({ local }) => local && buildLog(`<${service.name}> accessible at ${local}`));
429
+ return {
430
+ ...upResult,
431
+ dockerPort,
432
+ dockerUrl,
433
+ id,
434
+ image,
435
+ name,
436
+ port,
437
+ url,
438
+ };
765
439
  }
766
- //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uL3NyYy9kb2NrZXJDb21wb3NlLmpzIl0sIm5hbWVzIjpbImRvY2tlckNvbXBvc2VDcmVhdGVSZXNvdXJjZVRyYWNrZXIiLCJuZXR3b3JrcyIsIk1hcCIsInNlcnZpY2VzIiwiY29udGFpbmVycyIsInZvbHVtZXMiLCJjbGVhbmluZyIsImRlZmF1bHRUcmFja2VyIiwiZG9ja2VyQ29tcG9zZVBhcnNlIiwiZmlsZVBhdGgiLCJ5YW1sIiwibG9hZCIsImZzIiwicmVhZEZpbGUiLCJkYyIsImRvY2tlckNvbXBvc2VHZXRNYWluIiwiZm9yY2UiLCJkb2NrZXJDb21wb3NlUmVzb2x2ZSIsImRvY2tlckNvbXBvc2UiLCJwcmVmaXhOYW1lIiwibmFtZSIsInBhdGgiLCJiYXNlbmFtZSIsIl9fZGlybmFtZSIsImdldFNlcnZpY2VEZWYiLCJwYXJzZVBvcnRzIiwicG9ydHNDZmciLCJhdm9pZENvbmZsaWN0cyIsIm1hcExvY2FsIiwiaG9zdCIsInBvcnRzIiwicnVuQXJncyIsInJlZHVjZSIsImFyZ3MiLCJwb3J0U3RyIiwibHAiLCJkcCIsInNwbGl0IiwibG9jYWxEZWZhdWx0IiwicGFyc2VJbnQiLCJkb2NrZXIiLCJsb2NhbCIsInBvcnQiLCJwdXNoIiwicGFyc2VFbnYiLCJlbnYiLCJBcnJheSIsImlzQXJyYXkiLCJmbGF0TWFwIiwiZSIsImsiLCJ2IiwicGFyc2VVTGltaXRzIiwidWwiLCJzb2Z0IiwiaGFyZCIsInBhcnNlVm9sdW1lcyIsInZvbENmZyIsIm5hbWVTdWZmaXgiLCJ2b2xNYXAiLCJtYXAiLCJzcmMiLCJyZXN0IiwicmVhbFNyYyIsInJlc29sdmUiLCJqb2luIiwicGFyc2VOZXR3b3JrcyIsIm5ldENmZyIsIm5ldE1hcCIsIm4iLCJkb2NrZXJDb21wb3NlQ3JlYXRlTmV0d29ya3MiLCJuYW1lcyIsInRyYWNrZXIiLCJQcm9taXNlIiwiYWxsIiwia2V5IiwidmFsIiwiaW5jbHVkZXMiLCJuZXR3b3JrIiwic2V0IiwiZG9ja2VyQ29tcG9zZUNyZWF0ZVZvbHVtZXMiLCJ2b2x1bWUiLCJEb2NrZXJDb21wb3NlU2VydmljZSIsImNvbnN0cnVjdG9yIiwic2VydmljZURlZiIsImltYWdlIiwiZGVmYXVsdENvbnRhaW5lck5hbWUiLCJjb250YWluZXJfbmFtZSIsImNtZCIsImNvbW1hbmQiLCJlbnZBcmdzIiwiZW52aXJvbm1lbnQiLCJnZXROYW1lcyIsIm1heCIsImkiLCJzdWZmaXgiLCJ0ZXN0TmFtZSIsImNvbnRhaW5lciIsImFsaWFzZXMiLCJFcnJvciIsImdldFBvcnRzIiwiZ2V0RGVmYXVsdFBvcnRJbmZvIiwiZ2V0RGVmYXVsdFBvcnRzIiwiZ2V0RGVmYXVsdFBvcnRBcmdzIiwiZ2V0RGVmYXVsdFVybHMiLCJnZXRVcmxzIiwiZ2V0RGVmYXVsdE5ldHdvcmtJbmZvIiwiZ2V0RGVmYXVsdE5ldHdvcmtzIiwiZ2V0RGVmYXVsdE5ldHdvcmtBcmdzIiwiZ2V0RGVmYXVsdFZvbHVtZUluZm8iLCJnZXREZWZhdWx0Vm9sdW1lcyIsImdldERlZmF1bHRWb2x1bWVBcmdzIiwicHVsbCIsImdldEJhc2VSdW5BcmdzIiwidWxBcmdzIiwidWxpbWl0cyIsIm5ldEFyZ3MiLCJhc3NlbWJsZVJ1bkFyZ3MiLCJjb250YWluZXJOYW1lIiwiYWRkaXRpb25hbEFyZ3MiLCJhZGRpdGlvbmFsIiwiYSIsImdldFJ1bkFyZ3MiLCJtYXBMb2NhbFBvcnRzIiwiY05hbWUiLCJwQXJncyIsInZBcmdzIiwidXAiLCJoZWFsdGhDaGVjayIsIm1hcFZvbHVtZXMiLCJtYXBQb3J0cyIsInNpemUiLCJpc1J1bm5pbmciLCJzdGFydCIsImlkQWxpYXMiLCJpZCIsInNsaWNlIiwidXJscyIsImluZm8iLCJzZXJ2aWNlIiwiZG93biIsImluY2x1ZGVEZWZhdWx0cyIsImluY2x1ZGVWb2x1bWVzIiwiaW5jbHVkZU5ldHdvcmtzIiwiZG9ja2VyQ29tcG9zZVRlYXJkb3duIiwidGVhcmRvd24iLCJwYXJzZSIsInN2Y0RlZiIsImFsaWFzIiwiZG9ja2VyQ29tcG9zZUdldEFsbFNlcnZpY2VzIiwicyIsInByb21pc2VzIiwiZnJvbSIsInZhbHVlcyIsImNsZWFyIiwic3ZjTmFtZXMiLCJsZW5ndGgiLCJjIiwicm0iLCJlcnIiLCJtZXNzYWdlIiwiZG9ja2VyQ29tcG9zZVJ1blNlcnZpY2UiLCJ1cE9wdGlvbnMiLCJ1cFJlc3VsdCIsInVybCIsImRvY2tlclVybCIsImRvY2tlclBvcnQiLCJmb3JFYWNoIl0sIm1hcHBpbmdzIjoiO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTs7QUFFQTtBQUNBO0FBQ0E7Ozs7O0FBS0E7Ozs7OztBQU1BLDBDOzs7Ozs7Ozs7Ozs7OztBQWNPLE1BQU1BLGtDQUFrQyxHQUFHLE9BQXFDO0FBQ3JGQyxFQUFBQSxRQUFRLEVBQUUsSUFBSUMsR0FBSixFQUQyRTtBQUVyRkMsRUFBQUEsUUFBUSxFQUFFLElBQUlELEdBQUosRUFGMkU7QUFHckZFLEVBQUFBLFVBQVUsRUFBRSxJQUFJRixHQUFKLEVBSHlFO0FBSXJGRyxFQUFBQSxPQUFPLEVBQUUsSUFBSUgsR0FBSixFQUo0RTtBQUtyRkksRUFBQUEsUUFBUSxFQUFFLElBTDJFLEVBQXJDLENBQTNDLEM7OztBQVFQLE1BQU1DLGNBQWMsR0FBR1Asa0NBQWtDLEVBQXpEOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQTRDQTtBQUNBO0FBQ0E7QUFDQTtBQUNPLE1BQU1RLGtCQUFrQixHQUFHO0FBQ2hDQyxRQUFpQixHQUFHLHNCQURZO0FBRUpDLGdCQUFLQyxJQUFMLENBQVUsTUFBTUMsaUJBQUdDLFFBQUgsQ0FBWUosUUFBWixDQUFoQixDQUZ2QixDOztBQUlQLElBQUlLLEVBQWtCLEdBQUcsSUFBekI7O0FBRUE7QUFDQTtBQUNBO0FBQ0E7QUFDTyxNQUFNQyxvQkFBb0IsR0FBRztBQUNsQ0MsS0FBZSxHQUFHLEtBRGdCO0FBRVA7QUFDM0IsTUFBSUEsS0FBSyxJQUFJLENBQUNGLEVBQWQsRUFBa0I7QUFDaEJBLElBQUFBLEVBQUUsR0FBRyxNQUFNTixrQkFBa0IsRUFBN0I7QUFDRDtB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LENBSEY7QUFJSnZJLElBQUFBLEtBQUssRUFBRSxDQUFDLEVBQUVXLEtBQUssRUFBRUMsSUFBVCxFQUFlRixNQUFNLEVBQUU4SCxVQUF2QixFQUFELENBSkg7QUFLRkgsRUFBQUEsUUFMSjtBQU1BLFFBQU0sRUFBRTVCLEVBQUYsRUFBTW5ILElBQU4sRUFBWWlFLEtBQVosS0FBc0JZLFNBQTVCO0FBQ0F3QyxFQUFBQSxJQUFJLENBQUM4QixPQUFMO0FBQ0UsR0FBQyxFQUFFOUgsS0FBRixFQUFEO0FBQ0VBLEVBQUFBLEtBQUssSUFBSSxtQkFBVSxJQUFHa0csT0FBTyxDQUFDdkgsSUFBSyxtQkFBa0JxQixLQUFNLEVBQWxELENBRmI7O0FBSUEsU0FBTztBQUNMLE9BQUcwSCxRQURFO0FBRUw1QixJQUFBQSxFQUZLO0FBR0xsRCxJQUFBQSxLQUhLO0FBSUxqRSxJQUFBQSxJQUpLO0FBS0xzQixJQUFBQSxJQUxLO0FBTUw0SCxJQUFBQSxVQU5LO0FBT0xGLElBQUFBLEdBUEs7QUFRTEMsSUFBQUEsU0FSSyxFQUFQOztBQVVEIiwic291cmNlc0NvbnRlbnQiOlsiLy8gQGZsb3dcbmltcG9ydCBmcyBmcm9tICdmcy1leHRyYSc7XG5pbXBvcnQgeWFtbCBmcm9tICdqcy15YW1sJztcbmltcG9ydCBwYXRoIGZyb20gJ3BhdGgnO1xuaW1wb3J0IGdldFBvcnQgZnJvbSAnZ2V0LXBvcnQnO1xuaW1wb3J0IHsga2V5cywgZW50cmllcywgbWFwVmFsdWVzQXN5bmMsIHR5cGUgTWFwT2JqIH0gZnJvbSAnLi9tYXBzJztcblxuaW1wb3J0IHsgYnVpbGRMb2cgfSBmcm9tICcuL3J1bic7XG5pbXBvcnQgeyBkb2NrZXJQdWxsIH0gZnJvbSAnLi9kb2NrZXInO1xuaW1wb3J0IHtcbiAgZG9ja2VyQ29udGFpbmVyRmluZCxcbiAgZG9ja2VyQ29udGFpbmVyUnVuRGFlbW9uLFxuICB0eXBlIERvY2tlckNvbnRhaW5lcixcbn0gZnJvbSAnLi9kb2NrZXIuY29udGFpbmVyJztcbmltcG9ydCB7XG4gIGRvY2tlck5ldHdvcmtEZWxldGUsXG4gIGRvY2tlck5ldHdvcmtDcmVhdGUsXG4gIHR5cGUgRG9ja2VyTmV0d29ya0NyZWF0ZU9wdGlvbnMsXG4gIHR5cGUgRG9ja2VyTmV0d29yayxcbn0gZnJvbSAnLi9kb2NrZXIubmV0d29yayc7XG5pbXBvcnQge1xuICBkb2NrZXJWb2x1bWVDcmVhdGUsXG4gIGRvY2tlclZvbHVtZVJtLFxuICB0eXBlIERvY2tlclZvbHVtZSxcbn0gZnJvbSAnLi9kb2NrZXIudm9sdW1lJztcblxuZXhwb3J0IHR5cGUgRG9ja2VyQ29tcG9zZVJlc291cmNlVHJhY2tlciA9IHtcbiAgc2VydmljZXM6IE1hcDxzdHJpbmcsIERvY2tlckNvbXBvc2VTZXJ2aWNlPixcbiAgbmV0d29ya3M6IE1hcDxzdHJpbmcsIERvY2tlck5ldHdvcms+LFxuICBjb250YWluZXJzOiBNYXA8c3RyaW5nLCBEb2NrZXJDb250YWluZXI+LFxuICB2b2x1bWVzOiBNYXA8c3RyaW5nLCBEb2NrZXJWb2x1bWU+LFxuICBjbGVhbmluZzogP1Byb21pc2U8dm9pZD4sXG59O1xuXG5leHBvcnQgY29uc3QgZG9ja2VyQ29tcG9zZUNyZWF0ZVJlc291cmNlVHJhY2tlciA9ICgpOiBEb2NrZXJDb21wb3NlUmVzb3VyY2VUcmFja2VyID0+ICh7XG4gIG5ldHdvcmtzOiBuZXcgTWFwKCksXG4gIHNlcnZpY2VzOiBuZXcgTWFwKCksXG4gIGNvbnRhaW5lcnM6IG5ldyBNYXAoKSxcbiAgdm9sdW1lczogbmV3IE1hcCgpLFxuICBjbGVhbmluZzogbnVsbCxcbn0pO1xuXG5jb25zdCBkZWZhdWx0VHJhY2tlciA9IGRvY2tlckNvbXBvc2VDcmVhdGVSZXNvdXJjZVRyYWNrZXIoKTtcblxudHlwZSBEb2NrZXJDb21wb3NlRW52RGVmID0gc3RyaW5nW10gfCB7IFtzdHJpbmddOiBzdHJpbmcgfTtcblxudHlwZSBEb2NrZXJDb21wb3NlVUxpbWl0RGVmID0gbnVtYmVyIHwgeyBzb2Z0OiBudW1iZXIsIGhhcmQ6IG51bWJlciB9O1xuXG50eXBlIERvY2tlckNvbXBvc2VVTGltaXRzRGVmID0ge1xuICBbc3RyaW5nXTogRG9ja2VyQ29tcG9zZVVMaW1pdERlZixcbn07XG5cbnR5cGUgRG9ja2VyQ29tcG9zZVNlcnZpY2VEZWYgPSB7XG4gIGNvbnRhaW5lcl9uYW1lPzogc3RyaW5nLFxuICBpbWFnZT86IHN0cmluZyxcbiAgcG9ydHM/OiBzdHJpbmdbXSxcbiAgdm9sdW1lcz86IHN0cmluZ1tdLFxuICBjb21tYW5kPzogc3RyaW5nW10sXG4gIG5ldHdvcmtzPzogc3RyaW5nW10sXG4gIGVudmlyb25tZW50PzogRG9ja2VyQ29tcG9zZUVudkRlZixcbiAgbGlua3M/OiBzdHJpbmdbXSxcbiAgdWxpbWl0cz86IERvY2tlckNvbXBvc2VVTGltaXRzRGVmLFxufTtcblxudHlwZSBEb2NrZXJDb21wb3NlVm9sdW1lRGVmID0ge1xuICBuYW1lPzogc3RyaW5nLFxufTtcblxudHlwZSBEb2NrZXJDb21wb3NlTmV0d29ya0RlZiA9IHtcbiAgLi4uRG9ja2VyTmV0d29ya0NyZWF0ZU9wdGlvbnMsXG4gIG5hbWU/OiBzdHJpbmcsXG59O1xuXG50eXBlIERvY2tlckNvbXBvc2UgPSB7XG4gIHZlcnNpb246IHN0cmluZyxcbiAgc2VydmljZXM/OiB7XG4gICAgW3N0cmluZ106IERvY2tlckNvbXBvc2VTZXJ2aWNlRGVmLFxuICB9LFxuICB2b2x1bWVzPzoge1xuICAgIFtzdHJpbmddOiBEb2NrZXJDb21wb3NlVm9sdW1lRGVmLFxuICB9LFxuICBuZXR3b3Jrcz86IHtcbiAgICBbc3RyaW5nXTogRG9ja2VyQ29tcG9zZU5ldHdvcmtEZWYsXG4gIH0sXG59O1xuXG4vKipcbiAqIFBhcnNlIGEgZG9ja2VyLWNvbXBvc2UueW1sIGZpbGUgaW50byBhIHBvam8gcmVwcmVzZW50YXRpb25cbiAqIEBwYXJhbSB7c3RyaW5nfSBmaWxlUGF0aCBQYXRoIHRvIHRoZSBkb2NrZXItY29tcG9zZS55bWwgZmlsZVxuICovXG5leHBvcnQgY29uc3QgZG9ja2VyQ29tcG9zZVBhcnNlID0gYXN5bmMgKFxuICBmaWxlUGF0aD86IHN0cmluZyA9ICcuL2RvY2tlci1jb21wb3NlLnltbCcsXG4pOiBQcm9taXNlPERvY2tlckNvbXBvc2U+ID0+ICh5YW1sLmxvYWQoYXdhaXQgZnMucmVhZEZpbGUoZmlsZVBhdGgpKTogYW55KTtcblxubGV0IGRjOiA/RG9ja2VyQ29tcG9zZSA9IG51bGw7XG5cbi8qKlxuICogR2V0IHRoZSBtYWluIGRvY2tlci1jb21wb3NlLnltbCBmcm9tIHRoZSByb290IG9mIHRoZSByZXBvXG4gKiBAcGFyYW0ge2Jvb2xlYW59IGZvcmNlIEZvcmNlIHJlbG9hZCBmcm9tIGZpbGVcbiAqL1xuZXhwb3J0IGNvbnN0IGRvY2tlckNvbXBvc2VHZXRNYWluID0gYXN5bmMgKFxuICBmb3JjZT86IGJvb2xlYW4gPSBmYWxzZSxcbik6IFByb21pc2U8RG9ja2VyQ29tcG9zZT4gPT4ge1xuICBpZiAoZm9yY2UgfHwgIWRjKSB7XG4gICAgZGMgPSBhd2FpdCBkb2NrZXJDb21wb3NlUGFyc2UoKTtcbiAgfVxuICByZXR1cm4gZGM7XG59O1xuXG4vLyBGdW5jdGlvbiB0aGF0IGhhbmRsZXMgcGFzc2VkIGRvY2tlckNvbXBvc2UgYXMgZWl0aGVyIGEgZmlsZSBwYXRoIG9yIGBEb2NrZXJDb21wb3NlYCBvYmplY3QuXG4vLyBJZiBub3QgcGFzc2VkLCBkZWZhdWx0cyB0byB0aGUgbWFpbiBkb2NrZXItY29tcG9zZS55bWwgZnJvbSB0aGUgcm9vdCBvZiB0aGUgcmVwb1xuY29uc3QgZG9ja2VyQ29tcG9zZVJlc29sdmUgPSBhc3luYyAoXG4gIGRvY2tlckNvbXBvc2U/OiA/KHN0cmluZyB8IERvY2tlckNvbXBvc2UpLFxuICBmb3JjZT86IGJvb2xlYW4sXG4pOiBQcm9taXNlPERvY2tlckNvbXBvc2U+ID0+XG4gIHR5cGVvZiBkb2NrZXJDb21wb3NlID09PSAnc3RyaW5nJ1xuICAgID8gZG9ja2VyQ29tcG9zZVBhcnNlKGRvY2tlckNvbXBvc2UpXG4gICAgOiBkb2NrZXJDb21wb3NlIHx8IGRvY2tlckNvbXBvc2VHZXRNYWluKGZvcmNlKTtcblxuLy8gRGV0ZXJtaW5lcyBhbiB1bm5hbWVkIHJlc291cmNlJ3MgbmFtZSBmcm9tIHRoZSBkaXJuYW1lIGNvbWJpbmVkIHdpdGggdGhlIGtleVxuY29uc3QgcHJlZml4TmFtZSA9IChuYW1lOiBzdHJpbmcpID0+IGAke3BhdGguYmFzZW5hbWUoX19kaXJuYW1lKX1fJHtuYW1lfWA7XG5cbmNvbnN0IGdldFNlcnZpY2VEZWYgPSBhc3luYyAoXG4gIG5hbWU6IHN0cmluZyxcbiAgZm9yY2U/OiBib29sZWFuLFxuICBkb2NrZXJDb21wb3NlPzogPyhzdHJpbmcgfCBEb2NrZXJDb21wb3NlKSxcbik6IFByb21pc2U8P0RvY2tlckNvbXBvc2VTZXJ2aWNlRGVmPiA9PlxuICAoYXdhaXQgZG9ja2VyQ29tcG9zZVJlc29sdmUoZG9ja2VyQ29tcG9zZSwgZm9yY2UpKS5zZXJ2aWNlcz8uW25hbWVdIHx8IG51bGw7XG5cbnR5cGUgUG9ydE1hcCA9IHtcbiAgbG9jYWw6ID9udW1iZXIsXG4gIGxvY2FsRGVmYXVsdDogbnVtYmVyLFxuICBkb2NrZXI6IG51bWJlcixcbn07XG5cbnR5cGUgVXJsTWFwID0ge1xuICBsb2NhbDogP3N0cmluZyxcbiAgZG9ja2VyOiA/c3RyaW5nLFxufTtcblxudHlwZSBQYXJzZWRQb3J0SW5mbyA9IHtcbiAgcnVuQXJnczogc3RyaW5nW10sXG4gIHBvcnRzOiBQb3J0TWFwW10sXG59O1xuXG5jb25zdCBwYXJzZVBvcnRzID0gYXN5bmMgKFxuICBwb3J0c0NmZz86IHN0cmluZ1tdID0gW10sXG4gIGF2b2lkQ29uZmxpY3RzPzogYm9vbGVhbiA9IHRydWUsXG4gIG1hcExvY2FsPzogYm9vbGVhbiA9IHRydWUsXG4gIGhvc3Q/OiBzdHJpbmcgPSAnMC4wLjAuMCcsXG4pOiBQcm9taXNlPFBhcnNlZFBvcnRJbmZvPiA9PiB7XG4gIGNvbnN0IHBvcnRzOiBQb3J0TWFwW10gPSBbXTtcbiAgY29uc3QgcnVuQXJncyA9IGF3YWl0IHBvcnRzQ2ZnLnJlZHVjZShhc3luYyAoYXJncywgcG9ydFN0cikgPT4ge1xuICAgIGNvbnN0IFtscCwgZHBdID0gcG9ydFN0ci5zcGxpdCgnOicpO1xuICAgIGNvbnN0IGxvY2FsRGVmYXVsdCA9IHBhcnNlSW50KGxwLCAxMCk7XG4gICAgY29uc3QgZG9ja2VyID0gcGFyc2VJbnQoZHAsIDEwKTtcbiAgICBjb25zdCBsb2NhbCA9IG1hcExvY2FsXG4gICAgICA/IGF2b2lkQ29uZmxpY3RzXG4gICAgICAgID8gYXdhaXQgZ2V0UG9ydCh7IHBvcnQ6IGxvY2FsRGVmYXVsdCwgaG9zdCB9KVxuICAgICAgICA6IGxvY2FsRGVmYXVsdFxuICAgICAgOiBudWxsO1xuICAgIHBvcnRzLnB1c2goeyBsb2NhbCwgbG9jYWxEZWZhdWx0LCBkb2NrZXIgfSk7XG4gICAgcmV0dXJuIGxvY2FsID8gWy4uLihhd2FpdCBhcmdzKSwgJy1wJywgYCR7bG9jYWx9OiR7ZG9ja2VyfWBdIDogYXJncztcbiAgfSwgW10pO1xuICByZXR1cm4geyBydW5BcmdzLCBwb3J0cyB9O1xufTtcblxuY29uc3QgcGFyc2VFbnYgPSAoZW52PzogRG9ja2VyQ29tcG9zZUVudkRlZiA9IFtdKTogc3RyaW5nW10gPT5cbiAgQXJyYXkuaXNBcnJheShlbnYpXG4gICAgPyBlbnYuZmxhdE1hcCgoZSkgPT4gWyctZScsIGVdKVxuICAgIDogZW50cmllcyhlbnYpLmZsYXRNYXAoKFtrLCB2XSkgPT4gWyctZScsIGAke2t9PSR7dn1gXSk7XG5cbmNvbnN0IHBhcnNlVUxpbWl0cyA9ICh1bD86IERvY2tlckNvbXBvc2VVTGltaXRzRGVmID0ge30pOiBzdHJpbmdbXSA9PlxuICBlbnRyaWVzKHVsKS5mbGF0TWFwKChbaywgdl0pID0+IFtcbiAgICAnLS11bGltaXQnLFxuICAgIGAke2t9PSR7XG4gICAgICB0eXBlb2YgdiA9PT0gJ251bWJlcicgPyB2IDogYCR7di5zb2Z0fSR7di5oYXJkID8gYDoke3YuaGFyZH1gIDogJyd9YFxuICAgIH1gLFxuICBdKTtcblxudHlwZSBQYXJzZWRWb2x1bWVJbmZvID0ge1xuICBydW5BcmdzOiBzdHJpbmdbXSxcbiAgdm9sdW1lczogc3RyaW5nW10sXG59O1xuXG5jb25zdCBwYXJzZVZvbHVtZXMgPSBhc3luYyAoXG4gIHZvbENmZz86IHN0cmluZ1tdID0gW10sXG4gIG5hbWVTdWZmaXg/OiBzdHJpbmcgPSAnJyxcbiAgZG9ja2VyQ29tcG9zZT86ID8oc3RyaW5nIHwgRG9ja2VyQ29tcG9zZSksXG4pOiBQcm9taXNlPFBhcnNlZFZvbHVtZUluZm8+ID0+IHtcbiAgY29uc3QgeyB2b2x1bWVzOiB2b2xNYXAgfSA9IGF3YWl0IGRvY2tlckNvbXBvc2VSZXNvbHZlKGRvY2tlckNvbXBvc2UpO1xuICBjb25zdCB2b2x1bWVzID0gW107XG4gIGNvbnN0IHJ1bkFyZ3M6IHN0cmluZ1tdID0gdm9sQ2ZnXG4gICAgLm1hcCgodikgPT4ge1xuICAgICAgY29uc3QgW3NyYywgLi4ucmVzdF0gPSB2LnNwbGl0KCc6Jyk7XG4gICAgICBjb25zdCBuYW1lID0gdm9sTWFwPy5bc3JjXVxuICAgICAgICA/IGAke3ZvbE1hcFtzcmNdLm5hbWUgfHwgcHJlZml4TmFtZShzcmMpfSR7bmFtZVN1ZmZpeH1gXG4gICAgICAgIDogbnVsbDtcbiAgICAgIGlmIChuYW1lKSB7XG4gICAgICAgIHZvbHVtZXMucHVzaChuYW1lKTtcbiAgICAgIH1cbiAgICAgIGNvbnN0IHJlYWxTcmMgPSBuYW1lIHx8IHBhdGgucmVzb2x2ZShzcmMpO1xuICAgICAgcmV0dXJuIFtyZWFsU3JjLCAuLi5yZXN0XS5qb2luKCc6Jyk7XG4gICAgfSlcbiAgICAuZmxhdE1hcCgodikgPT4gWyctdicsIHZdKTtcbiAgcmV0dXJuIHsgcnVuQXJncywgdm9sdW1lcyB9O1xufTtcblxudHlwZSBQYXJzZWROZXR3b3JrSW5mbyA9IHtcbiAgcnVuQXJnczogc3RyaW5nW10sXG4gIG5ldHdvcmtzOiBzdHJpbmdbXSxcbn07XG5cbmNvbnN0IHBhcnNlTmV0d29ya3MgPSBhc3luYyAoXG4gIG5ldENmZz86IHN0cmluZ1tdID0gW10sXG4gIGRvY2tlckNvbXBvc2U/OiA/KHN0cmluZyB8IERvY2tlckNvbXBvc2UpLFxuKTogUHJvbWlzZTxQYXJzZWROZXR3b3JrSW5mbz4gPT4ge1xuICBjb25zdCB7IG5ldHdvcmtzOiBuZXRNYXAgfSA9IGF3YWl0IGRvY2tlckNvbXBvc2VSZXNvbHZlKGRvY2tlckNvbXBvc2UpO1xuICBjb25zdCBuZXR3b3JrcyA9IG5ldENmZy5tYXAoKG4pID0+IG5ldE1hcD8uW25dLm5hbWUgfHwgcHJlZml4TmFtZShuKSk7XG4gIHJldHVybiB7XG4gICAgbmV0d29ya3MsXG4gICAgcnVuQXJnczogKG5ldHdvcmtzLmZsYXRNYXAoKG4pID0+IFsnLS1uZXR3b3JrJywgbl0pOiBzdHJpbmdbXSksXG4gIH07XG59O1xuXG5leHBvcnQgY29uc3QgZG9ja2VyQ29tcG9zZUNyZWF0ZU5ldHdvcmtzID0gYXN5bmMgKFxuICBuYW1lcz86ID8oc3RyaW5nW10pLFxuICBkb2NrZXJDb21wb3NlPzogPyhzdHJpbmcgfCBEb2NrZXJDb21wb3NlKSxcbiAgdHJhY2tlcj86IERvY2tlckNvbXBvc2VSZXNvdXJjZVRyYWNrZXIgPSBkZWZhdWx0VHJhY2tlcixcbikgPT4ge1xuICBjb25zdCB7IG5ldHdvcmtzID0ge30gfSA9IGF3YWl0IGRvY2tlckNvbXBvc2VSZXNvbHZlKGRvY2tlckNvbXBvc2UpO1xuICBhd2FpdCBQcm9taXNlLmFsbChcbiAgICBlbnRyaWVzKG5ldHdvcmtzKS5tYXAoYXN5bmMgKFtrZXksIHZhbF0pID0+IHtcbiAgICAgIGNvbnN0IG5hbWUgPSB2YWw/Lm5hbWUgfHwgcHJlZml4TmFtZShrZXkpO1xuICAgICAgaWYgKCFuYW1lcyB8fCBuYW1lcy5pbmNsdWRlcyhuYW1lKSkge1xuICAgICAgICBjb25zdCBuZXR3b3JrID0gYXdhaXQgZG9ja2VyTmV0d29ya0NyZWF0ZShuYW1lLCAodmFsIHx8IHt9OiBhbnkpKTtcbiAgICAgICAgaWYgKG5ldHdvcmspIHtcbiAgICAgICAgICB0cmFja2VyLm5ldHdvcmtzLnNldChuYW1lLCBuZXR3b3JrKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH0pLFxuICApO1xufTtcblxuZXhwb3J0IGNvbnN0IGRvY2tlckNvbXBvc2VDcmVhdGVWb2x1bWVzID0gYXN5bmMgKFxuICBuYW1lcz86IHN0cmluZ1tdLFxuICBkb2NrZXJDb21wb3NlPzogPyhzdHJpbmcgfCBEb2NrZXJDb21wb3NlKSxcbiAgdHJhY2tlcj86IERvY2tlckNvbXBvc2VSZXNvdXJjZVRyYWNrZXIgPSBkZWZhdWx0VHJhY2tlcixcbikgPT4ge1xuICBjb25zdCB7IHZvbHVtZXMgPSB7fSB9ID0gYXdhaXQgZG9ja2VyQ29tcG9zZVJlc29sdmUoZG9ja2VyQ29tcG9zZSk7XG4gIGF3YWl0IFByb21pc2UuYWxsKFxuICAgIGVudHJpZXModm9sdW1lcykubWFwKGFzeW5jIChba2V5LCB2YWxdKSA9PiB7XG4gICAgICBjb25zdCBuYW1lID0gdmFsPy5uYW1lIHx8IHByZWZpeE5hbWUoa2V5KTtcbiAgICAgIGlmICghbmFtZXMgfHwgbmFtZXMuaW5jbHVkZXMobmFtZSkpIHtcbiAgICAgICAgY29uc3Qgdm9sdW1lID0gYXdhaXQgZG9ja2VyVm9sdW1lQ3JlYXRlKG5hbWUsICh2YWwgfHwge306IGFueSkpO1xuICAgICAgICBpZiAodm9sdW1lKSB7XG4gICAgICAgICAgdHJhY2tlci52b2x1bWVzLnNldChuYW1lLCB2b2x1bWUpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfSksXG4gICk7XG59O1xuXG50eXBlIEhlYWx0aENoZWNrRm4gPSAoVXBSZXN1bHQpID0+IFByb21pc2U8dm9pZD47XG5cbnR5cGUgVXBPcHRpb25zID0ge1xuICBoZWFsdGhDaGVjaz86IEhlYWx0aENoZWNrRm4sXG4gIGF2b2lkQ29uZmxpY3RzPzogYm9vbGVhbixcbiAgbWFwVm9sdW1lcz86IGJvb2xlYW4sXG4gIG1hcFBvcnRzPzogYm9vbGVhbixcbiAgY21kPzogc3RyaW5nW10sXG4gIHRyYWNrZXI/OiBEb2NrZXJDb21wb3NlUmVzb3VyY2VUcmFja2VyLFxufTtcblxudHlwZSBTZXJ2aWNlTmFtZUluZm8gPSB7XG4gIG5hbWU6IHN0cmluZyxcbiAgYWxpYXNlczogc3RyaW5nW10sXG4gIHN1ZmZpeDogc3RyaW5nLFxufTtcblxudHlwZSBVcFJlc3VsdCA9IHt8XG4gIHNlcnZpY2U6IERvY2tlckNvbXBvc2VTZXJ2aWNlLFxuICBjb250YWluZXI6IERvY2tlckNvbnRhaW5lcixcbiAgY29udGFpbmVyTmFtZTogc3RyaW5nLFxuICBhbGlhc2VzOiBzdHJpbmdbXSxcbiAgcG9ydHM6IFBvcnRNYXBbXSxcbiAgdXJsczogVXJsTWFwW10sXG4gIHZvbHVtZXM6IHN0cmluZ1tdLFxufH07XG5cbmV4cG9ydCBjbGFzcyBEb2NrZXJDb21wb3NlU2VydmljZSB7XG4gICNuYW1lOiBzdHJpbmc7XG4gICNzdmNEZWY6IERvY2tlckNvbXBvc2VTZXJ2aWNlRGVmO1xuICAjZG9ja2VyQ29tcG9zZTogPyhEb2NrZXJDb21wb3NlIHwgc3RyaW5nKTtcbiAgI3RyYWNrZXI6IERvY2tlckNvbXBvc2VSZXNvdXJjZVRyYWNrZXIgPSBkb2NrZXJDb21wb3NlQ3JlYXRlUmVzb3VyY2VUcmFja2VyKCk7XG5cbiAgLy8gbGF6aWx5IGNvbXB1dGVkXG4gICNwYXJzZWRQb3J0czogP1BhcnNlZFBvcnRJbmZvID0gbnVsbDtcbiAgI3BhcnNlZE5ldHdvcmtzOiA/UGFyc2VkTmV0d29ya0luZm8gPSBudWxsO1xuICAjcGFyc2VkVm9sdW1lczogP1BhcnNlZFZvbHVtZUluZm8gPSBudWxsO1xuICAjYmFzZVJ1bkFyZ3M6ID8oc3RyaW5nW10pID0gbnVsbDtcblxuICBjb25zdHJ1Y3RvcihcbiAgICBuYW1lOiBzdHJpbmcsXG4gICAgc2VydmljZURlZjogRG9ja2VyQ29tcG9zZVNlcnZpY2VEZWYsXG4gICAgZG9ja2VyQ29tcG9zZT86ID8oRG9ja2VyQ29tcG9zZSB8IHN0cmluZyksXG4gICkge1xuICAgIHRoaXMuI25hbWUgPSBuYW1lO1xuICAgIHRoaXMuI3N2Y0RlZiA9IHNlcnZpY2VEZWY7XG4gICAgdGhpcy4jZG9ja2VyQ29tcG9zZSA9IGRvY2tlckNvbXBvc2UgfHwgbnVsbDtcbiAgfVxuXG4gIGdldCBuYW1lKCk6IHN0cmluZyB7XG4gICAgcmV0dXJuIHRoaXMuI25hbWU7XG4gIH1cblxuICBnZXQgc2VydmljZURlZigpOiBEb2NrZXJDb21wb3NlU2VydmljZURlZiB7XG4gICAgcmV0dXJuIHRoaXMuI3N2Y0RlZjtcbiAgfVxuXG4gIGdldCBpbWFnZSgpOiA/c3RyaW5nIHtcbiAgICByZXR1cm4gdGhpcy4jc3ZjRGVmLmltYWdlIHx8IG51bGw7XG4gIH1cblxuICBnZXQgZGVmYXVsdENvbnRhaW5lck5hbWUoKTogc3RyaW5nIHtcbiAgICByZXR1cm4gdGhpcy4jc3ZjRGVmLmNvbnRhaW5lcl9uYW1lIHx8IHRoaXMuI25hbWU7XG4gIH1cblxuICBnZXQgY21kKCk6IHN0cmluZ1tdIHtcbiAgICByZXR1cm4gdGhpcy4jc3ZjRGVmLmNvbW1hbmQgfHwgW107XG4gIH1cblxuICBnZXQgZW52QXJncygpOiBzdHJpbmdbXSB7XG4gICAgcmV0dXJuIHBhcnNlRW52KHRoaXMuI3N2Y0RlZi5lbnZpcm9ubWVudCk7XG4gIH1cblxuICAvKipcbiAgICogRmluZCAoYXZhaWxhYmxlKSBjb250YWluZXIgbmFtZSBhbmQgYWxpYXMoZXMpXG4gICAqIEBwYXJhbSB7Ym9vbGVhbn0gYXZvaWRDb25mbGljdHMgaWYgYHRydWVgLCBmaW5kIGEgY29udGFpbmVyIG5hbWUgdGhhdCBpcyB1bnVzZWRcbiAgICogQHBhcmFtIHtudW1iZXJ9IG1heCBtYXhpbXVtIG51bWJlciBvZiBuYW1lcyB0byB0cnlcbiAgICovXG4gIGFzeW5jIGdldE5hbWVzKFxuICAgIGF2b2lkQ29uZmxpY3RzPzogYm9vbGVhbiA9IGZhbHNlLFxuICAgIG1heD86IG51bWJlciA9IDEwMCxcbiAgKTogUHJvbWlzZTxTZXJ2aWNlTmFtZUluZm8+IHtcbiAgICAvKiBlc2xpbnQtZGlzYWJsZSBuby1hd2FpdC1pbi1sb29wICovXG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCBtYXg7IGkgKz0gMSkge1xuICAgICAgY29uc3Qgc3VmZml4ID0gaSA/IGAtJHtpfWAgOiAnJztcbiAgICAgIGNvbnN0IHRlc3ROYW1lID0gYCR7dGhpcy5kZWZhdWx0Q29udGFpbmVyTmFtZX0ke3N1ZmZpeH1gO1xuICAgICAgY29uc3QgY29udGFpbmVyID0gYXdhaXQgZG9ja2VyQ29udGFpbmVyRmluZCh0ZXN0TmFtZSwgeyBhbGw6IHRydWUgfSk7XG4gICAgICBpZiAoIWF2b2lkQ29uZmxpY3RzIHx8ICFjb250YWluZXIpIHtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICBuYW1lOiB0ZXN0TmFtZSxcbiAgICAgICAgICBhbGlhc2VzOiBbYCR7dGhpcy5uYW1lfSR7c3VmZml4fWBdLFxuICAgICAgICAgIHN1ZmZpeCxcbiAgICAgICAgfTtcbiAgICAgIH1cbiAgICB9XG4gICAgLyogZXNsaW50LWVuYWJsZSBuby1hd2FpdC1pbi1sb29wICovXG4gICAgdGhyb3cgbmV3IEVycm9yKFxuICAgICAgYEZhaWxlZCB0byBmaW5kIGF2YWlsYWJsZSBjb250YWluZXIgbmFtZSBmb3IgJHt0aGlzLmRlZmF1bHRDb250YWluZXJOYW1lfWAsXG4gICAgKTtcbiAgfVxuXG4gIC8vIEdldCAoYXZhaWxhYmxlKSBwb3J0IG1hcHBpbmdzXG4gIGFzeW5jIGdldFBvcnRzKFxuICAgIGF2b2lkQ29uZmxpY3RzPzogYm9vbGVhbiA9IGZhbHNlLFxuICAgIG1hcExvY2FsPzogYm9vbGVhbiA9IHRydWUsXG4gICk6IFByb21pc2U8UGFyc2VkUG9ydEluZm8+IHtcbiAgICByZXR1cm4gcGFyc2VQb3J0cyh0aGlzLiNzdmNEZWYucG9ydHMsIGF2b2lkQ29uZmxpY3RzLCBtYXBMb2NhbCk7XG4gIH1cblxuICBhc3luYyBnZXREZWZhdWx0UG9ydEluZm8oKTogUHJvbWlzZTxQYXJzZWRQb3J0SW5mbz4ge1xuICAgIGlmICghdGhpcy4jcGFyc2VkUG9ydHMpIHtcbiAgICAgIHRoaXMuI3BhcnNlZFBvcnRzID0gYXdhaXQgdGhpcy5nZXRQb3J0cygpO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcy4jcGFyc2VkUG9ydHM7XG4gIH1cblxuICBhc3luYyBnZXREZWZhdWx0UG9ydHMoKTogUHJvbWlzZTxQb3J0TWFwW10+IHtcbiAgICBjb25zdCB7IHBvcnRzIH0gPSBhd2FpdCB0aGlzLmdldERlZmF1bHRQb3J0SW5mbygpO1xuICAgIHJldHVybiBwb3J0cztcbiAgfVxuXG4gIGFzeW5jIGdldERlZmF1bHRQb3J0QXJncygpOiBQcm9taXNlPHN0cmluZ1tdPiB7XG4gICAgY29uc3QgeyBydW5BcmdzIH0gPSBhd2FpdCB0aGlzLmdldERlZmF1bHRQb3J0SW5mbygpO1xuICAgIHJldHVybiBydW5BcmdzO1xuICB9XG5cbiAgYXN5bmMgZ2V0RGVmYXVsdFVybHMoKTogUHJvbWlzZTxVcmxNYXBbXT4ge1xuICAgIHJldHVybiB0aGlzLmNvbnN0cnVjdG9yLmdldFVybHMoXG4gICAgICBhd2FpdCB0aGlzLmdldERlZmF1bHRQb3J0cygpLFxuICAgICAgdGhpcy5kZWZhdWx0Q29udGFpbmVyTmFtZSxcbiAgICApO1xuICB9XG5cbiAgYXN5bmMgZ2V0RGVmYXVsdE5ldHdvcmtJbmZvKCk6IFByb21pc2U8UGFyc2VkTmV0d29ya0luZm8+IHtcbiAgICBpZiAoIXRoaXMuI3BhcnNlZE5ldHdvcmtzKSB7XG4gICAgICB0aGlzLiNwYXJzZWROZXR3b3JrcyA9IGF3YWl0IHBhcnNlTmV0d29ya3ModGhpcy4jc3ZjRGVmLm5ldHdvcmtzKTtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXMuI3BhcnNlZE5ldHdvcmtzO1xuICB9XG5cbiAgYXN5bmMgZ2V0RGVmYXVsdE5ldHdvcmtzKCk6IFByb21pc2U8c3RyaW5nW10+IHtcbiAgICBjb25zdCB7IG5ldHdvcmtzIH0gPSBhd2FpdCB0aGlzLmdldERlZmF1bHROZXR3b3JrSW5mbygpO1xuICAgIHJldHVybiBuZXR3b3JrcztcbiAgfVxuXG4gIGFzeW5jIGdldERlZmF1bHROZXR3b3JrQXJncygpOiBQcm9taXNlPHN0cmluZ1tdPiB7XG4gICAgY29uc3QgeyBydW5BcmdzIH0gPSBhd2FpdCB0aGlzLmdldERlZmF1bHROZXR3b3JrSW5mbygpO1xuICAgIHJldHVybiBydW5BcmdzO1xuICB9XG5cbiAgYXN5bmMgZ2V0RGVmYXVsdFZvbHVtZUluZm8oKTogUHJvbWlzZTxQYXJzZWRWb2x1bWVJbmZvPiB7XG4gICAgaWYgKCF0aGlzLiNwYXJzZWRWb2x1bWVzKSB7XG4gICAgICB0aGlzLiNwYXJzZWRWb2x1bWVzID0gYXdhaXQgcGFyc2VWb2x1bWVzKHRoaXMuI3N2Y0RlZi5uZXR3b3Jrcyk7XG4gICAgfVxuICAgIHJldHVybiB0aGlzLiNwYXJzZWRWb2x1bWVzO1xuICB9XG5cbiAgYXN5bmMgZ2V0RGVmYXVsdFZvbHVtZXMoKTogUHJvbWlzZTxzdHJpbmdbXT4ge1xuICAgIGNvbnN0IHsgdm9sdW1lcyB9ID0gYXdhaXQgdGhpcy5nZXREZWZhdWx0Vm9sdW1lSW5mbygpO1xuICAgIHJldHVybiB2b2x1bWVzO1xuICB9XG5cbiAgYXN5bmMgZ2V0RGVmYXVsdFZvbHVtZUFyZ3MoKTogUHJvbWlzZTxzdHJpbmdbXT4ge1xuICAgIGNvbnN0IHsgcnVuQXJncyB9ID0gYXdhaXQgdGhpcy5nZXREZWZhdWx0Vm9sdW1lSW5mbygpO1xuICAgIHJldHVybiBydW5BcmdzO1xuICB9XG5cbiAgYXN5bmMgcHVsbCgpIHtcbiAgICBpZiAoIXRoaXMuaW1hZ2UpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgQ2Fubm90IHB1bGwgJyR7dGhpcy5uYW1lfScsIG5vIGltYWdlIGNvbmZpZ3VyZWQuYCk7XG4gICAgfVxuICAgIGF3YWl0IGRvY2tlclB1bGwoeyBpbWFnZTogdGhpcy5pbWFnZSB9KTtcbiAgfVxuXG4gIGFzeW5jIGdldEJhc2VSdW5BcmdzKCk6IFByb21pc2U8c3RyaW5nW10+IHtcbiAgICBpZiAoIXRoaXMuI2Jhc2VSdW5BcmdzKSB7XG4gICAgICBjb25zdCBlbnZBcmdzID0gcGFyc2VFbnYodGhpcy4jc3ZjRGVmLmVudmlyb25tZW50KTtcbiAgICAgIGNvbnN0IHVsQXJncyA9IHBhcnNlVUxpbWl0cyh0aGlzLiNzdmNEZWYudWxpbWl0cyk7XG4gICAgICBjb25zdCBuZXRBcmdzID0gYXdhaXQgdGhpcy5nZXREZWZhdWx0TmV0d29ya0FyZ3MoKTtcblxuICAgICAgdGhpcy4jYmFzZVJ1bkFyZ3MgPSBbJy0tcm0nLCAuLi5lbnZBcmdzLCAuLi5uZXRBcmdzLCAuLi51bEFyZ3NdO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcy4jYmFzZVJ1bkFyZ3M7XG4gIH1cblxuICBhc3luYyBhc3NlbWJsZVJ1bkFyZ3MoXG4gICAgY29udGFpbmVyTmFtZT86IHN0cmluZyA9IHRoaXMuZGVmYXVsdENvbnRhaW5lck5hbWUsXG4gICAgYWxpYXNlcz86IHN0cmluZ1tdID0gW3RoaXMubmFtZV0sXG4gICAgYWRkaXRpb25hbEFyZ3M/OiBzdHJpbmdbXSxcbiAgKTogUHJvbWlzZTxzdHJpbmdbXT4ge1xuICAgIGNvbnN0IGFkZGl0aW9uYWwgPSBhZGRpdGlvbmFsQXJncyB8fCBbXG4gICAgICAuLi4oYXdhaXQgdGhpcy5nZXREZWZhdWx0UG9ydEFyZ3MoKSksXG4gICAgICAuLi4oYXdhaXQgdGhpcy5nZXREZWZhdWx0Vm9sdW1lQXJncygpKSxcbiAgICBdO1xuICAgIHJldHVybiBbXG4gICAgICAuLi4oYXdhaXQgdGhpcy5nZXRCYXNlUnVuQXJncygpKSxcbiAgICAgIC4uLihjb250YWluZXJOYW1lID8gWyctLW5hbWUnLCBjb250YWluZXJOYW1lXSA6IFtdKSxcbiAgICAgIC4uLmFsaWFzZXMuZmxhdE1hcCgoYSkgPT4gKGEgPyBbJy0tbmV0d29yay1hbGlhcycsIGFdIDogW10pKSxcbiAgICAgIC4uLmFkZGl0aW9uYWwsXG4gICAgXTtcbiAgfVxuXG4gIGFzeW5jIGdldFJ1bkFyZ3MoXG4gICAgYXZvaWRDb25mbGljdHM/OiBib29sZWFuID0gZmFsc2UsXG4gICAgbWFwTG9jYWxQb3J0cz86IGJvb2xlYW4gPSB0cnVlLFxuICApOiBQcm9taXNlPHN0cmluZ1tdPiB7XG4gICAgY29uc3QgeyBuYW1lOiBjTmFtZSwgYWxpYXNlcywgc3VmZml4IH0gPSBhd2FpdCB0aGlzLmdldE5hbWVzKFxuICAgICAgYXZvaWRDb25mbGljdHMsXG4gICAgKTtcbiAgICBjb25zdCB7IHJ1bkFyZ3M6IHBBcmdzIH0gPSBhd2FpdCB0aGlzLmdldFBvcnRzKFxuICAgICAgYXZvaWRDb25mbGljdHMsXG4gICAgICBtYXBMb2NhbFBvcnRzLFxuICAgICk7XG4gICAgY29uc3QgeyBydW5BcmdzOiB2QXJncyB9ID0gYXdhaXQgcGFyc2VWb2x1bWVzKHRoaXMuI3N2Y0RlZi52b2x1bWVzLCBzdWZmaXgpO1xuICAgIHJldHVybiB0aGlzLmFzc2VtYmxlUnVuQXJncyhjTmFtZSwgYWxpYXNlcywgWy4uLnBBcmdzLCAuLi52QXJnc10pO1xuICB9XG5cbiAgYXN5bmMgdXAoe1xuICAgIGhlYWx0aENoZWNrLFxuICAgIGF2b2lkQ29uZmxpY3RzID0gZmFsc2UsXG4gICAgbWFwVm9sdW1lcyA9IHRydWUsXG4gICAgbWFwUG9ydHMgPSB0cnVlLFxuICAgIGNtZCA9IHRoaXMuY21kLFxuICAgIHRyYWNrZXIgPSBkZWZhdWx0VHJhY2tlcixcbiAgfTogVXBPcHRpb25zID0ge30pOiBQcm9taXNlPFVwUmVzdWx0PiB7XG4gICAgY29uc3QgeyBpbWFnZSB9ID0gdGhpcztcbiAgICBpZiAoIWltYWdlKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXG4gICAgICAgIGBDYW5ub3QgYnJpbmcgdXAgc2VydmljZSAnJHt0aGlzLm5hbWV9Jywgbm8gaW1hZ2UgZGVmaW5lZC5gLFxuICAgICAgKTtcbiAgICB9XG4gICAgaWYgKHRoaXMuI3RyYWNrZXIuY29udGFpbmVycy5zaXplKSB7XG4gICAgICBidWlsZExvZyhcbiAgICAgICAgYFdhcm5pbmc6IHVwIGNhbGxlZCBvbiBzZXJ2aWNlICcke3RoaXMubmFtZX0nIHdpdGggYWxyZWFkeSBydW5uaW5nIGNvbnRhaW5lcmAsXG4gICAgICApO1xuICAgIH1cbiAgICBjb25zdCB7IG5hbWU6IGNvbnRhaW5lck5hbWUsIGFsaWFzZXMsIHN1ZmZpeCB9ID0gYXdhaXQgdGhpcy5nZXROYW1lcyhcbiAgICAgIGF2b2lkQ29uZmxpY3RzLFxuICAgICk7XG4gICAgY29uc3QgeyBydW5BcmdzOiBwQXJncywgcG9ydHMgfSA9IGF3YWl0IHRoaXMuZ2V0UG9ydHMoXG4gICAgICBhdm9pZENvbmZsaWN0cyxcbiAgICAgIG1hcFBvcnRzLFxuICAgICk7XG4gICAgY29uc3QgeyBydW5BcmdzOiB2QXJncywgdm9sdW1lcyB9ID0gbWFwVm9sdW1lc1xuICAgICAgPyBhd2FpdCBwYXJzZVZvbHVtZXModGhpcy4jc3ZjRGVmLnZvbHVtZXMsIHN1ZmZpeClcbiAgICAgIDogeyBydW5BcmdzOiBbXSwgdm9sdW1lczogW10gfTtcblxuICAgIGxldCBjb250YWluZXIgPSBhd2FpdCBkb2NrZXJDb250YWluZXJGaW5kKGNvbnRhaW5lck5hbWUsIHsgYWxsOiB0cnVlIH0pO1xuICAgIGlmIChjb250YWluZXIgJiYgIShhd2FpdCBjb250YWluZXIuaXNSdW5uaW5nKCkpKSB7XG4gICAgICBhd2FpdCBjb250YWluZXIuc3RhcnQoKTtcbiAgICB9XG4gICAgaWYgKCFjb250YWluZXIpIHtcbiAgICAgIGF3YWl0IHRoaXMucHVsbCgpO1xuICAgICAgYXdhaXQgZG9ja2VyQ29tcG9zZUNyZWF0ZU5ldHdvcmtzKFxuICAgICAgICBhd2FpdCB0aGlzLmdldERlZmF1bHROZXR3b3JrcygpLFxuICAgICAgICB0aGlzLiNkb2NrZXJDb21wb3NlLFxuICAgICAgICB0aGlzLiN0cmFja2VyLFxuICAgICAgKTtcbiAgICAgIGF3YWl0IGRvY2tlckNvbXBvc2VDcmVhdGVWb2x1bWVzKFxuICAgICAgICB2b2x1bWVzLFxuICAgICAgICB0aGlzLiNkb2NrZXJDb21wb3NlLFxuICAgICAgICB0aGlzLiN0cmFja2VyLFxuICAgICAgKTtcbiAgICAgIGNvbnN0IHJ1bkFyZ3MgPSBhd2FpdCB0aGlzLmFzc2VtYmxlUnVuQXJncyhjb250YWluZXJOYW1lLCBhbGlhc2VzLCBbXG4gICAgICAgIC4uLnBBcmdzLFxuICAgICAgICAuLi52QXJncyxcbiAgICAgIF0pO1xuICAgICAgY29udGFpbmVyID0gYXdhaXQgZG9ja2VyQ29udGFpbmVyUnVuRGFlbW9uKHtcbiAgICAgICAgaW1hZ2UsXG4gICAgICAgIHJ1bkFyZ3MsXG4gICAgICAgIGNtZCxcbiAgICAgIH0pO1xuICAgIH0gZWxzZSB7XG4gICAgICBidWlsZExvZyhgUmV1c2luZyBleGlzdGluZyBjb250YWluZXIgZm9yICcke3RoaXMubmFtZX0nIHNlcnZpY2UuYCk7XG4gICAgfVxuICAgIC8vIFRoaXMgc2VydmljZSB0cmFja3MgdGhlIHRoaW5ncyBpdCBjcmVhdGVkXG4gICAgdGhpcy4jdHJhY2tlci5jb250YWluZXJzLnNldChjb250YWluZXJOYW1lLCBjb250YWluZXIpO1xuICAgIC8vIFRoZSBwYXNzZWQgdHJhY2tlciBuZWVkcyB0byB0cmFjayB0aGlzIHNlcnZpY2VcbiAgICB0cmFja2VyLnNlcnZpY2VzLnNldCh0aGlzLm5hbWUsIHRoaXMpO1xuXG4gICAgY29uc3QgaWRBbGlhcyA9IGNvbnRhaW5lci5pZC5zbGljZSgwLCAxMik7XG4gICAgYWxpYXNlcy5wdXNoKGlkQWxpYXMpO1xuICAgIGNvbnN0IHVybHMgPSB0aGlzLmNvbnN0cnVjdG9yLmdldFVybHMocG9ydHMsIGlkQWxpYXMpO1xuXG4gICAgY29uc3QgaW5mbzogVXBSZXN1bHQgPSB7XG4gICAgICBzZXJ2aWNlOiB0aGlzLFxuICAgICAgY29udGFpbmVyLFxuICAgICAgY29udGFpbmVyTmFtZSxcbiAgICAgIGFsaWFzZXMsXG4gICAgICBwb3J0cyxcbiAgICAgIHZvbHVtZXMsXG4gICAgICB1cmxzLFxuICAgIH07XG4gICAgYXdhaXQgaGVhbHRoQ2hlY2s/LihpbmZvKTtcbiAgICByZXR1cm4gaW5mbztcbiAgfVxuXG4gIGFzeW5jIGRvd24oe1xuICAgIGluY2x1ZGVEZWZhdWx0cyA9IGZhbHNlLFxuICAgIGluY2x1ZGVWb2x1bWVzID0gZmFsc2UsXG4gICAgaW5jbHVkZU5ldHdvcmtzID0gZmFsc2UsXG4gIH06IHtcbiAgICBpbmNsdWRlRGVmYXVsdHM/OiBib29sZWFuLFxuICAgIGluY2x1ZGVWb2x1bWVzPzogYm9vbGVhbixcbiAgICBpbmNsdWRlTmV0d29ya3M/OiBib29sZWFuLFxuICB9ID0ge30pIHtcbiAgICBidWlsZExvZyhgQnJpbmdpbmcgZG93biA8JHt0aGlzLm5hbWV9PiBzZXJ2aWNlLi4uYCk7XG4gICAgYXdhaXQgZG9ja2VyQ29tcG9zZVRlYXJkb3duKHtcbiAgICAgIHRyYWNrZXI6IHRoaXMuI3RyYWNrZXIsXG4gICAgICBpbmNsdWRlVm9sdW1lcyxcbiAgICAgIGluY2x1ZGVOZXR3b3JrcyxcbiAgICB9KTtcbiAgICBpZiAoaW5jbHVkZURlZmF1bHRzKSB7XG4gICAgICBjb25zdCBjb250YWluZXIgPSBhd2FpdCBkb2NrZXJDb250YWluZXJGaW5kKHRoaXMuZGVmYXVsdENvbnRhaW5lck5hbWUpO1xuICAgICAgaWYgKGNvbnRhaW5lcikge1xuICAgICAgICBhd2FpdCBjb250YWluZXIudGVhcmRvd24odHJ1ZSk7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgc3RhdGljIGFzeW5jIHBhcnNlKFxuICAgIG5hbWU6IHN0cmluZyxcbiAgICBmb3JjZT86IGJvb2xlYW4gPSB0cnVlLFxuICAgIGRvY2tlckNvbXBvc2U/OiA/KERvY2tlckNvbXBvc2UgfCBzdHJpbmcpLFxuICApOiBQcm9taXNlPD9Eb2NrZXJDb21wb3NlU2VydmljZT4ge1xuICAgIGNvbnN0IHN2Y0RlZiA9IGF3YWl0IGdldFNlcnZpY2VEZWYobmFtZSwgZm9yY2UsIGRvY2tlckNvbXBvc2UpO1xuICAgIHJldHVybiBzdmNEZWYgPyBuZXcgdGhpcyhuYW1lLCBzdmNEZWYsIGRvY2tlckNvbXBvc2UpIDogbnVsbDtcbiAgfVxuXG4gIHN0YXRpYyBnZXRVcmxzKHBvcnRzOiBQb3J0TWFwW10sIGFsaWFzOiBzdHJpbmcpOiBVcmxNYXBbXSB7XG4gICAgcmV0dXJuIHBvcnRzLm1hcCgoeyBsb2NhbCwgZG9ja2VyIH0pID0+ICh7XG4gICAgICBsb2NhbDogbG9jYWwgPyBgaHR0cDovL2xvY2FsaG9zdDoke2xvY2FsfWAgOiBudWxsLFxuICAgICAgZG9ja2VyOiBkb2NrZXIgPyBgaHR0cDovLyR7YWxpYXN9OiR7ZG9ja2VyfWAgOiBudWxsLFxuICAgIH0pKTtcbiAgfVxufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZG9ja2VyQ29tcG9zZUdldEFsbFNlcnZpY2VzKFxuICBkb2NrZXJDb21wb3NlPzogPyhzdHJpbmcgfCBEb2NrZXJDb21wb3NlKSxcbik6IFByb21pc2U8TWFwT2JqPHN0cmluZywgRG9ja2VyQ29tcG9zZVNlcnZpY2U+PiB7XG4gIGNvbnN0IHsgc2VydmljZXMgfSA9IGF3YWl0IGRvY2tlckNvbXBvc2VSZXNvbHZlKGRvY2tlckNvbXBvc2UpO1xuICByZXR1cm4gbWFwVmFsdWVzQXN5bmMoc2VydmljZXMsIChzLCBuYW1lKSA9PlxuICAgIERvY2tlckNvbXBvc2VTZXJ2aWNlLnBhcnNlKG5hbWUpLFxuICApO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZG9ja2VyQ29tcG9zZVRlYXJkb3duKHtcbiAgaW5jbHVkZURlZmF1bHRzID0gZmFsc2UsXG4gIGluY2x1ZGVWb2x1bWVzID0gZmFsc2UsXG4gIGluY2x1ZGVOZXR3b3JrcyA9IGZhbHNlLFxuICBkb2NrZXJDb21wb3NlLFxuICB0cmFja2VyID0gZGVmYXVsdFRyYWNrZXIsXG59OiB7XG4gIGluY2x1ZGVEZWZhdWx0cz86IGJvb2xlYW4sXG4gIGluY2x1ZGVWb2x1bWVzPzogYm9vbGVhbixcbiAgaW5jbHVkZU5ldHdvcmtzPzogYm9vbGVhbixcbiAgZG9ja2VyQ29tcG9zZT86ID8oc3RyaW5nIHwgRG9ja2VyQ29tcG9zZSksXG4gIHRyYWNrZXI/OiBEb2NrZXJDb21wb3NlUmVzb3VyY2VUcmFja2VyLFxufSA9IHt9KTogUHJvbWlzZTx2b2lkPiB7XG4gIGlmICghdHJhY2tlci5jbGVhbmluZykge1xuICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBuby1wYXJhbS1yZWFzc2lnblxuICAgIHRyYWNrZXIuY2xlYW5pbmcgPSAoYXN5bmMgKCkgPT4ge1xuICAgICAgaWYgKHRyYWNrZXIuc2VydmljZXMuc2l6ZSkge1xuICAgICAgICBidWlsZExvZygnQnJpbmdpbmcgZG93biBzdGFydGVkIGRvY2tlciBzZXJ2aWNlcy4uLicpO1xuICAgICAgICBjb25zdCBwcm9taXNlcyA9IFByb21pc2UuYWxsKFxuICAgICAgICAgIEFycmF5LmZyb20odHJhY2tlci5zZXJ2aWNlcy52YWx1ZXMoKSkubWFwKGFzeW5jIChzKSA9PlxuICAgICAgICAgICAgcy5kb3duKHsgaW5jbHVkZVZvbHVtZXMsIGluY2x1ZGVOZXR3b3JrcyB9KSxcbiAgICAgICAgICApLFxuICAgICAgICApO1xuICAgICAgICB0cmFja2VyLnNlcnZpY2VzLmNsZWFyKCk7XG4gICAgICAgIGF3YWl0IHByb21pc2VzO1xuICAgICAgfVxuICAgICAgaWYgKGluY2x1ZGVEZWZhdWx0cykge1xuICAgICAgICBjb25zdCB7IHNlcnZpY2VzIH0gPSBhd2FpdCBkb2NrZXJDb21wb3NlUmVzb2x2ZShkb2NrZXJDb21wb3NlKTtcbiAgICAgICAgY29uc3Qgc3ZjTmFtZXMgPSBrZXlzKHNlcnZpY2VzKTtcbiAgICAgICAgaWYgKHN2Y05hbWVzLmxlbmd0aCkge1xuICAgICAgICAgIGJ1aWxkTG9nKCdCcmluZ2luZyBkb3duIGRlZmF1bHQgZG9ja2VyIHNlcnZpY2VzLi4uJyk7XG4gICAgICAgICAgYXdhaXQgUHJvbWlzZS5hbGwoXG4gICAgICAgICAgICBzdmNOYW1lcy5tYXAoYXN5bmMgKHMpID0+XG4gICAgICAgICAgICAgIChhd2FpdCBEb2NrZXJDb21wb3NlU2VydmljZS5wYXJzZShzKSk/LmRvd24oe1xuICAgICAgICAgICAgICAgIGluY2x1ZGVEZWZhdWx0cyxcbiAgICAgICAgICAgICAgICBpbmNsdWRlVm9sdW1lcyxcbiAgICAgICAgICAgICAgICBpbmNsdWRlTmV0d29ya3MsXG4gICAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgKSxcbiAgICAgICAgICApO1xuICAgICAgICB9XG4gICAgICB9XG5cbiAgICAgIGlmICh0cmFja2VyLmNvbnRhaW5lcnMuc2l6ZSkge1xuICAgICAgICBidWlsZExvZygnU3RvcHBpbmcgY3JlYXRlZCBkb2NrZXIgY29udGFpbmVycy4uLicpO1xuICAgICAgICBjb25zdCBwcm9taXNlcyA9IFByb21pc2UuYWxsKFxuICAgICAgICAgIEFycmF5LmZyb20odHJhY2tlci5jb250YWluZXJzLnZhbHVlcygpKS5tYXAoYXN5bmMgKGMpID0+XG4gICAgICAgICAgICBjLnRlYXJkb3duKHRydWUpLFxuICAgICAgICAgICksXG4gICAgICAgICk7XG4gICAgICAgIHRyYWNrZXIuY29udGFpbmVycy5jbGVhcigpO1xuICAgICAgICBhd2FpdCBwcm9taXNlcztcbiAgICAgIH1cblxuICAgICAgaWYgKGluY2x1ZGVWb2x1bWVzKSB7XG4gICAgICAgIGlmICh0cmFja2VyLnZvbHVtZXMuc2l6ZSkge1xuICAgICAgICAgIGJ1aWxkTG9nKCdSZW1vdmluZyBjcmVhdGVkIGRvY2tlciB2b2x1bWVzLi4uJyk7XG4gICAgICAgICAgY29uc3QgcHJvbWlzZXMgPSBQcm9taXNlLmFsbChcbiAgICAgICAgICAgIEFycmF5LmZyb20odHJhY2tlci52b2x1bWVzLnZhbHVlcygpKS5tYXAoYXN5bmMgKHYpID0+IHYucm0oKSksXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0cmFja2VyLnZvbHVtZXMuY2xlYXIoKTtcbiAgICAgICAgICBhd2FpdCBwcm9taXNlcztcbiAgICAgICAgfVxuICAgICAgICBpZiAoaW5jbHVkZURlZmF1bHRzKSB7XG4gICAgICAgICAgYnVpbGRMb2coJ1JlbW92aW5nIGRlZmF1bHQgZG9ja2VyIHZvbHVtZXMuLi4nKTtcbiAgICAgICAgICBjb25zdCB7IHZvbHVtZXMgfSA9IGF3YWl0IGRvY2tlckNvbXBvc2VSZXNvbHZlKGRvY2tlckNvbXBvc2UpO1xuICAgICAgICAgIGF3YWl0IFByb21pc2UuYWxsKFxuICAgICAgICAgICAgZW50cmllcyh2b2x1bWVzKS5tYXAoYXN5bmMgKFtrZXksIHZhbF0pID0+IHtcbiAgICAgICAgICAgICAgY29uc3QgbmFtZSA9IHZhbD8ubmFtZSB8fCBwcmVmaXhOYW1lKGtleSk7XG4gICAgICAgICAgICAgIGF3YWl0IGRvY2tlclZvbHVtZVJtKG5hbWUsIHRydWUpO1xuICAgICAgICAgICAgfSksXG4gICAgICAgICAgKTtcbiAgICAgICAgfVxuICAgICAgfVxuXG4gICAgICBpZiAoaW5jbHVkZU5ldHdvcmtzKSB7XG4gICAgICAgIGlmICh0cmFja2VyLm5ldHdvcmtzLnNpemUpIHtcbiAgICAgICAgICBidWlsZExvZygnUmVtb3ZpbmcgY3JlYXRlZCBkb2NrZXIgbmV0d29ya3MuLi4nKTtcbiAgICAgICAgICBjb25zdCBwcm9taXNlcyA9IFByb21pc2UuYWxsKFxuICAgICAgICAgICAgQXJyYXkuZnJvbSh0cmFja2VyLm5ldHdvcmtzLnZhbHVlcygpKS5tYXAoYXN5bmMgKG4pID0+IG4ucm0oKSksXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0cmFja2VyLm5ldHdvcmtzLmNsZWFyKCk7XG4gICAgICAgICAgYXdhaXQgcHJvbWlzZXM7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGluY2x1ZGVEZWZhdWx0cykge1xuICAgICAgICAgIGJ1aWxkTG9nKCdSZW1vdmluZyBkZWZhdWx0IGRvY2tlciBuZXR3b3Jrcy4uLicpO1xuICAgICAgICAgIGNvbnN0IHsgbmV0d29ya3MgfSA9IGF3YWl0IGRvY2tlckNvbXBvc2VSZXNvbHZlKGRvY2tlckNvbXBvc2UpO1xuICAgICAgICAgIGF3YWl0IFByb21pc2UuYWxsKFxuICAgICAgICAgICAgZW50cmllcyhuZXR3b3JrcykubWFwKGFzeW5jIChba2V5LCB2YWxdKSA9PiB7XG4gICAgICAgICAgICAgIGNvbnN0IG5hbWUgPSB2YWw/Lm5hbWUgfHwgcHJlZml4TmFtZShrZXkpO1xuICAgICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgIGF3YWl0IGRvY2tlck5ldHdvcmtEZWxldGUobmFtZSk7XG4gICAgICAgICAgICAgIH0gY2F0Y2ggKGVycikge1xuICAgICAgICAgICAgICAgIGJ1aWxkTG9nKGBFcnJvciBkZWxldGluZyBuZXR3b3JrICcke25hbWV9JzogJHtlcnIubWVzc2FnZX1gKTtcbiAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSksXG4gICAgICAgICAgKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIG5vLXBhcmFtLXJlYXNzaWduXG4gICAgICB0cmFja2VyLmNsZWFuaW5nID0gbnVsbDtcbiAgICB9KSgpO1xuICB9XG4gIHJldHVybiB0cmFja2VyLmNsZWFuaW5nO1xufVxuXG5leHBvcnQgdHlwZSBEb2NrZXJDb250YWluZXJJbmZvID0ge3xcbiAgLi4uVXBSZXN1bHQsXG4gIGlkOiBzdHJpbmcsXG4gIGltYWdlOiBzdHJpbmcsXG4gIG5hbWU/OiA/c3RyaW5nLFxuXG4gIC8vIGZvciBjb252ZW5pZW5jZSwgdGhlIGZpcnN0IHBvcnQgbWFwcGluZyBpbmZvXG4gIHBvcnQ/OiA/bnVtYmVyLFxuICBkb2NrZXJQb3J0PzogP251bWJlcixcbiAgdXJsPzogP3N0cmluZyxcbiAgZG9ja2VyVXJsPzogP3N0cmluZyxcbnx9O1xuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gZG9ja2VyQ29tcG9zZVJ1blNlcnZpY2UoXG4gIGtleTogc3RyaW5nLFxuICB1cE9wdGlvbnM/OiBVcE9wdGlvbnMgPSB7fSxcbiAgZG9ja2VyQ29tcG9zZT86ID8oc3RyaW5nIHwgRG9ja2VyQ29tcG9zZSksXG4pOiBQcm9taXNlPERvY2tlckNvbnRhaW5lckluZm8+IHtcbiAgY29uc3Qgc2VydmljZTogP0RvY2tlckNvbXBvc2VTZXJ2aWNlID0gYXdhaXQgRG9ja2VyQ29tcG9zZVNlcnZpY2UucGFyc2UoXG4gICAga2V5LFxuICAgIGZhbHNlLFxuICAgIGRvY2tlckNvbXBvc2UsXG4gICk7XG4gIGlmICghc2VydmljZSkge1xuICAgIHRocm93IG5ldyBFcnJvcihgRmFpbGVkIHRvIGZpbmQgc2VydmljZSAnJHtrZXl9J2ApO1xuICB9XG4gIGJ1aWxkTG9nKGBTdGFydGluZyA8JHtzZXJ2aWNlLm5hbWV9PiBzZXJ2aWNlLi4uYCk7XG4gIGNvbnN0IHVwUmVzdWx0OiBVcFJlc3VsdCA9IGF3YWl0IHNlcnZpY2UudXAodXBPcHRpb25zKTtcbiAgY29uc3Qge1xuICAgIGNvbnRhaW5lcixcbiAgICB1cmxzLFxuICAgIHVybHM6IFt7IGxvY2FsOiB1cmwsIGRvY2tlcjogZG9ja2VyVXJsIH1dLFxuICAgIHBvcnRzOiBbeyBsb2NhbDogcG9ydCwgZG9ja2VyOiBkb2NrZXJQb3J0IH1dLFxuICB9ID0gdXBSZXN1bHQ7XG4gIGNvbnN0IHsgaWQsIG5hbWUsIGltYWdlIH0gPSBjb250YWluZXI7XG4gIHVybHMuZm9yRWFjaChcbiAgICAoeyBsb2NhbCB9KSA9PlxuICAgICAgbG9jYWwgJiYgYnVpbGRMb2coYDwke3NlcnZpY2UubmFtZX0+IGFjY2Vzc2libGUgYXQgJHtsb2NhbH1gKSxcbiAgKTtcbiAgcmV0dXJuIHtcbiAgICAuLi51cFJlc3VsdCxcbiAgICBpZCxcbiAgICBpbWFnZSxcbiAgICBuYW1lLFxuICAgIHBvcnQsXG4gICAgZG9ja2VyUG9ydCxcbiAgICB1cmwsXG4gICAgZG9ja2VyVXJsLFxuICB9O1xufVxuIl19