qase-javascript-commons 2.4.1 → 2.4.2
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 +6 -0
- package/changelog.md +12 -0
- package/dist/config/config-validation-schema.d.ts +7 -0
- package/dist/config/config-validation-schema.js +7 -0
- package/dist/env/env-enum.d.ts +2 -1
- package/dist/env/env-enum.js +1 -0
- package/dist/env/env-to-config.js +1 -0
- package/dist/env/env-type.d.ts +1 -0
- package/dist/env/env-validation-schema.js +4 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/models/config/TestOpsOptionsType.d.ts +1 -0
- package/dist/qase.d.ts +5 -0
- package/dist/qase.js +22 -0
- package/dist/utils/test-status-utils.d.ts +8 -0
- package/dist/utils/test-status-utils.js +104 -0
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -59,6 +59,7 @@ All configuration options are listed in the table below:
|
|
|
59
59
|
| Size of batch for sending test results | `testops.batch.size` | `QASE_TESTOPS_BATCH_SIZE` | `200` | No | Any integer |
|
|
60
60
|
| Enable defects for failed test cases | `testops.defect` | `QASE_TESTOPS_DEFECT` | `False` | No | `True`, `False` |
|
|
61
61
|
| Enable/disable attachment uploads | `testops.uploadAttachments` | `QASE_TESTOPS_UPLOAD_ATTACHMENTS` | `true` | No | `True`, `False` |
|
|
62
|
+
| Filter test results by status (comma-separated list of statuses to exclude from reporting) | `testops.statusFilter` | `QASE_TESTOPS_STATUS_FILTER` | undefined | No | Array of strings (`passed`, `failed`, `skipped`, `invalid`) |
|
|
62
63
|
| Configuration values to create/find in groups (format: `group1=value1,group2=value2`) | `testops.configurations.values` | `QASE_TESTOPS_CONFIGURATIONS_VALUES` | undefined | No | Comma-separated key=value pairs |
|
|
63
64
|
| Create configuration groups if they don't exist | `testops.configurations.createIfNotExists` | `QASE_TESTOPS_CONFIGURATIONS_CREATE_IF_NOT_EXISTS` | `false` | No | `True`, `False` |
|
|
64
65
|
|
|
@@ -97,6 +98,8 @@ All configuration options are listed in the table below:
|
|
|
97
98
|
},
|
|
98
99
|
"defect": false,
|
|
99
100
|
"project": "<project_code>",
|
|
101
|
+
"uploadAttachments": true,
|
|
102
|
+
"statusFilter": ["passed", "skipped"],
|
|
100
103
|
"batch": {
|
|
101
104
|
"size": 100
|
|
102
105
|
},
|
|
@@ -125,4 +128,7 @@ export QASE_TESTOPS_RUN_EXTERNAL_LINK='{"type":"jiraCloud","link":"PROJ-123"}'
|
|
|
125
128
|
|
|
126
129
|
# Set external link for Jira Server
|
|
127
130
|
export QASE_TESTOPS_RUN_EXTERNAL_LINK='{"type":"jiraServer","link":"PROJ-456"}'
|
|
131
|
+
|
|
132
|
+
# Filter out test results with specific statuses
|
|
133
|
+
export QASE_TESTOPS_STATUS_FILTER="passed,failed"
|
|
128
134
|
```
|
package/changelog.md
CHANGED
|
@@ -1,3 +1,15 @@
|
|
|
1
|
+
# qase-javascript-commons@2.4.2
|
|
2
|
+
|
|
3
|
+
## What's new
|
|
4
|
+
|
|
5
|
+
Added support for status filter in the test run.
|
|
6
|
+
|
|
7
|
+
You can now filter out test results by status.
|
|
8
|
+
The status filter is specified in the `testops.statusFilter` configuration option.
|
|
9
|
+
The status filter is a comma-separated list of statuses to exclude from reporting.
|
|
10
|
+
The statuses are: `passed`, `failed`, `skipped`, `invalid`.
|
|
11
|
+
The status filter is applied to the test results before they are sent to Qase.
|
|
12
|
+
|
|
1
13
|
# qase-javascript-commons@2.4.1
|
|
2
14
|
|
|
3
15
|
## What's new
|
package/dist/env/env-enum.d.ts
CHANGED
|
@@ -15,7 +15,8 @@ export declare enum EnvEnum {
|
|
|
15
15
|
export declare enum EnvTestOpsEnum {
|
|
16
16
|
project = "QASE_TESTOPS_PROJECT",
|
|
17
17
|
uploadAttachments = "QASE_TESTOPS_UPLOAD_ATTACHMENTS",
|
|
18
|
-
defect = "QASE_TESTOPS_DEFECT"
|
|
18
|
+
defect = "QASE_TESTOPS_DEFECT",
|
|
19
|
+
statusFilter = "QASE_TESTOPS_STATUS_FILTER"
|
|
19
20
|
}
|
|
20
21
|
/**
|
|
21
22
|
* @enum {string}
|
package/dist/env/env-enum.js
CHANGED
|
@@ -21,6 +21,7 @@ var EnvTestOpsEnum;
|
|
|
21
21
|
EnvTestOpsEnum["project"] = "QASE_TESTOPS_PROJECT";
|
|
22
22
|
EnvTestOpsEnum["uploadAttachments"] = "QASE_TESTOPS_UPLOAD_ATTACHMENTS";
|
|
23
23
|
EnvTestOpsEnum["defect"] = "QASE_TESTOPS_DEFECT";
|
|
24
|
+
EnvTestOpsEnum["statusFilter"] = "QASE_TESTOPS_STATUS_FILTER";
|
|
24
25
|
})(EnvTestOpsEnum || (exports.EnvTestOpsEnum = EnvTestOpsEnum = {}));
|
|
25
26
|
/**
|
|
26
27
|
* @enum {string}
|
|
@@ -16,6 +16,7 @@ const envToConfig = (env) => ({
|
|
|
16
16
|
testops: {
|
|
17
17
|
project: env[env_enum_1.EnvTestOpsEnum.project],
|
|
18
18
|
uploadAttachments: env[env_enum_1.EnvTestOpsEnum.uploadAttachments],
|
|
19
|
+
statusFilter: env[env_enum_1.EnvTestOpsEnum.statusFilter]?.split(',').map(status => status.trim()) ?? undefined,
|
|
19
20
|
api: {
|
|
20
21
|
token: env[env_enum_1.EnvApiEnum.token],
|
|
21
22
|
host: env[env_enum_1.EnvApiEnum.host],
|
package/dist/env/env-type.d.ts
CHANGED
|
@@ -11,6 +11,7 @@ export interface EnvType {
|
|
|
11
11
|
[EnvTestOpsEnum.project]?: string;
|
|
12
12
|
[EnvTestOpsEnum.uploadAttachments]?: boolean;
|
|
13
13
|
[EnvTestOpsEnum.defect]?: boolean;
|
|
14
|
+
[EnvTestOpsEnum.statusFilter]?: string;
|
|
14
15
|
[EnvApiEnum.token]?: string;
|
|
15
16
|
[EnvApiEnum.host]?: string;
|
|
16
17
|
[EnvRunEnum.id]?: number;
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -25,4 +25,5 @@ __exportStar(require("./writer"), exports);
|
|
|
25
25
|
__exportStar(require("./utils/get-package-version"), exports);
|
|
26
26
|
__exportStar(require("./utils/mimeTypes"), exports);
|
|
27
27
|
__exportStar(require("./utils/signature"), exports);
|
|
28
|
+
__exportStar(require("./utils/test-status-utils"), exports);
|
|
28
29
|
__exportStar(require("./steps/step"), exports);
|
|
@@ -7,6 +7,7 @@ export interface TestOpsOptionsType {
|
|
|
7
7
|
batch?: TestOpsBatchType;
|
|
8
8
|
defect?: boolean | undefined;
|
|
9
9
|
configurations?: TestOpsConfigurationType | undefined;
|
|
10
|
+
statusFilter?: string[] | undefined;
|
|
10
11
|
}
|
|
11
12
|
export interface TestOpsConfigurationType {
|
|
12
13
|
values: TestOpsConfigurationValueType[];
|
package/dist/qase.d.ts
CHANGED
|
@@ -69,6 +69,11 @@ export declare class QaseReporter implements ReporterInterface {
|
|
|
69
69
|
* @param {TestResultType} result
|
|
70
70
|
*/
|
|
71
71
|
addTestResult(result: TestResultType): Promise<void>;
|
|
72
|
+
/**
|
|
73
|
+
* @param {TestResultType} result
|
|
74
|
+
* @private
|
|
75
|
+
*/
|
|
76
|
+
private shouldFilterResult;
|
|
72
77
|
/**
|
|
73
78
|
* @param {TestResultType} result
|
|
74
79
|
* @private
|
package/dist/qase.js
CHANGED
|
@@ -281,6 +281,11 @@ class QaseReporter {
|
|
|
281
281
|
*/
|
|
282
282
|
async addTestResult(result) {
|
|
283
283
|
if (!this.disabled) {
|
|
284
|
+
// Check if result should be filtered out based on status
|
|
285
|
+
if (this.shouldFilterResult(result)) {
|
|
286
|
+
this.logger.logDebug(`Filtering out test result with status: ${result.execution.status}`);
|
|
287
|
+
return;
|
|
288
|
+
}
|
|
284
289
|
await this.startTestRunOperation;
|
|
285
290
|
this.logTestItem(result);
|
|
286
291
|
if (this.useFallback) {
|
|
@@ -308,6 +313,23 @@ class QaseReporter {
|
|
|
308
313
|
}
|
|
309
314
|
}
|
|
310
315
|
}
|
|
316
|
+
/**
|
|
317
|
+
* @param {TestResultType} result
|
|
318
|
+
* @private
|
|
319
|
+
*/
|
|
320
|
+
shouldFilterResult(result) {
|
|
321
|
+
const statusFilter = this.options.testops?.statusFilter;
|
|
322
|
+
if (!statusFilter || statusFilter.length === 0) {
|
|
323
|
+
return false;
|
|
324
|
+
}
|
|
325
|
+
// Convert TestStatusEnum to string for comparison
|
|
326
|
+
const statusString = result.execution.status.toString();
|
|
327
|
+
this.logger.logDebug(`Checking filter: status="${statusString}", filter=${JSON.stringify(statusFilter)}`);
|
|
328
|
+
// Check if the status is in the filter list
|
|
329
|
+
const shouldFilter = statusFilter.includes(statusString);
|
|
330
|
+
this.logger.logDebug(`Filter result: ${shouldFilter ? 'FILTERED' : 'NOT FILTERED'}`);
|
|
331
|
+
return shouldFilter;
|
|
332
|
+
}
|
|
311
333
|
/**
|
|
312
334
|
* @param {TestResultType} result
|
|
313
335
|
* @private
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { TestStatusEnum } from '../models/test-execution';
|
|
2
|
+
/**
|
|
3
|
+
* Determines test status based on error type
|
|
4
|
+
* @param error - Error object or null
|
|
5
|
+
* @param originalStatus - Original test status from test runner
|
|
6
|
+
* @returns TestStatusEnum - failed for assertion errors, invalid for other errors
|
|
7
|
+
*/
|
|
8
|
+
export declare function determineTestStatus(error: Error | null, originalStatus: string): TestStatusEnum;
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.determineTestStatus = void 0;
|
|
4
|
+
const test_execution_1 = require("../models/test-execution");
|
|
5
|
+
/**
|
|
6
|
+
* Determines test status based on error type
|
|
7
|
+
* @param error - Error object or null
|
|
8
|
+
* @param originalStatus - Original test status from test runner
|
|
9
|
+
* @returns TestStatusEnum - failed for assertion errors, invalid for other errors
|
|
10
|
+
*/
|
|
11
|
+
function determineTestStatus(error, originalStatus) {
|
|
12
|
+
// If no error, return the original status
|
|
13
|
+
if (!error) {
|
|
14
|
+
return mapOriginalStatus(originalStatus);
|
|
15
|
+
}
|
|
16
|
+
// Check if it's an assertion error
|
|
17
|
+
if (isAssertionError(error)) {
|
|
18
|
+
return test_execution_1.TestStatusEnum.failed;
|
|
19
|
+
}
|
|
20
|
+
// For all other errors, return invalid
|
|
21
|
+
return test_execution_1.TestStatusEnum.invalid;
|
|
22
|
+
}
|
|
23
|
+
exports.determineTestStatus = determineTestStatus;
|
|
24
|
+
/**
|
|
25
|
+
* Checks if error is an assertion error
|
|
26
|
+
* @param error - Error object
|
|
27
|
+
* @returns boolean - true if assertion error
|
|
28
|
+
*/
|
|
29
|
+
function isAssertionError(error) {
|
|
30
|
+
const errorMessage = error.message.toLowerCase();
|
|
31
|
+
const errorStack = error.stack?.toLowerCase() || '';
|
|
32
|
+
// Common assertion error patterns
|
|
33
|
+
const assertionPatterns = [
|
|
34
|
+
'expect',
|
|
35
|
+
'assert',
|
|
36
|
+
'matcher',
|
|
37
|
+
'assertion',
|
|
38
|
+
'expected',
|
|
39
|
+
'actual',
|
|
40
|
+
'to be',
|
|
41
|
+
'to equal',
|
|
42
|
+
'to contain',
|
|
43
|
+
'to match',
|
|
44
|
+
'to throw',
|
|
45
|
+
'to be called',
|
|
46
|
+
'to have been called',
|
|
47
|
+
'test failed',
|
|
48
|
+
'expectation failed',
|
|
49
|
+
'assertion failed'
|
|
50
|
+
];
|
|
51
|
+
// Non-assertion error patterns that should be invalid
|
|
52
|
+
const nonAssertionPatterns = [
|
|
53
|
+
'syntaxerror',
|
|
54
|
+
'referenceerror',
|
|
55
|
+
'typeerror',
|
|
56
|
+
'network',
|
|
57
|
+
'timeout',
|
|
58
|
+
'connection',
|
|
59
|
+
'http',
|
|
60
|
+
'fetch',
|
|
61
|
+
'axios',
|
|
62
|
+
'cors',
|
|
63
|
+
'permission',
|
|
64
|
+
'access denied',
|
|
65
|
+
'unauthorized',
|
|
66
|
+
'forbidden',
|
|
67
|
+
'not found',
|
|
68
|
+
'server error',
|
|
69
|
+
'internal error'
|
|
70
|
+
];
|
|
71
|
+
// Check for non-assertion patterns first
|
|
72
|
+
const hasNonAssertionPattern = nonAssertionPatterns.some(pattern => errorMessage.includes(pattern) || errorStack.includes(pattern));
|
|
73
|
+
if (hasNonAssertionPattern) {
|
|
74
|
+
return false;
|
|
75
|
+
}
|
|
76
|
+
// Check error message and stack for assertion patterns
|
|
77
|
+
const hasAssertionPattern = assertionPatterns.some(pattern => errorMessage.includes(pattern) || errorStack.includes(pattern));
|
|
78
|
+
// Check for specific error types that indicate assertions
|
|
79
|
+
const isJestMatcherError = error.name === 'Error' &&
|
|
80
|
+
(errorMessage.includes('expect') || errorMessage.includes('matcher'));
|
|
81
|
+
const isChaiAssertionError = error.name === 'AssertionError';
|
|
82
|
+
const isPlaywrightAssertionError = error.name === 'Error' &&
|
|
83
|
+
(errorMessage.includes('expect') || errorMessage.includes('assert'));
|
|
84
|
+
return hasAssertionPattern || isJestMatcherError || isChaiAssertionError || isPlaywrightAssertionError;
|
|
85
|
+
}
|
|
86
|
+
/**
|
|
87
|
+
* Maps original test runner status to TestStatusEnum
|
|
88
|
+
* @param originalStatus - Original status from test runner
|
|
89
|
+
* @returns TestStatusEnum
|
|
90
|
+
*/
|
|
91
|
+
function mapOriginalStatus(originalStatus) {
|
|
92
|
+
const statusMap = {
|
|
93
|
+
'passed': test_execution_1.TestStatusEnum.passed,
|
|
94
|
+
'failed': test_execution_1.TestStatusEnum.failed,
|
|
95
|
+
'skipped': test_execution_1.TestStatusEnum.skipped,
|
|
96
|
+
'disabled': test_execution_1.TestStatusEnum.disabled,
|
|
97
|
+
'pending': test_execution_1.TestStatusEnum.skipped,
|
|
98
|
+
'todo': test_execution_1.TestStatusEnum.disabled,
|
|
99
|
+
'focused': test_execution_1.TestStatusEnum.passed,
|
|
100
|
+
'timedOut': test_execution_1.TestStatusEnum.failed,
|
|
101
|
+
'interrupted': test_execution_1.TestStatusEnum.failed,
|
|
102
|
+
};
|
|
103
|
+
return statusMap[originalStatus] || test_execution_1.TestStatusEnum.skipped;
|
|
104
|
+
}
|