@dev-blinq/cucumber-js 1.0.62 → 1.0.63-stage
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/bin/download-install.js +48 -32
- package/lib/api/gherkin.js +6 -1
- package/lib/api/gherkin.js.map +1 -1
- package/lib/configuration/axios_client.js +1 -1
- package/lib/configuration/axios_client.js.map +1 -1
- package/lib/formatter/api.d.ts +2 -0
- package/lib/formatter/api.js +53 -0
- package/lib/formatter/api.js.map +1 -0
- package/lib/formatter/bvt_analysis_formatter.d.ts +8 -1
- package/lib/formatter/bvt_analysis_formatter.js +171 -72
- package/lib/formatter/bvt_analysis_formatter.js.map +1 -1
- package/lib/formatter/feature_data_format.d.ts +2 -2
- package/lib/formatter/feature_data_format.js +52 -7
- package/lib/formatter/feature_data_format.js.map +1 -1
- package/lib/formatter/helpers/constants.d.ts +44 -0
- package/lib/formatter/helpers/constants.js +50 -0
- package/lib/formatter/helpers/constants.js.map +1 -0
- package/lib/formatter/helpers/report_generator.d.ts +41 -1
- package/lib/formatter/helpers/report_generator.js +267 -12
- package/lib/formatter/helpers/report_generator.js.map +1 -1
- package/lib/formatter/helpers/test_case_attempt_formatter.js +1 -1
- package/lib/formatter/helpers/test_case_attempt_formatter.js.map +1 -1
- package/lib/formatter/helpers/upload_serivce.d.ts +16 -3
- package/lib/formatter/helpers/upload_serivce.js +150 -18
- package/lib/formatter/helpers/upload_serivce.js.map +1 -1
- package/lib/formatter/helpers/uploader.d.ts +2 -1
- package/lib/formatter/helpers/uploader.js +87 -14
- package/lib/formatter/helpers/uploader.js.map +1 -1
- package/lib/runtime/test_case_runner.d.ts +1 -0
- package/lib/runtime/test_case_runner.js +7 -1
- package/lib/runtime/test_case_runner.js.map +1 -1
- package/lib/version.d.ts +1 -1
- package/lib/version.js +1 -1
- package/lib/version.js.map +1 -1
- package/package.json +3 -2
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
export declare const LOCAL: {
|
|
2
|
+
SSO: string;
|
|
3
|
+
WORKSPACE: string;
|
|
4
|
+
RUNS: string;
|
|
5
|
+
STORAGE: string;
|
|
6
|
+
};
|
|
7
|
+
export declare const DEV: {
|
|
8
|
+
SSO: string;
|
|
9
|
+
WORKSPACE: string;
|
|
10
|
+
RUNS: string;
|
|
11
|
+
STORAGE: string;
|
|
12
|
+
};
|
|
13
|
+
export declare const PROD: {
|
|
14
|
+
SSO: string;
|
|
15
|
+
WORKSPACE: string;
|
|
16
|
+
RUNS: string;
|
|
17
|
+
STORAGE: string;
|
|
18
|
+
};
|
|
19
|
+
export declare const STAGE: {
|
|
20
|
+
SSO: string;
|
|
21
|
+
WORKSPACE: string;
|
|
22
|
+
RUNS: string;
|
|
23
|
+
STORAGE: string;
|
|
24
|
+
};
|
|
25
|
+
export declare const SERVICES_URI: {
|
|
26
|
+
SSO: string;
|
|
27
|
+
WORKSPACE: string;
|
|
28
|
+
RUNS: string;
|
|
29
|
+
STORAGE: string;
|
|
30
|
+
};
|
|
31
|
+
export declare enum ActionEvents {
|
|
32
|
+
record_scenario = "record_scenario",
|
|
33
|
+
download_editor = "download_editor",
|
|
34
|
+
launch_editor = "launch_editor",
|
|
35
|
+
click_start_recording = "click_start_recording",
|
|
36
|
+
click_run_scenario = "click_run_scenario",
|
|
37
|
+
publish_scenario = "publish_scenario",
|
|
38
|
+
click_ai_generate = "click_ai_generate",
|
|
39
|
+
click_run_all = "click_run_all",
|
|
40
|
+
click_open_vscode = "click_open_vscode",
|
|
41
|
+
error_open_vscode = "error_open_vscode",
|
|
42
|
+
cli_run_tests = "cli_run_tests",
|
|
43
|
+
upload_report = "upload_report"
|
|
44
|
+
}
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ActionEvents = exports.SERVICES_URI = exports.STAGE = exports.PROD = exports.DEV = exports.LOCAL = void 0;
|
|
4
|
+
exports.LOCAL = {
|
|
5
|
+
SSO: 'http://localhost:5000/api/auth',
|
|
6
|
+
WORKSPACE: 'http://localhost:6000/api/workspace',
|
|
7
|
+
RUNS: 'http://localhost:5001/api/runs',
|
|
8
|
+
STORAGE: 'http://localhost:5050/api/storage',
|
|
9
|
+
};
|
|
10
|
+
exports.DEV = {
|
|
11
|
+
SSO: 'https://dev.api.blinq.io/api/auth',
|
|
12
|
+
WORKSPACE: 'https://dev.api.blinq.io/api/workspace',
|
|
13
|
+
RUNS: 'https://dev.api.blinq.io/api/runs',
|
|
14
|
+
STORAGE: 'https://dev.api.blinq.io/api/storage',
|
|
15
|
+
};
|
|
16
|
+
exports.PROD = {
|
|
17
|
+
SSO: 'https://api.blinq.io/api/auth',
|
|
18
|
+
WORKSPACE: 'https://api.blinq.io/api/workspace',
|
|
19
|
+
RUNS: 'https://api.blinq.io/api/runs',
|
|
20
|
+
STORAGE: 'https://api.blinq.io/api/storage',
|
|
21
|
+
};
|
|
22
|
+
exports.STAGE = {
|
|
23
|
+
SSO: 'https://stage.api.blinq.io/api/auth',
|
|
24
|
+
WORKSPACE: 'https://stage.api.blinq.io/api/workspace',
|
|
25
|
+
RUNS: 'https://stage.api.blinq.io/api/runs',
|
|
26
|
+
STORAGE: 'https://stage.api.blinq.io/api/storage',
|
|
27
|
+
};
|
|
28
|
+
exports.SERVICES_URI = process.env.NODE_ENV_BLINQ === 'local'
|
|
29
|
+
? exports.LOCAL // eslint-disable-line
|
|
30
|
+
: process.env.NODE_ENV_BLINQ === 'dev'
|
|
31
|
+
? exports.DEV // eslint-disable-line
|
|
32
|
+
: process.env.NODE_ENV_BLINQ === 'stage'
|
|
33
|
+
? exports.STAGE
|
|
34
|
+
: exports.PROD; // eslint-disable-line
|
|
35
|
+
var ActionEvents;
|
|
36
|
+
(function (ActionEvents) {
|
|
37
|
+
ActionEvents["record_scenario"] = "record_scenario";
|
|
38
|
+
ActionEvents["download_editor"] = "download_editor";
|
|
39
|
+
ActionEvents["launch_editor"] = "launch_editor";
|
|
40
|
+
ActionEvents["click_start_recording"] = "click_start_recording";
|
|
41
|
+
ActionEvents["click_run_scenario"] = "click_run_scenario";
|
|
42
|
+
ActionEvents["publish_scenario"] = "publish_scenario";
|
|
43
|
+
ActionEvents["click_ai_generate"] = "click_ai_generate";
|
|
44
|
+
ActionEvents["click_run_all"] = "click_run_all";
|
|
45
|
+
ActionEvents["click_open_vscode"] = "click_open_vscode";
|
|
46
|
+
ActionEvents["error_open_vscode"] = "error_open_vscode";
|
|
47
|
+
ActionEvents["cli_run_tests"] = "cli_run_tests";
|
|
48
|
+
ActionEvents["upload_report"] = "upload_report";
|
|
49
|
+
})(ActionEvents = exports.ActionEvents || (exports.ActionEvents = {}));
|
|
50
|
+
//# sourceMappingURL=constants.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants.js","sourceRoot":"","sources":["../../../src/formatter/helpers/constants.ts"],"names":[],"mappings":";;;AAAa,QAAA,KAAK,GAAG;IACnB,GAAG,EAAE,gCAAgC;IACrC,SAAS,EAAE,qCAAqC;IAChD,IAAI,EAAE,gCAAgC;IACtC,OAAO,EAAE,mCAAmC;CAC7C,CAAA;AACY,QAAA,GAAG,GAAG;IACjB,GAAG,EAAE,mCAAmC;IACxC,SAAS,EAAE,wCAAwC;IACnD,IAAI,EAAE,mCAAmC;IACzC,OAAO,EAAE,sCAAsC;CAChD,CAAA;AACY,QAAA,IAAI,GAAG;IAClB,GAAG,EAAE,+BAA+B;IACpC,SAAS,EAAE,oCAAoC;IAC/C,IAAI,EAAE,+BAA+B;IACrC,OAAO,EAAE,kCAAkC;CAC5C,CAAA;AACY,QAAA,KAAK,GAAG;IACnB,GAAG,EAAE,qCAAqC;IAC1C,SAAS,EAAE,0CAA0C;IACrD,IAAI,EAAE,qCAAqC;IAC3C,OAAO,EAAE,wCAAwC;CAClD,CAAA;AAEY,QAAA,YAAY,GACvB,OAAO,CAAC,GAAG,CAAC,cAAc,KAAK,OAAO;IACpC,CAAC,CAAC,aAAK,CAAC,sBAAsB;IAC9B,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,cAAc,KAAK,KAAK;QACtC,CAAC,CAAC,WAAG,CAAC,sBAAsB;QAC5B,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,cAAc,KAAK,OAAO;YACxC,CAAC,CAAC,aAAK;YACP,CAAC,CAAC,YAAI,CAAA,CAAC,sBAAsB;AAEjC,IAAY,YAaX;AAbD,WAAY,YAAY;IACtB,mDAAmC,CAAA;IACnC,mDAAmC,CAAA;IACnC,+CAA+B,CAAA;IAC/B,+DAA+C,CAAA;IAC/C,yDAAyC,CAAA;IACzC,qDAAqC,CAAA;IACrC,uDAAuC,CAAA;IACvC,+CAA+B,CAAA;IAC/B,uDAAuC,CAAA;IACvC,uDAAuC,CAAA;IACvC,+CAA+B,CAAA;IAC/B,+CAA+B,CAAA;AACjC,CAAC,EAbW,YAAY,GAAZ,oBAAY,KAAZ,oBAAY,QAavB","sourcesContent":["export const LOCAL = {\n SSO: 'http://localhost:5000/api/auth',\n WORKSPACE: 'http://localhost:6000/api/workspace',\n RUNS: 'http://localhost:5001/api/runs',\n STORAGE: 'http://localhost:5050/api/storage',\n}\nexport const DEV = {\n SSO: 'https://dev.api.blinq.io/api/auth',\n WORKSPACE: 'https://dev.api.blinq.io/api/workspace',\n RUNS: 'https://dev.api.blinq.io/api/runs',\n STORAGE: 'https://dev.api.blinq.io/api/storage',\n}\nexport const PROD = {\n SSO: 'https://api.blinq.io/api/auth',\n WORKSPACE: 'https://api.blinq.io/api/workspace',\n RUNS: 'https://api.blinq.io/api/runs',\n STORAGE: 'https://api.blinq.io/api/storage',\n}\nexport const STAGE = {\n SSO: 'https://stage.api.blinq.io/api/auth',\n WORKSPACE: 'https://stage.api.blinq.io/api/workspace',\n RUNS: 'https://stage.api.blinq.io/api/runs',\n STORAGE: 'https://stage.api.blinq.io/api/storage',\n}\n\nexport const SERVICES_URI =\n process.env.NODE_ENV_BLINQ === 'local'\n ? LOCAL // eslint-disable-line\n : process.env.NODE_ENV_BLINQ === 'dev'\n ? DEV // eslint-disable-line\n : process.env.NODE_ENV_BLINQ === 'stage'\n ? STAGE\n : PROD // eslint-disable-line\n\nexport enum ActionEvents {\n record_scenario = 'record_scenario',\n download_editor = 'download_editor',\n launch_editor = 'launch_editor',\n click_start_recording = 'click_start_recording',\n click_run_scenario = 'click_run_scenario',\n publish_scenario = 'publish_scenario',\n click_ai_generate = 'click_ai_generate',\n click_run_all = 'click_run_all',\n click_open_vscode = 'click_open_vscode',\n error_open_vscode = 'error_open_vscode',\n cli_run_tests = 'cli_run_tests',\n upload_report = 'upload_report',\n}\n"]}
|
|
@@ -48,6 +48,13 @@ type JsonCommand = {
|
|
|
48
48
|
text: string;
|
|
49
49
|
screenshotId?: string;
|
|
50
50
|
result: JsonCommandResult;
|
|
51
|
+
netWorkLog?: any[];
|
|
52
|
+
};
|
|
53
|
+
type webLog = {
|
|
54
|
+
type: string;
|
|
55
|
+
text: string;
|
|
56
|
+
location: string;
|
|
57
|
+
time: string;
|
|
51
58
|
};
|
|
52
59
|
export type JsonStep = {
|
|
53
60
|
keyword: string;
|
|
@@ -55,6 +62,10 @@ export type JsonStep = {
|
|
|
55
62
|
text: string;
|
|
56
63
|
commands: JsonCommand[];
|
|
57
64
|
result: JsonStepResult;
|
|
65
|
+
webLog: webLog[];
|
|
66
|
+
networkData: any[];
|
|
67
|
+
data?: any;
|
|
68
|
+
ariaSnapshot: string;
|
|
58
69
|
};
|
|
59
70
|
export type RetrainStats = {
|
|
60
71
|
result: JsonTestResult;
|
|
@@ -71,11 +82,28 @@ export type JsonTestProgress = {
|
|
|
71
82
|
steps: JsonStep[];
|
|
72
83
|
result: JsonTestResult;
|
|
73
84
|
retrainStats?: RetrainStats;
|
|
85
|
+
initialAriaSnapshot?: string;
|
|
86
|
+
webLog: any;
|
|
87
|
+
networkLog: any;
|
|
88
|
+
env: {
|
|
89
|
+
name: string;
|
|
90
|
+
baseUrl: string;
|
|
91
|
+
};
|
|
74
92
|
};
|
|
75
93
|
export type JsonReport = {
|
|
76
94
|
testCases: JsonTestProgress[];
|
|
77
95
|
result: JsonReportResult;
|
|
96
|
+
env: {
|
|
97
|
+
name: string;
|
|
98
|
+
baseUrl: string;
|
|
99
|
+
};
|
|
78
100
|
};
|
|
101
|
+
interface MetaMessage extends messages.Meta {
|
|
102
|
+
runName: string;
|
|
103
|
+
}
|
|
104
|
+
interface EnvelopeWithMetaMessage extends messages.Envelope {
|
|
105
|
+
meta: MetaMessage;
|
|
106
|
+
}
|
|
79
107
|
export default class ReportGenerator {
|
|
80
108
|
private report;
|
|
81
109
|
private gherkinDocumentMap;
|
|
@@ -86,8 +114,16 @@ export default class ReportGenerator {
|
|
|
86
114
|
private stepReportMap;
|
|
87
115
|
private testCaseReportMap;
|
|
88
116
|
private scenarioIterationCountMap;
|
|
117
|
+
private logs;
|
|
118
|
+
private networkLog;
|
|
119
|
+
private stepLogs;
|
|
120
|
+
private stepNetworkLogs;
|
|
121
|
+
private runName;
|
|
122
|
+
private ariaSnapshot;
|
|
123
|
+
private initialAriaSnapshot;
|
|
89
124
|
reportFolder: null | string;
|
|
90
|
-
|
|
125
|
+
private uploadService;
|
|
126
|
+
handleMessage(envelope: EnvelopeWithMetaMessage | messages.Envelope): Promise<any>;
|
|
91
127
|
getReport(): JsonReport;
|
|
92
128
|
private handleParseError;
|
|
93
129
|
private onGherkinDocument;
|
|
@@ -100,9 +136,13 @@ export default class ReportGenerator {
|
|
|
100
136
|
private onTestCaseStarted;
|
|
101
137
|
private onTestStepStarted;
|
|
102
138
|
private onAttachment;
|
|
139
|
+
private getFailedTestStepResult;
|
|
103
140
|
private onTestStepFinished;
|
|
141
|
+
getLogFileContent(): any;
|
|
104
142
|
private getTestCaseResult;
|
|
105
143
|
private onTestCaseFinished;
|
|
144
|
+
private uploadTestCase;
|
|
145
|
+
private writeTestCaseReportToDisk;
|
|
106
146
|
private onTestRunFinished;
|
|
107
147
|
}
|
|
108
148
|
export {};
|
|
@@ -1,5 +1,47 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || function (mod) {
|
|
19
|
+
if (mod && mod.__esModule) return mod;
|
|
20
|
+
var result = {};
|
|
21
|
+
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
22
|
+
__setModuleDefault(result, mod);
|
|
23
|
+
return result;
|
|
24
|
+
};
|
|
25
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
26
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
27
|
+
};
|
|
28
|
+
var _a, _b;
|
|
2
29
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
30
|
+
const messages = __importStar(require("@cucumber/messages"));
|
|
31
|
+
const fs_1 = __importDefault(require("fs"));
|
|
32
|
+
const path_1 = __importDefault(require("path"));
|
|
33
|
+
const upload_serivce_1 = require("./upload_serivce");
|
|
34
|
+
const URL = process.env.NODE_ENV_BLINQ === 'dev'
|
|
35
|
+
? 'https://dev.api.blinq.io/api/runs'
|
|
36
|
+
: process.env.NODE_ENV_BLINQ === 'local'
|
|
37
|
+
? 'http://localhost:5001/api/runs'
|
|
38
|
+
: process.env.NODE_ENV_BLINQ === 'stage'
|
|
39
|
+
? 'https://stage.api.blinq.io/api/runs'
|
|
40
|
+
: 'https://api.blinq.io/api/runs';
|
|
41
|
+
const REPORT_SERVICE_URL = (_a = process.env.REPORT_SERVICE_URL) !== null && _a !== void 0 ? _a : URL;
|
|
42
|
+
const BATCH_SIZE = 10;
|
|
43
|
+
const MAX_RETRIES = 3;
|
|
44
|
+
const REPORT_SERVICE_TOKEN = (_b = process.env.TOKEN) !== null && _b !== void 0 ? _b : process.env.REPORT_SERVICE_TOKEN;
|
|
3
45
|
class ReportGenerator {
|
|
4
46
|
constructor() {
|
|
5
47
|
this.report = {
|
|
@@ -7,6 +49,10 @@ class ReportGenerator {
|
|
|
7
49
|
status: 'UNKNOWN',
|
|
8
50
|
},
|
|
9
51
|
testCases: [],
|
|
52
|
+
env: {
|
|
53
|
+
name: '',
|
|
54
|
+
baseUrl: '',
|
|
55
|
+
},
|
|
10
56
|
};
|
|
11
57
|
this.gherkinDocumentMap = new Map();
|
|
12
58
|
this.stepMap = new Map();
|
|
@@ -16,9 +62,20 @@ class ReportGenerator {
|
|
|
16
62
|
this.stepReportMap = new Map();
|
|
17
63
|
this.testCaseReportMap = new Map();
|
|
18
64
|
this.scenarioIterationCountMap = new Map();
|
|
65
|
+
this.logs = [];
|
|
66
|
+
this.networkLog = [];
|
|
67
|
+
this.stepLogs = [];
|
|
68
|
+
this.stepNetworkLogs = [];
|
|
69
|
+
this.runName = '';
|
|
70
|
+
this.ariaSnapshot = '';
|
|
71
|
+
this.initialAriaSnapshot = '';
|
|
19
72
|
this.reportFolder = null;
|
|
73
|
+
this.uploadService = new upload_serivce_1.RunUploadService(REPORT_SERVICE_URL, REPORT_SERVICE_TOKEN);
|
|
20
74
|
}
|
|
21
|
-
handleMessage(envelope) {
|
|
75
|
+
async handleMessage(envelope) {
|
|
76
|
+
if (envelope.meta && 'runName' in envelope.meta) {
|
|
77
|
+
this.runName = envelope.meta.runName;
|
|
78
|
+
}
|
|
22
79
|
const type = Object.keys(envelope)[0];
|
|
23
80
|
switch (type) {
|
|
24
81
|
// case "meta": { break}
|
|
@@ -72,8 +129,7 @@ class ReportGenerator {
|
|
|
72
129
|
}
|
|
73
130
|
case 'testCaseFinished': {
|
|
74
131
|
const testCaseFinished = envelope[type];
|
|
75
|
-
this.onTestCaseFinished(testCaseFinished);
|
|
76
|
-
break;
|
|
132
|
+
return await this.onTestCaseFinished(testCaseFinished);
|
|
77
133
|
}
|
|
78
134
|
// case "hook": { break} // After Hook
|
|
79
135
|
case 'testRunFinished': {
|
|
@@ -209,6 +265,10 @@ class ReportGenerator {
|
|
|
209
265
|
result: {
|
|
210
266
|
status: 'UNKNOWN',
|
|
211
267
|
},
|
|
268
|
+
networkData: [],
|
|
269
|
+
webLog: [],
|
|
270
|
+
data: {},
|
|
271
|
+
ariaSnapshot: this.ariaSnapshot,
|
|
212
272
|
});
|
|
213
273
|
return this.stepReportMap.get(pickleStep.id);
|
|
214
274
|
});
|
|
@@ -223,6 +283,12 @@ class ReportGenerator {
|
|
|
223
283
|
status: 'STARTED',
|
|
224
284
|
startTime: this.getTimeStamp(timestamp),
|
|
225
285
|
},
|
|
286
|
+
webLog: [],
|
|
287
|
+
networkLog: [],
|
|
288
|
+
env: {
|
|
289
|
+
name: this.report.env.name,
|
|
290
|
+
baseUrl: this.report.env.baseUrl,
|
|
291
|
+
},
|
|
226
292
|
});
|
|
227
293
|
this.report.testCases.push(this.testCaseReportMap.get(id));
|
|
228
294
|
}
|
|
@@ -243,6 +309,36 @@ class ReportGenerator {
|
|
|
243
309
|
const { testStepId, body, mediaType } = attachment;
|
|
244
310
|
if (mediaType === 'text/plain') {
|
|
245
311
|
this.reportFolder = body.replaceAll('\\', '/');
|
|
312
|
+
return;
|
|
313
|
+
}
|
|
314
|
+
if (mediaType === 'application/json+snapshot-before') {
|
|
315
|
+
this.initialAriaSnapshot = body;
|
|
316
|
+
return;
|
|
317
|
+
}
|
|
318
|
+
if (mediaType === 'application/json+snapshot-after') {
|
|
319
|
+
this.ariaSnapshot = body;
|
|
320
|
+
return;
|
|
321
|
+
}
|
|
322
|
+
if (mediaType === 'application/json+env') {
|
|
323
|
+
const data = JSON.parse(body);
|
|
324
|
+
this.report.env = data;
|
|
325
|
+
this.report.testCases.map((testCase) => {
|
|
326
|
+
testCase.env = data;
|
|
327
|
+
return testCase;
|
|
328
|
+
});
|
|
329
|
+
}
|
|
330
|
+
if (mediaType === 'application/json+log') {
|
|
331
|
+
const log = JSON.parse(body);
|
|
332
|
+
if (this.logs.length < 1000) {
|
|
333
|
+
this.logs.push(log);
|
|
334
|
+
this.stepLogs.push(log);
|
|
335
|
+
}
|
|
336
|
+
}
|
|
337
|
+
if (mediaType === 'application/json+network') {
|
|
338
|
+
const networkLog = JSON.parse(body);
|
|
339
|
+
if (this.networkLog.length < 1000)
|
|
340
|
+
this.networkLog.push(networkLog);
|
|
341
|
+
this.stepNetworkLogs.push(networkLog);
|
|
246
342
|
}
|
|
247
343
|
const testStep = this.testStepMap.get(testStepId);
|
|
248
344
|
if (testStep.pickleStepId === undefined)
|
|
@@ -253,20 +349,115 @@ class ReportGenerator {
|
|
|
253
349
|
stepProgess.commands.push(command);
|
|
254
350
|
}
|
|
255
351
|
}
|
|
352
|
+
getFailedTestStepResult({ commands, startTime, endTime, result, }) {
|
|
353
|
+
for (const command of commands) {
|
|
354
|
+
if (command.result.status === 'FAILED') {
|
|
355
|
+
return {
|
|
356
|
+
status: 'FAILED',
|
|
357
|
+
message: command.result.message,
|
|
358
|
+
startTime,
|
|
359
|
+
endTime,
|
|
360
|
+
};
|
|
361
|
+
}
|
|
362
|
+
}
|
|
363
|
+
return {
|
|
364
|
+
status: 'FAILED',
|
|
365
|
+
startTime,
|
|
366
|
+
endTime,
|
|
367
|
+
message: result.message,
|
|
368
|
+
};
|
|
369
|
+
}
|
|
256
370
|
onTestStepFinished(testStepFinished) {
|
|
257
371
|
const { testStepId, testStepResult, timestamp } = testStepFinished;
|
|
258
372
|
const testStep = this.testStepMap.get(testStepId);
|
|
259
|
-
if (testStep.pickleStepId === undefined)
|
|
373
|
+
if (testStep.pickleStepId === undefined) {
|
|
374
|
+
if (testStepResult.status === 'FAILED') {
|
|
375
|
+
console.error(`Before/After hook failed with message: ${testStepResult.message}`);
|
|
376
|
+
}
|
|
260
377
|
return;
|
|
378
|
+
}
|
|
379
|
+
if (testStepResult.status === 'UNDEFINED') {
|
|
380
|
+
const step = this.stepReportMap.get(testStep.pickleStepId);
|
|
381
|
+
const stepName = step ? step.keyword + ' ' + step.text : 'Undefined step';
|
|
382
|
+
const undefinedCommand = {
|
|
383
|
+
testStepId: testStepId,
|
|
384
|
+
body: JSON.stringify({
|
|
385
|
+
type: 'error',
|
|
386
|
+
text: 'Undefined step: ' + stepName,
|
|
387
|
+
result: {
|
|
388
|
+
status: 'FAILED',
|
|
389
|
+
startTime: this.getTimeStamp(timestamp),
|
|
390
|
+
endTime: this.getTimeStamp(timestamp),
|
|
391
|
+
},
|
|
392
|
+
}),
|
|
393
|
+
mediaType: 'application/json',
|
|
394
|
+
contentEncoding: messages.AttachmentContentEncoding.IDENTITY,
|
|
395
|
+
};
|
|
396
|
+
this.onAttachment(undefinedCommand);
|
|
397
|
+
}
|
|
261
398
|
const stepProgess = this.stepReportMap.get(testStep.pickleStepId);
|
|
262
399
|
const prevStepResult = stepProgess.result;
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
400
|
+
let data = {};
|
|
401
|
+
try {
|
|
402
|
+
const reportFolder = this.reportFolder;
|
|
403
|
+
if (reportFolder === null) {
|
|
404
|
+
throw new Error('"reportFolder" is "null". Failed to run BVT hooks. Please retry after running "Generate All" or "Record Scenario" ');
|
|
405
|
+
}
|
|
406
|
+
if (fs_1.default.existsSync(path_1.default.join(reportFolder, 'data.json'))) {
|
|
407
|
+
data = JSON.parse(fs_1.default.readFileSync(path_1.default.join(reportFolder, 'data.json'), 'utf8'));
|
|
408
|
+
}
|
|
409
|
+
}
|
|
410
|
+
catch (error) {
|
|
411
|
+
console.log('Error reading data.json');
|
|
412
|
+
}
|
|
413
|
+
if (testStepResult.status === 'FAILED') {
|
|
414
|
+
stepProgess.result = this.getFailedTestStepResult({
|
|
415
|
+
commands: stepProgess.commands,
|
|
416
|
+
startTime: prevStepResult.startTime,
|
|
417
|
+
endTime: this.getTimeStamp(timestamp),
|
|
418
|
+
result: testStepResult,
|
|
419
|
+
});
|
|
420
|
+
}
|
|
421
|
+
else {
|
|
422
|
+
stepProgess.result = {
|
|
423
|
+
status: testStepResult.status,
|
|
424
|
+
startTime: prevStepResult.startTime,
|
|
425
|
+
endTime: this.getTimeStamp(timestamp),
|
|
426
|
+
};
|
|
427
|
+
}
|
|
428
|
+
stepProgess.webLog = this.stepLogs;
|
|
429
|
+
stepProgess.networkData = this.stepNetworkLogs;
|
|
430
|
+
stepProgess.ariaSnapshot = this.ariaSnapshot;
|
|
431
|
+
this.ariaSnapshot = '';
|
|
432
|
+
this.stepNetworkLogs = [];
|
|
433
|
+
this.stepLogs = [];
|
|
434
|
+
if (Object.keys(data).length > 0) {
|
|
435
|
+
stepProgess.data = data;
|
|
436
|
+
}
|
|
437
|
+
}
|
|
438
|
+
getLogFileContent() {
|
|
439
|
+
let projectPath = process.cwd();
|
|
440
|
+
if (process.env.PROJECT_PATH) {
|
|
441
|
+
projectPath = process.env.PROJECT_PATH;
|
|
442
|
+
}
|
|
443
|
+
const logFolder = path_1.default.join(projectPath, 'logs', 'web');
|
|
444
|
+
if (!fs_1.default.existsSync(logFolder)) {
|
|
445
|
+
return [];
|
|
446
|
+
}
|
|
447
|
+
let nextId = 1;
|
|
448
|
+
while (fs_1.default.existsSync(path_1.default.join(logFolder, `${nextId}.json`))) {
|
|
449
|
+
nextId++;
|
|
450
|
+
}
|
|
451
|
+
if (nextId === 1) {
|
|
452
|
+
return [];
|
|
453
|
+
}
|
|
454
|
+
try {
|
|
455
|
+
const logFileContent = fs_1.default.readFileSync(path_1.default.join(logFolder, `${nextId - 1}.json`), 'utf8');
|
|
456
|
+
return JSON.parse(logFileContent);
|
|
457
|
+
}
|
|
458
|
+
catch (error) {
|
|
459
|
+
return [];
|
|
460
|
+
}
|
|
270
461
|
}
|
|
271
462
|
getTestCaseResult(steps) {
|
|
272
463
|
for (const step of steps) {
|
|
@@ -290,7 +481,7 @@ class ReportGenerator {
|
|
|
290
481
|
status: 'PASSED',
|
|
291
482
|
};
|
|
292
483
|
}
|
|
293
|
-
onTestCaseFinished(testCaseFinished) {
|
|
484
|
+
async onTestCaseFinished(testCaseFinished) {
|
|
294
485
|
const { testCaseStartedId, timestamp } = testCaseFinished;
|
|
295
486
|
const testProgress = this.testCaseReportMap.get(testCaseStartedId);
|
|
296
487
|
const prevResult = testProgress.result;
|
|
@@ -301,6 +492,70 @@ class ReportGenerator {
|
|
|
301
492
|
startTime: prevResult.startTime,
|
|
302
493
|
endTime: this.getTimeStamp(timestamp),
|
|
303
494
|
};
|
|
495
|
+
testProgress.webLog = this.logs;
|
|
496
|
+
testProgress.networkLog = this.networkLog;
|
|
497
|
+
testProgress.initialAriaSnapshot = this.initialAriaSnapshot;
|
|
498
|
+
this.initialAriaSnapshot = '';
|
|
499
|
+
this.networkLog = [];
|
|
500
|
+
this.logs = [];
|
|
501
|
+
return await this.uploadTestCase(testProgress);
|
|
502
|
+
}
|
|
503
|
+
async uploadTestCase(testCase) {
|
|
504
|
+
let runId = '';
|
|
505
|
+
let projectId = '';
|
|
506
|
+
if (!process.env.UPLOADING_TEST_CASE) {
|
|
507
|
+
process.env.UPLOADING_TEST_CASE = '[]';
|
|
508
|
+
}
|
|
509
|
+
const anyRemArr = JSON.parse(process.env.UPLOADING_TEST_CASE);
|
|
510
|
+
const randomID = Math.random().toString(36).substring(7);
|
|
511
|
+
anyRemArr.push(randomID);
|
|
512
|
+
let data;
|
|
513
|
+
process.env.UPLOADING_TEST_CASE = JSON.stringify(anyRemArr);
|
|
514
|
+
try {
|
|
515
|
+
if (process.env.RUN_ID &&
|
|
516
|
+
process.env.PROJECT_ID &&
|
|
517
|
+
!process.env.IGNORE_ENV_VARIABLES) {
|
|
518
|
+
runId = process.env.RUN_ID;
|
|
519
|
+
projectId = process.env.PROJECT_ID;
|
|
520
|
+
}
|
|
521
|
+
else {
|
|
522
|
+
const runDoc = await this.uploadService.createRunDocument(this.runName);
|
|
523
|
+
runId = runDoc._id;
|
|
524
|
+
projectId = runDoc.project_id;
|
|
525
|
+
if (!process.env.IGNORE_ENV_VARIABLES) {
|
|
526
|
+
process.env.RUN_ID = runId;
|
|
527
|
+
process.env.PROJECT_ID = projectId;
|
|
528
|
+
}
|
|
529
|
+
}
|
|
530
|
+
data = await this.uploadService.uploadTestCase(testCase, runId, projectId, this.reportFolder);
|
|
531
|
+
this.writeTestCaseReportToDisk(testCase);
|
|
532
|
+
}
|
|
533
|
+
catch (e) {
|
|
534
|
+
console.error('Error uploading test case:', e);
|
|
535
|
+
}
|
|
536
|
+
finally {
|
|
537
|
+
const arrRem = JSON.parse(process.env.UPLOADING_TEST_CASE);
|
|
538
|
+
arrRem.splice(arrRem.indexOf(randomID), 1);
|
|
539
|
+
process.env.UPLOADING_TEST_CASE = JSON.stringify(arrRem);
|
|
540
|
+
}
|
|
541
|
+
return data ? data : null;
|
|
542
|
+
}
|
|
543
|
+
writeTestCaseReportToDisk(testCase) {
|
|
544
|
+
try {
|
|
545
|
+
let i = 0;
|
|
546
|
+
while (fs_1.default.existsSync(path_1.default.join(this.reportFolder, `${i}`))) {
|
|
547
|
+
i++;
|
|
548
|
+
}
|
|
549
|
+
fs_1.default.mkdirSync(path_1.default.join(this.reportFolder, `${i}`));
|
|
550
|
+
//exclude network log from the saved report
|
|
551
|
+
const networkLog = testCase.networkLog;
|
|
552
|
+
delete testCase.networkLog;
|
|
553
|
+
fs_1.default.writeFileSync(path_1.default.join(this.reportFolder, `${i}`, `report.json`), JSON.stringify(testCase, null, 2));
|
|
554
|
+
fs_1.default.writeFileSync(path_1.default.join(this.reportFolder, `${i}`, `network.json`), JSON.stringify(networkLog, null, 2));
|
|
555
|
+
}
|
|
556
|
+
catch (error) {
|
|
557
|
+
console.error('Error writing test case report to disk:', error);
|
|
558
|
+
}
|
|
304
559
|
}
|
|
305
560
|
onTestRunFinished(testRunFinished) {
|
|
306
561
|
const { timestamp, success, message } = testRunFinished;
|