@testomatio/reporter 1.1.1-beta.1.fix-logger → 1.1.1-file-upload.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -65,13 +65,16 @@ yarn add @testomatio/reporter --dev
65
65
 
66
66
  ### 1️⃣ Attach Reporter to the Test Runner
67
67
 
68
+ | | | |
69
+ |--|--|--|
68
70
  | [Playwright](./docs/frameworks.md#playwright) | [CodeceptJS](./docs/frameworks.md#CodeceptJS) | [Cypress](./docs/frameworks.md#Cypress) |
69
71
  | [Jest](./docs/frameworks.md#Jest) | [Mocha](./docs/frameworks.md#Mocha) | [WebDriverIO](./docs/frameworks.md#WebDriverIO) |
70
72
  | [TestCafe](./docs/frameworks.md#TestCafe) | [Detox](./docs/frameworks.md#Detox) | [Codeception](https://github.com/testomatio/php-reporter) |
71
73
  | [Newman (Postman)](./docs/frameworks.md#Newman) | [JUnit](./docs/junit.md#junit) | [NUnit](./docs/junit.md#nunit) |
72
74
  | [PyTest](./docs/junit.md#pytest) | [PHPUnit](./docs/junit.md#phpunit) | [Protractor](./docs/frameworks.md#protractor) |
73
75
 
74
- or any [other via JUnit](./docs/junit.md) report....
76
+
77
+ or **any [other via JUnit](./docs/junit.md)** report....
75
78
 
76
79
  ### 2️⃣ Configure Reports
77
80
 
@@ -17,11 +17,12 @@ class PlaywrightReporter {
17
17
  this.uploads = [];
18
18
  }
19
19
 
20
- onBegin(_config, suite) {
20
+ onBegin(config, suite) {
21
21
  // clean data storage
22
22
  fileSystem.clearDir(TESTOMAT_TMP_STORAGE_DIR);
23
23
  if (!this.client) return;
24
24
  this.suite = suite;
25
+ this.config = config;
25
26
  this.client.createRun();
26
27
  }
27
28
 
@@ -73,7 +74,24 @@ class PlaywrightReporter {
73
74
  reportTestPromises.push(reportTestPromise);
74
75
  }
75
76
 
76
- async onEnd(result) {
77
+
78
+ #getArtifactPath(artifact) {
79
+ if (artifact.path) {
80
+ if (path.isAbsolute(artifact.path)) return artifact.path;
81
+
82
+ return path.join(this.config.outputDir || this.config.projects[0].outputDir, artifact.path);
83
+ }
84
+
85
+ if (artifact.body) {
86
+ const fileName = tmpFile();
87
+ fs.writeFileSync(fileName, artifact.body);
88
+ return fileName;
89
+ }
90
+
91
+ return null;
92
+ }
93
+
94
+ async onEnd(result, config) {
77
95
  if (!this.client) return;
78
96
 
79
97
  await Promise.all(reportTestPromises);
@@ -87,11 +105,7 @@ class PlaywrightReporter {
87
105
  const { title, testId, suite_title } = upload;
88
106
 
89
107
  const files = upload.files.map(attachment => {
90
- if (attachment.body) {
91
- const fileName = tmpFile();
92
- fs.writeFileSync(fileName, attachment.body);
93
- }
94
- return { path: attachment.path, title, type: attachment.contentType };
108
+ return { path: this.#getArtifactPath(attachment), title, type: attachment.contentType };
95
109
  });
96
110
 
97
111
  promises.push(
@@ -151,7 +165,7 @@ function initPlaywrightForStorage() {
151
165
  });
152
166
  } catch (e) {
153
167
  // ignore
154
- }
168
+ }
155
169
  }
156
170
 
157
171
  module.exports = PlaywrightReporter;
package/lib/client.js CHANGED
@@ -27,6 +27,7 @@ class Client {
27
27
  this.pipes = pipesFactory(params, store);
28
28
  this.queue = Promise.resolve();
29
29
  this.totalUploaded = 0;
30
+ this.failedToUpload = 0;
30
31
  this.version = JSON.parse(fs.readFileSync(join(__dirname, '..', 'package.json')).toString()).version;
31
32
  this.executionList = Promise.resolve();
32
33
 
@@ -163,11 +164,14 @@ class Client {
163
164
  uploadedFiles.push(upload.uploadFileAsBuffer(buffer, fileName, this.uuid));
164
165
  }
165
166
 
166
- const artifacts = await Promise.all(uploadedFiles);
167
+ const artifacts = (await Promise.all(uploadedFiles)).filter(n => !!n);
167
168
 
168
- // global.testomatioArtifacts = [];
169
+ if (artifacts.length < uploadedFiles.length) {
170
+ const failedUploading = uploadedFiles.length - artifacts.length;
171
+ this.failedToUpload += failedUploading;
172
+ }
169
173
 
170
- this.totalUploaded += uploadedFiles.filter(n => n).length;
174
+ this.totalUploaded += artifacts.length;
171
175
 
172
176
  const data = {
173
177
  files,
@@ -233,6 +237,16 @@ class Client {
233
237
  process.env.TESTOMATIO_PRIVATE_ARTIFACTS ? 'privately' : chalk.bold('publicly')
234
238
  } uploaded to S3 bucket`,
235
239
  );
240
+
241
+ if (this.failedToUpload > 0) {
242
+ console.log(
243
+ APP_PREFIX,
244
+ chalk.yellow(
245
+ `Some artifacts were not uploaded. ${this.failedToUpload} artifacts could not be uploaded. Run tests with DEBUG="@testomatio/reporter:file-uploader" to see details"`,
246
+ ),
247
+ );
248
+ }
249
+
236
250
  }
237
251
  })
238
252
  .catch(err => console.log(APP_PREFIX, err));
@@ -295,6 +309,7 @@ class Client {
295
309
 
296
310
  function isNotInternalFrame(frame) {
297
311
  return (
312
+ frame.getFileName() &&
298
313
  frame.getFileName().includes(sep) &&
299
314
  !frame.getFileName().includes('node_modules') &&
300
315
  !frame.getFileName().includes('internal')
@@ -11,7 +11,6 @@ const readFile = util.promisify(fs.readFile);
11
11
  const stat = util.promisify(fs.stat);
12
12
  const chalk = require('chalk');
13
13
  const { randomUUID } = require('crypto');
14
- const memoize = require('lodash.memoize');
15
14
 
16
15
  const { APP_PREFIX } = require('./constants');
17
16
 
@@ -146,8 +145,13 @@ const uploadUsingS3 = async (filePath, runId) => {
146
145
  params
147
146
  });
148
147
 
149
- return await getS3LocationLink(out);
150
- }
148
+
149
+ const link = await getS3LocationLink(out);
150
+
151
+ debug(`Succesfully uploaded ${filePath} => ${S3_BUCKET}/${Key} | URL: ${link}`);
152
+
153
+ return link;
154
+ }
151
155
  catch (e) {
152
156
  debug('S3 file uploading error: ', e);
153
157
 
@@ -279,8 +283,6 @@ const getS3LocationLink = async (out) => {
279
283
 
280
284
  let s3Location = response?.Location;
281
285
 
282
- debug('Uploaded response.Location', s3Location);
283
-
284
286
  if (!s3Location) {
285
287
  // TODO: out: a fallback case - remove after deeper testing
286
288
  s3Location = out?.singleUploadResult?.Location;
@@ -295,8 +297,8 @@ const getS3LocationLink = async (out) => {
295
297
  };
296
298
 
297
299
  module.exports = {
298
- uploadFileByPath: memoize(uploadFileByPath),
299
- uploadFileAsBuffer: memoize(uploadFileAsBuffer),
300
+ uploadFileByPath,
301
+ uploadFileAsBuffer,
300
302
  isArtifactsEnabled,
301
303
  resetConfig,
302
304
  };
@@ -19,7 +19,7 @@ function saveArtifact(data, context = null) {
19
19
  * @param {...any} args
20
20
  */
21
21
  function logMessage(...args) {
22
- services.logger._templateLiteralLog(...args);
22
+ services.logger.templateLiteralLog(...args);
23
23
  }
24
24
 
25
25
  /**
package/lib/reporter.js CHANGED
@@ -1,19 +1,19 @@
1
1
  const TestomatClient = require('./client');
2
2
  const TRConstants = require('./constants');
3
- const { services } = require('./services');
4
3
 
5
4
  const reporterFunctions = require('./reporter-functions');
6
5
 
7
6
  module.exports = {
8
7
  // TODO: deprecate in future; use log or testomat.log
9
- testomatioLogger: services.logger,
8
+ logger: reporterFunctions.log,
9
+ testomatioLogger: reporterFunctions.log,
10
10
 
11
11
  artifact: reporterFunctions.artifact,
12
12
  log: reporterFunctions.log,
13
- logger: services.logger,
14
13
  meta: reporterFunctions.keyValue,
15
14
  step: reporterFunctions.step,
16
15
 
17
16
  TestomatClient,
18
17
  TRConstants,
19
18
  };
19
+
@@ -44,7 +44,8 @@ class Logger {
44
44
  logLevel = process?.env?.LOG_LEVEL?.toUpperCase() || 'ALL';
45
45
 
46
46
  constructor() {
47
- if (!dataStorage.isFileStorage || process.env.TESTOMATIO_INTERCEPT_CONSOLE_LOGS) this.intercept(console);
47
+ // intercept console by default
48
+ this.intercept(console);
48
49
  }
49
50
 
50
51
  /**
@@ -105,7 +106,7 @@ class Logger {
105
106
  * 2. Standard: log(`text ${someVar}`)
106
107
  * 3. Standard with multiple arguments: log('text', someVar)
107
108
  */
108
- _templateLiteralLog(strings, ...args) {
109
+ templateLiteralLog(strings, ...args) {
109
110
  if (Array.isArray(strings)) strings = strings.filter(item => item !== '').map(item => item.trim());
110
111
  if (Array.isArray(args)) args = args.filter(item => item !== '');
111
112
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@testomatio/reporter",
3
- "version": "1.1.1-beta.1.fix-logger",
3
+ "version": "1.1.1-file-upload.1",
4
4
  "description": "Testomatio Reporter Client",
5
5
  "main": "./lib/reporter.js",
6
6
  "typings": "typings/index.d.ts",
@@ -52,7 +52,7 @@
52
52
  "test:adapter:jasmine:example": "./tests/adapter/examples/jasmine/passReporterOpts.sh && jasmine './tests/adapter/examples/jasmine/index.test.js' --reporter=./../../../lib/adapter/jasmine.js",
53
53
  "test:adapter:codecept:example": "codeceptjs run --config='./tests/adapter/examples/codecept/codecept.conf.js'",
54
54
  "test:adapter:cucumber:example": "cd ./tests/adapter/examples/cucumber && npx cucumber-js",
55
- "test:storage": "npx mocha tests-storage/artifact-storage.test.js && npx mocha tests-storage/data-storage.test.js && TESTOMATIO_INTERCEPT_CONSOLE_LOGS=true npx mocha tests-storage/logger.test.js && npx mocha tests-storage/reporter-functions.test.js"
55
+ "test:storage": "npx mocha tests-storage/artifact-storage.test.js && npx mocha tests-storage/data-storage.test.js && npx mocha tests-storage/logger.test.js && npx mocha tests-storage/reporter-functions.test.js"
56
56
  },
57
57
  "devDependencies": {
58
58
  "@cucumber/cucumber": "^9.3.0",