UNPKG

8.21 kBJavaScriptView Raw
1"use strict";
2var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3 if (k2 === undefined) k2 = k;
4 Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });
5}) : (function(o, m, k, k2) {
6 if (k2 === undefined) k2 = k;
7 o[k2] = m[k];
8}));
9var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
10 Object.defineProperty(o, "default", { enumerable: true, value: v });
11}) : function(o, v) {
12 o["default"] = v;
13});
14var __importStar = (this && this.__importStar) || function (mod) {
15 if (mod && mod.__esModule) return mod;
16 var result = {};
17 if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
18 __setModuleDefault(result, mod);
19 return result;
20};
21var __importDefault = (this && this.__importDefault) || function (mod) {
22 return (mod && mod.__esModule) ? mod : { "default": mod };
23};
24Object.defineProperty(exports, "__esModule", { value: true });
25exports.runTests = void 0;
26const utils_1 = require("@terascope/utils");
27const misc_1 = require("../misc");
28const services_1 = require("./services");
29const scripts_1 = require("../scripts");
30const utils = __importStar(require("./utils"));
31const signale_1 = __importDefault(require("../signale"));
32const packages_1 = require("../packages");
33const utils_2 = require("../publish/utils");
34const tracker_1 = require("./tracker");
35const logger = utils_1.debugLogger('ts-scripts:cmd:test');
36async function runTests(pkgInfos, options) {
37 const tracker = new tracker_1.TestTracker(options);
38 logger.info('running tests with options', options);
39 try {
40 await _runTests(pkgInfos, options, tracker);
41 }
42 catch (err) {
43 tracker.addError(err);
44 }
45 finally {
46 tracker.finish();
47 }
48}
49exports.runTests = runTests;
50async function _runTests(pkgInfos, options, tracker) {
51 var _a;
52 if ((_a = options.suite) === null || _a === void 0 ? void 0 : _a.includes('e2e')) {
53 await runE2ETest(options, tracker);
54 return;
55 }
56 const filtered = utils.filterBySuite(pkgInfos, options);
57 if (!filtered.length) {
58 signale_1.default.warn('No tests found.');
59 return;
60 }
61 const availableSuites = misc_1.getAvailableTestSuites();
62 const grouped = utils.groupBySuite(filtered, availableSuites, options);
63 for (const [suite, pkgs] of Object.entries(grouped)) {
64 if (!pkgs.length || suite === 'e2e')
65 continue;
66 try {
67 await runTestSuite(suite, pkgs, options, tracker);
68 if (tracker.hasErrors()) {
69 if (options.bail || utils_1.isCI) {
70 break;
71 }
72 }
73 }
74 catch (err) {
75 tracker.addError(err);
76 break;
77 }
78 }
79}
80async function runTestSuite(suite, pkgInfos, options, tracker) {
81 if (suite === 'e2e')
82 return;
83 // jest or our tests have a memory leak, limiting this seems to help
84 const MAX_CHUNK_SIZE = utils_1.isCI ? 7 : 10;
85 const CHUNK_SIZE = options.debug ? 1 : MAX_CHUNK_SIZE;
86 if (options.watch && pkgInfos.length > MAX_CHUNK_SIZE) {
87 throw new Error(`Running more than ${MAX_CHUNK_SIZE} packages will cause memory leaks`);
88 }
89 tracker.expected += pkgInfos.length;
90 const chunked = utils_1.chunk(pkgInfos, CHUNK_SIZE);
91 // don't log unless this useful information (more than one package)
92 if (chunked.length > 1 && chunked[0].length > 1) {
93 misc_1.writeHeader(`Running test suite "${suite}"`, false);
94 }
95 const cleanupKeys = [`${suite}:services`];
96 tracker.addCleanup(`${suite}:services`, await services_1.ensureServices(options.forceSuite || suite, options));
97 const timeLabel = `test suite "${suite}"`;
98 signale_1.default.time(timeLabel);
99 const env = printAndGetEnv(suite, options);
100 let chunkIndex = -1;
101 for (const pkgs of chunked) {
102 chunkIndex++;
103 if (!pkgs.length)
104 continue;
105 if (pkgs.length === 1) {
106 misc_1.writePkgHeader('Running test', pkgs, false);
107 }
108 else {
109 misc_1.writeHeader(`Running batch of ${pkgs.length} tests`, false);
110 }
111 const args = utils.getArgs(options);
112 args.projects = pkgs.map((pkgInfo) => pkgInfo.relativeDir);
113 tracker.started += pkgs.length;
114 try {
115 await scripts_1.runJest(misc_1.getRootDir(), args, env, options.jestArgs, options.debug);
116 tracker.ended += pkgs.length;
117 }
118 catch (err) {
119 tracker.ended += pkgs.length;
120 tracker.addError(err.message);
121 const teardownPkgs = pkgs.map((pkg) => ({
122 name: pkg.name,
123 dir: pkg.dir,
124 suite: pkg.terascope.testSuite
125 }));
126 const cleanupKey = `${suite}:teardown:${pkgs.map((pkg) => pkg.folderName).join(',')}`;
127 cleanupKeys.push(cleanupKey);
128 tracker.addCleanup(cleanupKey, async () => {
129 options.keepOpen = false;
130 await utils.globalTeardown(options, teardownPkgs);
131 });
132 if (options.bail || utils_1.isCI) {
133 signale_1.default.error('Bailing out of tests due to error');
134 break;
135 }
136 }
137 finally {
138 if (options.reportCoverage) {
139 await utils.reportCoverage(suite, chunkIndex);
140 }
141 }
142 }
143 if (!options.keepOpen) {
144 await utils_1.pMap(cleanupKeys, (key) => tracker.runCleanupByKey(key));
145 }
146 signale_1.default.timeEnd(timeLabel);
147}
148async function runE2ETest(options, tracker) {
149 tracker.expected++;
150 const suite = 'e2e';
151 let startedTest = false;
152 const e2eDir = packages_1.getE2EDir();
153 if (!e2eDir) {
154 throw new Error('Missing e2e test directory');
155 }
156 const rootInfo = misc_1.getRootInfo();
157 const [registry] = rootInfo.terascope.docker.registries;
158 const e2eImage = `${registry}:e2e`;
159 if (utils_1.isCI) {
160 // pull the services first in CI
161 await services_1.pullServices(suite, options);
162 }
163 try {
164 const devImage = await utils_2.buildDevDockerImage();
165 await scripts_1.dockerTag(devImage, e2eImage);
166 }
167 catch (err) {
168 tracker.addError(err);
169 }
170 try {
171 tracker.addCleanup('e2e:services', await services_1.ensureServices(suite, options));
172 }
173 catch (err) {
174 tracker.addError(err);
175 }
176 if (!tracker.hasErrors()) {
177 const timeLabel = `test suite "${suite}"`;
178 signale_1.default.time(timeLabel);
179 startedTest = true;
180 const env = printAndGetEnv(suite, options);
181 tracker.started++;
182 try {
183 await scripts_1.runJest(e2eDir, utils.getArgs(options), env, options.jestArgs, options.debug);
184 tracker.ended++;
185 }
186 catch (err) {
187 tracker.ended++;
188 tracker.addError(err.message);
189 }
190 signale_1.default.timeEnd(timeLabel);
191 }
192 if (!startedTest)
193 return;
194 if (!options.keepOpen) {
195 try {
196 await utils.logE2E(e2eDir, tracker.hasErrors());
197 }
198 catch (err) {
199 signale_1.default.error(new utils_1.TSError(err, {
200 reason: `Writing the "${suite}" logs failed`,
201 }));
202 }
203 }
204 if (tracker.hasErrors()) {
205 tracker.addCleanup('e2e:teardown', async () => {
206 options.keepOpen = false;
207 await utils.globalTeardown(options, [{
208 name: suite,
209 dir: e2eDir,
210 suite,
211 }]);
212 });
213 }
214}
215function printAndGetEnv(suite, options) {
216 const env = utils.getEnv(options, suite);
217 if (options.debug || options.trace || utils_1.isCI) {
218 const envStr = Object
219 .entries(env)
220 .filter(([_, val]) => val != null && val !== '')
221 .map(([key, val]) => `${key}: "${val}"`)
222 .join(', ');
223 signale_1.default.debug(`Setting ${suite} test suite env to ${envStr}`);
224 }
225 return env;
226}
227//# sourceMappingURL=index.js.map
\No newline at end of file