@camperaid/watest 2.5.0 → 2.5.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 +274 -129
- package/bin/watest.js +36 -2
- package/core/base.js +10 -3
- package/core/core.js +43 -15
- package/core/deps.js +211 -0
- package/core/{process_args.js → process-args.js} +8 -0
- package/core/series.js +70 -28
- package/core/settings.js +28 -10
- package/core/system.js +68 -0
- package/core/util.js +1 -1
- package/eslint.config.js +1 -1
- package/index.js +15 -3
- package/interfaces/servicer.js +13 -3
- package/logging/logging.js +1 -1
- package/logging/logpipe.js +38 -21
- package/package.json +1 -1
- package/tests/base/{t_core.js → t-core.js} +10 -3
- package/tests/base/t-system.js +59 -0
- package/tests/base/{t_throws.js → t-throws.js} +67 -0
- package/tests/base/test.js +1 -2
- package/tests/deps/samples/nested/.watestrc.js +3 -0
- package/tests/deps/samples/nested/tests/meta.js +1 -0
- package/tests/deps/samples/nested/tests/services/meta.js +1 -0
- package/tests/deps/samples/nested/tests/services/ws/meta.js +1 -0
- package/tests/deps/samples/nested/tests/services/ws/webservice/meta.js +2 -0
- package/tests/deps/samples/nested/tests/services/ws/webservice/t-ws.js +3 -0
- package/tests/deps/samples/unified/.watestrc.js +3 -0
- package/tests/deps/samples/unified/tests/e2e/meta.js +4 -0
- package/tests/deps/samples/unified/tests/e2e/pages/meta.js +1 -0
- package/tests/deps/samples/unified/tests/e2e/pages/t-example.js +3 -0
- package/tests/deps/samples/unified/tests/e2e/t-example.js +3 -0
- package/tests/deps/samples/unified/tests/integration/meta.js +3 -0
- package/tests/deps/samples/unified/tests/lib/meta.js +0 -0
- package/tests/deps/samples/unified/tests/lib/t-example.js +3 -0
- package/tests/deps/samples/unified/tests/meta.js +8 -0
- package/tests/deps/samples/unified/tests/services/meta.js +3 -0
- package/tests/deps/samples/unified/tests/services/request/meta.js +1 -0
- package/tests/deps/samples/unified/tests/services/t-example.js +3 -0
- package/tests/deps/t-parse-cell-syntax.js +6 -0
- package/tests/deps/t-parse-grid-args.js +11 -0
- package/tests/deps/t-watest-deps.js +37 -0
- package/tests/deps/t-watest-grid.js +122 -0
- package/tests/deps/test.js +63 -0
- package/tests/e2e/samples/folder/package-lock.json +3 -1
- package/tests/e2e/samples/loader/package-lock.json +3 -1
- package/tests/e2e/samples/loader/tests/meta.js +1 -1
- package/tests/e2e/samples/{loader_mixed → loader-mixed}/package-lock.json +3 -1
- package/tests/e2e/samples/{loader_multiple/tests/core → loader-mixed/tests/ui}/meta.js +1 -1
- package/tests/e2e/samples/{loader_multiple → loader-multiple}/package-lock.json +3 -1
- package/tests/e2e/samples/{loader_multiple → loader-multiple}/tests/base/meta.js +1 -1
- package/tests/e2e/samples/{loader_mixed/tests/ui → loader-multiple/tests/core}/meta.js +1 -1
- package/tests/e2e/samples/single/package-lock.json +3 -1
- package/tests/e2e/samples/{wd_mixed → wd-mixed}/package-lock.json +3 -1
- package/tests/e2e/samples/{wd_single → wd-single}/package-lock.json +3 -1
- package/tests/e2e/{t_folder.js → t-folder.js} +3 -3
- package/tests/e2e/{t_loader_mixed.js → t-loader-mixed.js} +7 -7
- package/tests/e2e/{t_loader_multiple_patterns.js → t-loader-multiple-patterns.js} +9 -9
- package/tests/e2e/{t_loader_multiple.js → t-loader-multiple.js} +8 -8
- package/tests/e2e/{t_loader.js → t-loader.js} +4 -4
- package/tests/e2e/{t_single.js → t-single.js} +3 -3
- package/tests/e2e/{t_wd_firefox_chrome_pattern.js → t-wd-firefox-chrome-pattern.js} +8 -8
- package/tests/e2e/{t_wd_firefox_chrome.js → t-wd-firefox-chrome.js} +7 -7
- package/tests/e2e/{t_wd_firefox.js → t-wd-firefox.js} +5 -5
- package/tests/e2e/{t_wd_mixed_firefox_chrome.js → t-wd-mixed-firefox-chrome.js} +9 -9
- package/tests/e2e/{t_wd_mixed_firefox.js → t-wd-mixed-firefox.js} +7 -7
- package/tests/meta.js +1 -1
- package/tests/series/build/t-pattern-filtering.js +175 -0
- package/tests/series/build/{t_webdriver_services.js → t-webdriver-services.js} +1 -0
- package/tests/series/logging/{t_failures.js → t-failures.js} +1 -1
- package/tests/series/logging/{t_success.js → t-success.js} +1 -1
- package/tests/series/logging/{t_verify.js → t-verify.js} +2 -2
- package/tests/series/meta.js +1 -0
- package/tests/series/perform/{t_failure_notest.js → t-failure-notest.js} +1 -0
- package/tests/series/perform/{t_failure.js → t-failure.js} +1 -0
- package/tests/series/perform/{t_intermittent_global.js → t-intermittent-global.js} +1 -0
- package/tests/series/perform/{t_intermittent.js → t-intermittent.js} +2 -0
- package/tests/series/perform/{t_missing_perma.js → t-missing-perma.js} +2 -0
- package/tests/series/perform/{t_nested.js → t-nested.js} +1 -0
- package/tests/series/perform/{t_perma.js → t-perma.js} +1 -0
- package/tests/series/perform/{t_success.js → t-success.js} +2 -0
- package/tests/series/servicer/mock-servicer.js +68 -0
- package/tests/series/servicer/t-nested-servicer-lifecycle.js +99 -0
- package/tests/series/servicer/t-servicer-no-services.js +53 -0
- package/tests/series/servicer/t-servicer-type-switching.js +139 -0
- package/tests/series/servicer/t-servicer.js +51 -0
- package/tests/series/test.js +1 -1
- package/tests/test.js +2 -0
- package/tests/webdriver/test.js +3 -3
- package/webdriver/{control_driver.js → control-driver.js} +1 -1
- package/webdriver/{driver_base.js → driver-base.js} +3 -1
- package/webdriver/driver.js +1 -1
- package/webdriver/session.js +57 -30
- package/tests/base/{t_api.js → t-api.js} +0 -0
- package/tests/base/{t_contains.js → t-contains.js} +0 -0
- package/tests/base/{t_format.js → t-format.js} +0 -0
- package/tests/base/{t_is_object.js → t-is-object.js} +0 -0
- package/tests/base/{t_is_primitive.js → t-is-primitive.js} +0 -0
- package/tests/base/{t_is_string.js → t-is-string.js} +0 -0
- package/tests/base/{t_is.js → t-is.js} +0 -0
- package/tests/base/{t_ok.js → t-ok.js} +0 -0
- package/tests/base/{t_stringify.js → t-stringify.js} +0 -0
- package/tests/base/{t_test_.js → t-test-.js} +0 -0
- package/tests/e2e/samples/folder/tests/unit/{t_test.js → t-test.js} +0 -0
- package/tests/e2e/samples/{loader_multiple/tests/module_mock.js → loader/tests/module-mock.js} +0 -0
- package/tests/e2e/samples/loader/tests/{t_test.js → t-test.js} +0 -0
- package/tests/e2e/samples/{loader_mixed → loader-mixed}/.watestrc.js +0 -0
- package/tests/e2e/samples/{loader_mixed → loader-mixed}/package.json +0 -0
- package/tests/e2e/samples/{loader_mixed → loader-mixed}/tests/meta.js +0 -0
- package/tests/e2e/samples/{loader/tests/module_mock.js → loader-mixed/tests/module-mock.js} +0 -0
- package/tests/e2e/samples/{loader_mixed → loader-mixed}/tests/module.js +0 -0
- package/tests/e2e/samples/{loader_mixed/tests/ui/t_test.js → loader-mixed/tests/ui/t-test.js} +0 -0
- package/tests/e2e/samples/{loader_mixed/tests/unit/t_test.js → loader-mixed/tests/unit/t-test.js} +0 -0
- package/tests/e2e/samples/{loader_multiple → loader-multiple}/.watestrc.js +0 -0
- package/tests/e2e/samples/{loader_multiple → loader-multiple}/package.json +0 -0
- package/tests/e2e/samples/{loader_multiple/tests/base/t_btest.js → loader-multiple/tests/base/t-btest.js} +0 -0
- package/tests/e2e/samples/{loader_multiple/tests/core/t_ctest.js → loader-multiple/tests/core/t-ctest.js} +0 -0
- package/tests/e2e/samples/{loader_multiple → loader-multiple}/tests/meta.js +0 -0
- package/tests/e2e/samples/{loader_mixed/tests/module_mock.js → loader-multiple/tests/module-mock.js} +0 -0
- package/tests/e2e/samples/{loader_multiple → loader-multiple}/tests/module.js +0 -0
- package/tests/e2e/samples/single/tests/{t_test.js → t-test.js} +0 -0
- package/tests/e2e/samples/{wd_mixed → wd-mixed}/.watestrc.js +0 -0
- package/tests/e2e/samples/{wd_mixed → wd-mixed}/package.json +0 -0
- package/tests/e2e/samples/{wd_mixed → wd-mixed}/tests/meta.js +0 -0
- package/tests/e2e/samples/{wd_mixed → wd-mixed}/tests/ui/meta.js +0 -0
- package/tests/e2e/samples/{wd_mixed/tests/ui/t_test.js → wd-mixed/tests/ui/t-test.js} +0 -0
- package/tests/e2e/samples/{wd_mixed/tests/unit/t_test.js → wd-mixed/tests/unit/t-test.js} +0 -0
- package/tests/e2e/samples/{wd_single → wd-single}/.watestrc.js +0 -0
- package/tests/e2e/samples/{wd_single → wd-single}/package.json +0 -0
- package/tests/e2e/samples/{wd_single → wd-single}/tests/meta.js +0 -0
- package/tests/e2e/samples/{wd_single/tests/t_test.js → wd-single/tests/t-test.js} +0 -0
- package/tests/series/build/{t_adjust_names_webdriver.js → t-adjust-names-webdriver.js} +0 -0
- package/tests/series/build/{t_adjust_names.js → t-adjust-names.js} +0 -0
- package/tests/series/build/{t_expected_failures.js → t-expected-failures.js} +0 -0
- package/tests/series/build/{t_loader_mixed.js → t-loader-mixed.js} +0 -0
- package/tests/series/build/{t_loader.js → t-loader.js} +0 -0
- package/tests/series/build/{t_mixed.js → t-mixed.js} +0 -0
- package/tests/series/build/{t_nested.js → t-nested.js} +0 -0
- package/tests/series/build/{t_patterns_loader.js → t-patterns-loader.js} +0 -0
- package/tests/series/build/{t_patterns_webdriver.js → t-patterns-webdriver.js} +0 -0
- package/tests/series/build/{t_webdriver_firefox_mixed.js → t-webdriver-firefox-mixed.js} +0 -0
- package/tests/series/build/{t_webdriver_nested.js → t-webdriver-nested.js} +0 -0
- package/tests/series/build/{t_webdriver.js → t-webdriver.js} +0 -0
- package/tests/series/generic/{t_failures_info.js → t-failures-info.js} +0 -0
- package/tests/series/{mock_series.js → mock-series.js} +0 -0
- package/tests/series/run/{t_debunk_failure.js → t-debunk-failure.js} +1 -1
- package/tests/series/run/{t_debunk_success.js → t-debunk-success.js} +1 -1
- package/tests/series/run/{t_nested.js → t-nested.js} +1 -1
- package/tests/series/run/{t_verify_webdriver.js → t-verify-webdriver.js} +1 -1
- package/tests/series/run/{t_verify.js → t-verify.js} +1 -1
- /package/tests/webdriver/{t_app_driver_selectors.js → t-app-driver-selectors.js} +0 -0
- /package/tests/webdriver/{t_app_driver.js → t-app-driver.js} +0 -0
- /package/tests/webdriver/{t_attribute_all.js → t-attribute-all.js} +0 -0
- /package/tests/webdriver/{t_attribute.js → t-attribute.js} +0 -0
- /package/tests/webdriver/{t_doubleclick.js → t-doubleclick.js} +0 -0
- /package/tests/webdriver/{t_doubleclickat.js → t-doubleclickat.js} +0 -0
- /package/tests/webdriver/{t_execute.js → t-execute.js} +0 -0
- /package/tests/webdriver/{t_if_has_elements.js → t-if-has-elements.js} +0 -0
- /package/tests/webdriver/{t_if_no_elements.js → t-if-no-elements.js} +0 -0
- /package/tests/webdriver/{t_no_elements_or_not_visible.js → t-no-elements-or-not-visible.js} +0 -0
- /package/tests/webdriver/{t_properties.js → t-properties.js} +0 -0
- /package/tests/webdriver/{t_script.js → t-script.js} +0 -0
- /package/tests/webdriver/{t_select_all.js → t-select-all.js} +0 -0
- /package/tests/webdriver/{t_selection.js → t-selection.js} +0 -0
- /package/tests/webdriver/{t_text_all.js → t-text-all.js} +0 -0
- /package/tests/webdriver/{t_text.js → t-text.js} +0 -0
- /package/webdriver/{app_driver.js → app-driver.js} +0 -0
|
@@ -0,0 +1,175 @@
|
|
|
1
|
+
import { is, MockSeries } from '../test.js';
|
|
2
|
+
|
|
3
|
+
export async function test() {
|
|
4
|
+
// Test that buildSubtests only processes subfolders that match patterns
|
|
5
|
+
// This test tracks which directories are actually accessed to verify the optimization
|
|
6
|
+
|
|
7
|
+
const accessedDirs = [];
|
|
8
|
+
|
|
9
|
+
class TrackingMockSeries extends MockSeries {
|
|
10
|
+
loadTestMeta(folder) {
|
|
11
|
+
accessedDirs.push(folder);
|
|
12
|
+
return super.loadTestMeta(folder);
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
getTestFileList(folder) {
|
|
16
|
+
accessedDirs.push(folder);
|
|
17
|
+
return super.getTestFileList(folder);
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
const ts = {
|
|
22
|
+
'tests': {
|
|
23
|
+
meta: {
|
|
24
|
+
folders: ['unit', 'integration', 'e2e'],
|
|
25
|
+
},
|
|
26
|
+
},
|
|
27
|
+
'tests/unit': {
|
|
28
|
+
meta: {
|
|
29
|
+
folders: ['base', 'core'],
|
|
30
|
+
},
|
|
31
|
+
},
|
|
32
|
+
'tests/unit/base': {
|
|
33
|
+
files: ['t_test1.js'],
|
|
34
|
+
},
|
|
35
|
+
'tests/unit/base/t_test1.js': {
|
|
36
|
+
test() {},
|
|
37
|
+
},
|
|
38
|
+
'tests/unit/core': {
|
|
39
|
+
files: ['t_test2.js'],
|
|
40
|
+
},
|
|
41
|
+
'tests/unit/core/t_test2.js': {
|
|
42
|
+
test() {},
|
|
43
|
+
},
|
|
44
|
+
'tests/integration': {
|
|
45
|
+
files: ['t_integration.js'],
|
|
46
|
+
},
|
|
47
|
+
'tests/integration/t_integration.js': {
|
|
48
|
+
test() {},
|
|
49
|
+
},
|
|
50
|
+
'tests/e2e': {
|
|
51
|
+
files: ['t_e2e.js'],
|
|
52
|
+
},
|
|
53
|
+
'tests/e2e/t_e2e.js': {
|
|
54
|
+
test() {},
|
|
55
|
+
},
|
|
56
|
+
};
|
|
57
|
+
|
|
58
|
+
const series = new TrackingMockSeries([], { ts });
|
|
59
|
+
|
|
60
|
+
// Test 1: When targeting a specific test, only relevant folders should be processed
|
|
61
|
+
accessedDirs.length = 0; // Clear the array
|
|
62
|
+
|
|
63
|
+
const tests = await series.build({
|
|
64
|
+
patterns: [
|
|
65
|
+
{
|
|
66
|
+
path: 'tests/unit/base/t_test1.js',
|
|
67
|
+
webdriver: '',
|
|
68
|
+
},
|
|
69
|
+
],
|
|
70
|
+
folder: 'tests',
|
|
71
|
+
virtual_folder: 'mac',
|
|
72
|
+
});
|
|
73
|
+
series.shutdown();
|
|
74
|
+
|
|
75
|
+
// Should only build the unit folder and its relevant subfolders
|
|
76
|
+
// Should NOT build integration or e2e folders
|
|
77
|
+
const testNames = getAllTestNames(tests);
|
|
78
|
+
|
|
79
|
+
// Should include the targeted test and its path
|
|
80
|
+
is(
|
|
81
|
+
testNames.includes('mac/unit/base/t_test1.js'),
|
|
82
|
+
true,
|
|
83
|
+
'Should include the targeted test',
|
|
84
|
+
);
|
|
85
|
+
|
|
86
|
+
// Should NOT include tests from unrelated folders
|
|
87
|
+
is(
|
|
88
|
+
testNames.includes('mac/integration/t_integration.js'),
|
|
89
|
+
false,
|
|
90
|
+
'Should not include integration tests when targeting unit test',
|
|
91
|
+
);
|
|
92
|
+
|
|
93
|
+
is(
|
|
94
|
+
testNames.includes('mac/e2e/t_e2e.js'),
|
|
95
|
+
false,
|
|
96
|
+
'Should not include e2e tests when targeting unit test',
|
|
97
|
+
);
|
|
98
|
+
|
|
99
|
+
// Check directory access optimization - this will fail with commented optimization
|
|
100
|
+
is(
|
|
101
|
+
accessedDirs.includes('tests/integration'),
|
|
102
|
+
false,
|
|
103
|
+
'Should not access integration directory when targeting unit test',
|
|
104
|
+
);
|
|
105
|
+
|
|
106
|
+
is(
|
|
107
|
+
accessedDirs.includes('tests/e2e'),
|
|
108
|
+
false,
|
|
109
|
+
'Should not access e2e directory when targeting unit test',
|
|
110
|
+
);
|
|
111
|
+
|
|
112
|
+
// Test 2: When no patterns specified, all folders should be processed
|
|
113
|
+
accessedDirs.length = 0; // Clear the array
|
|
114
|
+
|
|
115
|
+
const allTests = await series.build({
|
|
116
|
+
patterns: [],
|
|
117
|
+
folder: 'tests',
|
|
118
|
+
virtual_folder: 'mac',
|
|
119
|
+
});
|
|
120
|
+
|
|
121
|
+
const allTestNames = getAllTestNames(allTests);
|
|
122
|
+
|
|
123
|
+
// Should include all tests when no patterns specified
|
|
124
|
+
is(
|
|
125
|
+
allTestNames.includes('mac/unit/base/t_test1.js'),
|
|
126
|
+
true,
|
|
127
|
+
'Should include unit test when no patterns',
|
|
128
|
+
);
|
|
129
|
+
|
|
130
|
+
is(
|
|
131
|
+
allTestNames.includes('mac/integration/t_integration.js'),
|
|
132
|
+
true,
|
|
133
|
+
'Should include integration test when no patterns',
|
|
134
|
+
);
|
|
135
|
+
|
|
136
|
+
is(
|
|
137
|
+
allTestNames.includes('mac/e2e/t_e2e.js'),
|
|
138
|
+
true,
|
|
139
|
+
'Should include e2e test when no patterns',
|
|
140
|
+
);
|
|
141
|
+
|
|
142
|
+
// When no patterns, all directories should be accessed
|
|
143
|
+
is(
|
|
144
|
+
accessedDirs.includes('tests/integration'),
|
|
145
|
+
true,
|
|
146
|
+
'Should access integration directory when no patterns specified',
|
|
147
|
+
);
|
|
148
|
+
|
|
149
|
+
is(
|
|
150
|
+
accessedDirs.includes('tests/e2e'),
|
|
151
|
+
true,
|
|
152
|
+
'Should access e2e directory when no patterns specified',
|
|
153
|
+
);
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
function getAllTestNames(tests) {
|
|
157
|
+
const names = [];
|
|
158
|
+
|
|
159
|
+
function collectNames(testList) {
|
|
160
|
+
for (const test of testList) {
|
|
161
|
+
if (test.subtests) {
|
|
162
|
+
collectNames(test.subtests);
|
|
163
|
+
} else if (
|
|
164
|
+
test.name &&
|
|
165
|
+
!test.name.includes('/init') &&
|
|
166
|
+
!test.name.includes('/uninit')
|
|
167
|
+
) {
|
|
168
|
+
names.push(test.name);
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
collectNames(tests);
|
|
174
|
+
return names;
|
|
175
|
+
}
|
|
@@ -6,7 +6,7 @@ import {
|
|
|
6
6
|
stderr_format_failure,
|
|
7
7
|
success,
|
|
8
8
|
} from '../test.js';
|
|
9
|
-
import settings from '../../../core/settings.js';
|
|
9
|
+
import { settings } from '../../../core/settings.js';
|
|
10
10
|
|
|
11
11
|
const completed_in = name => got => got.startsWith(`>${name} completed in`);
|
|
12
12
|
|
|
@@ -146,7 +146,7 @@ export async function test() {
|
|
|
146
146
|
is(
|
|
147
147
|
buffers,
|
|
148
148
|
[
|
|
149
|
-
['log', [
|
|
149
|
+
['log', [got => got.startsWith('Elapsed:')]],
|
|
150
150
|
[
|
|
151
151
|
'mac/log',
|
|
152
152
|
[
|
package/tests/series/meta.js
CHANGED
|
@@ -26,6 +26,7 @@ export async function test() {
|
|
|
26
26
|
'>t_testo.js has 1 warnings(s)',
|
|
27
27
|
'>t_testo.js completed in',
|
|
28
28
|
'\x1B[38;5;243mCompleted\x1B[0m tests/',
|
|
29
|
+
'Testsuite: shutdown',
|
|
29
30
|
];
|
|
30
31
|
let expected_stderr = [];
|
|
31
32
|
|
|
@@ -77,6 +78,7 @@ export async function test() {
|
|
|
77
78
|
'>t_testo_2.js has 3 warnings(s)',
|
|
78
79
|
'>t_testo_2.js completed in',
|
|
79
80
|
'\x1B[38;5;243mCompleted\x1B[0m tests/',
|
|
81
|
+
'Testsuite: shutdown',
|
|
80
82
|
];
|
|
81
83
|
expected_stderr = [];
|
|
82
84
|
|
|
@@ -33,6 +33,7 @@ export async function test() {
|
|
|
33
33
|
'!Running: t_testo.js, path: t_testo.js',
|
|
34
34
|
'>t_testo.js completed in',
|
|
35
35
|
'\x1B[38;5;243mCompleted\x1B[0m tests/',
|
|
36
|
+
'Testsuite: shutdown',
|
|
36
37
|
],
|
|
37
38
|
[
|
|
38
39
|
'\x1B[31mFailed:\x1B[0m Server busy',
|
|
@@ -79,6 +80,7 @@ export async function test() {
|
|
|
79
80
|
'>t_testo.js has 1 warnings(s)',
|
|
80
81
|
'>t_testo.js completed in',
|
|
81
82
|
'\x1B[38;5;243mCompleted\x1B[0m tests/',
|
|
83
|
+
'Testsuite: shutdown',
|
|
82
84
|
],
|
|
83
85
|
[],
|
|
84
86
|
'no perma but intermittent',
|
|
@@ -18,6 +18,7 @@ export async function test() {
|
|
|
18
18
|
'\x1B[32mOk:\x1B[0m Successio!',
|
|
19
19
|
'>t_testo.js completed in',
|
|
20
20
|
'\x1B[38;5;243mCompleted\x1B[0m tests/',
|
|
21
|
+
'Testsuite: shutdown',
|
|
21
22
|
],
|
|
22
23
|
[],
|
|
23
24
|
'success',
|
|
@@ -53,6 +54,7 @@ export async function test() {
|
|
|
53
54
|
'\x1B[32mOk:\x1B[0m Successio!',
|
|
54
55
|
'>t_testo.js completed in',
|
|
55
56
|
'\x1B[38;5;243mCompleted\x1B[0m tests/',
|
|
57
|
+
'Testsuite: shutdown',
|
|
56
58
|
],
|
|
57
59
|
[],
|
|
58
60
|
'success #2',
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { log } from '../../../logging/logging.js';
|
|
2
|
+
import { MockSeries } from '../mock-series.js';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Mock servicer for testing servicer lifecycle.
|
|
6
|
+
* Logs all operations for test validation.
|
|
7
|
+
*/
|
|
8
|
+
class MockServicer {
|
|
9
|
+
constructor(type) {
|
|
10
|
+
this.type = type;
|
|
11
|
+
this.services = new Set();
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
async init(services) {
|
|
15
|
+
log(`MockServicer:${this.type} init`);
|
|
16
|
+
if (services) {
|
|
17
|
+
for (const service of services) {
|
|
18
|
+
await this.start(service);
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
async deinit(services) {
|
|
24
|
+
log(`MockServicer:${this.type} deinit`);
|
|
25
|
+
if (services) {
|
|
26
|
+
for (const service of [...services].reverse()) {
|
|
27
|
+
await this.stop(service);
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
async start(service) {
|
|
33
|
+
log(`MockServicer:${this.type} starting ${service}`);
|
|
34
|
+
this.services.add(service);
|
|
35
|
+
return { started: service, type: this.type };
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
async stop(service) {
|
|
39
|
+
log(`MockServicer:${this.type} stopping ${service}`);
|
|
40
|
+
this.services.delete(service);
|
|
41
|
+
return { stopped: service, type: this.type };
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
async shutdown() {
|
|
45
|
+
const servicesStr =
|
|
46
|
+
this.services.size > 0
|
|
47
|
+
? ` (services still running: ${Array.from(this.services).join(', ')})`
|
|
48
|
+
: '';
|
|
49
|
+
log(`MockServicer:${this.type} shutdown${servicesStr}`);
|
|
50
|
+
return { shutdown: true, type: this.type };
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
async ontest() {
|
|
54
|
+
return null;
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* MockSeries with servicer support.
|
|
60
|
+
* Creates MockServicer instances for testing.
|
|
61
|
+
*/
|
|
62
|
+
class MockSeriesWithServicer extends MockSeries {
|
|
63
|
+
createServicer(type) {
|
|
64
|
+
return new MockServicer(type || 'docker');
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
export { MockServicer, MockSeriesWithServicer };
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
import { is_test_output, success } from '../../base/test.js';
|
|
2
|
+
import { MockSeriesWithServicer } from './mock-servicer.js';
|
|
3
|
+
|
|
4
|
+
export async function test() {
|
|
5
|
+
const ts = {
|
|
6
|
+
'tests': {
|
|
7
|
+
meta: {
|
|
8
|
+
servicer: 'docker',
|
|
9
|
+
services: ['db', 'cache'],
|
|
10
|
+
folders: ['nested'],
|
|
11
|
+
},
|
|
12
|
+
files: ['t_parent.js'],
|
|
13
|
+
},
|
|
14
|
+
'tests/t_parent.js': {
|
|
15
|
+
test() {
|
|
16
|
+
success('Parent test works');
|
|
17
|
+
},
|
|
18
|
+
},
|
|
19
|
+
'tests/nested': {
|
|
20
|
+
meta: {
|
|
21
|
+
servicer: 'docker',
|
|
22
|
+
services: ['worker', 'queue'],
|
|
23
|
+
},
|
|
24
|
+
files: ['t_child.js'],
|
|
25
|
+
},
|
|
26
|
+
'tests/nested/t_child.js': {
|
|
27
|
+
test() {
|
|
28
|
+
success('Child test works');
|
|
29
|
+
},
|
|
30
|
+
},
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
await is_test_output(
|
|
34
|
+
() => MockSeriesWithServicer.run([], { ts }),
|
|
35
|
+
[
|
|
36
|
+
'Settings: no temporary storage dir',
|
|
37
|
+
'Settings: logging into /tmp',
|
|
38
|
+
'Settings: chrome webdrivers',
|
|
39
|
+
'\x1B[38;5;99mStarted\x1B[0m mac/',
|
|
40
|
+
|
|
41
|
+
// Parent folder init - starts parent services
|
|
42
|
+
'!Running: mac/init, path: tests/meta.js',
|
|
43
|
+
'MockServicer:docker init',
|
|
44
|
+
'MockServicer:docker starting db',
|
|
45
|
+
'MockServicer:docker starting cache',
|
|
46
|
+
'>mac/init completed in',
|
|
47
|
+
|
|
48
|
+
// Parent test
|
|
49
|
+
'!Running: mac/t_parent.js, path: tests/t_parent.js',
|
|
50
|
+
'\x1B[32mOk:\x1B[0m Parent test works',
|
|
51
|
+
'>mac/t_parent.js completed in',
|
|
52
|
+
|
|
53
|
+
// Nested folder starts
|
|
54
|
+
'\x1B[38;5;99mStarted\x1B[0m mac/nested',
|
|
55
|
+
|
|
56
|
+
// Nested folder init - starts child services (parent services still running)
|
|
57
|
+
'!Running: mac/nested/init, path: tests/nested/meta.js',
|
|
58
|
+
'MockServicer:docker init',
|
|
59
|
+
'MockServicer:docker starting worker',
|
|
60
|
+
'MockServicer:docker starting queue',
|
|
61
|
+
'>mac/nested/init completed in',
|
|
62
|
+
|
|
63
|
+
// Child test
|
|
64
|
+
'!Running: mac/nested/t_child.js, path: tests/nested/t_child.js',
|
|
65
|
+
'\x1B[32mOk:\x1B[0m Child test works',
|
|
66
|
+
'>mac/nested/t_child.js completed in',
|
|
67
|
+
|
|
68
|
+
// Critical: nested uninit should only stop child services, NOT shutdown servicer
|
|
69
|
+
'!Running: mac/nested/uninit, path: tests/nested/meta.js',
|
|
70
|
+
'MockServicer:docker deinit',
|
|
71
|
+
'MockServicer:docker stopping queue',
|
|
72
|
+
'MockServicer:docker stopping worker',
|
|
73
|
+
// Should NOT see "MockServicer:docker shutdown" here!
|
|
74
|
+
'>mac/nested/uninit completed in',
|
|
75
|
+
|
|
76
|
+
'\x1B[38;5;243mCompleted\x1B[0m mac/nested',
|
|
77
|
+
'Logs are written to',
|
|
78
|
+
|
|
79
|
+
// Parent uninit - stops parent services
|
|
80
|
+
'!Running: mac/uninit, path: tests/meta.js',
|
|
81
|
+
'MockServicer:docker deinit',
|
|
82
|
+
'MockServicer:docker stopping cache',
|
|
83
|
+
'MockServicer:docker stopping db',
|
|
84
|
+
'>mac/uninit completed in',
|
|
85
|
+
|
|
86
|
+
'\x1B[102mSuccess!\x1B[0m Total: 2',
|
|
87
|
+
'\x1B[38;5;243mCompleted\x1B[0m mac/',
|
|
88
|
+
'Logs are written to',
|
|
89
|
+
'Elapsed:',
|
|
90
|
+
'Logs are written to',
|
|
91
|
+
|
|
92
|
+
// Final shutdown should happen here with no remaining services
|
|
93
|
+
'MockServicer:docker shutdown',
|
|
94
|
+
'Testsuite: shutdown',
|
|
95
|
+
],
|
|
96
|
+
[],
|
|
97
|
+
'nested servicer lifecycle - no premature shutdown',
|
|
98
|
+
);
|
|
99
|
+
}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import { is_test_output, success } from '../../base/test.js';
|
|
2
|
+
import { MockSeriesWithServicer } from './mock-servicer.js';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Test that a folder can specify servicer type without services.
|
|
6
|
+
* This is useful when you want to select an environment (e.g., kubernetes)
|
|
7
|
+
* without starting any services.
|
|
8
|
+
*/
|
|
9
|
+
export async function test() {
|
|
10
|
+
const ts = {
|
|
11
|
+
'tests': {
|
|
12
|
+
meta: {
|
|
13
|
+
servicer: 'kubernetes', // Just select the servicer type, no services
|
|
14
|
+
},
|
|
15
|
+
files: ['t_example.js'],
|
|
16
|
+
},
|
|
17
|
+
'tests/t_example.js': {
|
|
18
|
+
test() {
|
|
19
|
+
success('Test in kubernetes environment works');
|
|
20
|
+
},
|
|
21
|
+
},
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
await is_test_output(
|
|
25
|
+
() => MockSeriesWithServicer.run([], { ts }),
|
|
26
|
+
[
|
|
27
|
+
'Settings: no temporary storage dir',
|
|
28
|
+
'Settings: logging into /tmp',
|
|
29
|
+
'Settings: chrome webdrivers',
|
|
30
|
+
'\x1B[38;5;99mStarted\x1B[0m mac/',
|
|
31
|
+
'!Running: mac/init, path: tests/meta.js',
|
|
32
|
+
'MockServicer:kubernetes init',
|
|
33
|
+
// No services started - init is called with undefined/empty
|
|
34
|
+
'>mac/init completed in',
|
|
35
|
+
'!Running: mac/t_example.js, path: tests/t_example.js',
|
|
36
|
+
'\x1B[32mOk:\x1B[0m Test in kubernetes environment works',
|
|
37
|
+
'>mac/t_example.js completed in',
|
|
38
|
+
'!Running: mac/uninit, path: tests/meta.js',
|
|
39
|
+
'MockServicer:kubernetes deinit',
|
|
40
|
+
// No services stopped
|
|
41
|
+
'>mac/uninit completed in',
|
|
42
|
+
'\x1B[102mSuccess!\x1B[0m Total: 1',
|
|
43
|
+
'\x1B[38;5;243mCompleted\x1B[0m mac/',
|
|
44
|
+
'Logs are written to',
|
|
45
|
+
'Elapsed:',
|
|
46
|
+
'Logs are written to',
|
|
47
|
+
'MockServicer:kubernetes shutdown',
|
|
48
|
+
'Testsuite: shutdown',
|
|
49
|
+
],
|
|
50
|
+
[],
|
|
51
|
+
'servicer without services',
|
|
52
|
+
);
|
|
53
|
+
}
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Test for Servicer Type Switching
|
|
3
|
+
*
|
|
4
|
+
* Verifies that when switching between test folders with different servicer types,
|
|
5
|
+
* the old servicer is properly shut down before creating the new one.
|
|
6
|
+
*
|
|
7
|
+
* This prevents port conflicts when transitioning between Kubernetes and Docker servicers.
|
|
8
|
+
*
|
|
9
|
+
* Test scenario:
|
|
10
|
+
* 1. Folder 1: docker servicer with services
|
|
11
|
+
* 2. Folder 2: kubernetes servicer with services
|
|
12
|
+
* 3. Folder 3: back to docker servicer with services
|
|
13
|
+
* Expected: docker → kubernetes (shutdown docker, create k8s) → docker (shutdown k8s, create docker)
|
|
14
|
+
*/
|
|
15
|
+
|
|
16
|
+
import { is_test_output, success } from '../../base/test.js';
|
|
17
|
+
import { MockSeriesWithServicer } from './mock-servicer.js';
|
|
18
|
+
|
|
19
|
+
export async function test() {
|
|
20
|
+
const ts = {
|
|
21
|
+
'tests': {
|
|
22
|
+
meta: {
|
|
23
|
+
folders: ['folder1', 'folder2', 'folder3'],
|
|
24
|
+
},
|
|
25
|
+
},
|
|
26
|
+
'tests/folder1': {
|
|
27
|
+
meta: {
|
|
28
|
+
servicer: 'docker',
|
|
29
|
+
services: ['db'],
|
|
30
|
+
},
|
|
31
|
+
files: ['t_test1.js'],
|
|
32
|
+
},
|
|
33
|
+
'tests/folder2': {
|
|
34
|
+
meta: {
|
|
35
|
+
servicer: 'kubernetes',
|
|
36
|
+
services: ['ws'],
|
|
37
|
+
},
|
|
38
|
+
files: ['t_test2.js'],
|
|
39
|
+
},
|
|
40
|
+
'tests/folder3': {
|
|
41
|
+
meta: {
|
|
42
|
+
servicer: 'docker',
|
|
43
|
+
services: ['cache'],
|
|
44
|
+
},
|
|
45
|
+
files: ['t_test3.js'],
|
|
46
|
+
},
|
|
47
|
+
'tests/folder1/t_test1.js': {
|
|
48
|
+
test() {
|
|
49
|
+
success('Test 1 in docker folder');
|
|
50
|
+
},
|
|
51
|
+
},
|
|
52
|
+
'tests/folder2/t_test2.js': {
|
|
53
|
+
test() {
|
|
54
|
+
success('Test 2 in kubernetes folder');
|
|
55
|
+
},
|
|
56
|
+
},
|
|
57
|
+
'tests/folder3/t_test3.js': {
|
|
58
|
+
test() {
|
|
59
|
+
success('Test 3 back to docker');
|
|
60
|
+
},
|
|
61
|
+
},
|
|
62
|
+
};
|
|
63
|
+
|
|
64
|
+
await is_test_output(
|
|
65
|
+
() => MockSeriesWithServicer.run([], { ts }),
|
|
66
|
+
[
|
|
67
|
+
'Settings: no temporary storage dir',
|
|
68
|
+
'Settings: logging into /tmp',
|
|
69
|
+
'Settings: chrome webdrivers',
|
|
70
|
+
'\x1B[38;5;99mStarted\x1B[0m mac/',
|
|
71
|
+
'\x1B[38;5;99mStarted\x1B[0m mac/folder1',
|
|
72
|
+
|
|
73
|
+
// Folder 1: docker servicer
|
|
74
|
+
'!Running: mac/folder1/init, path: tests/folder1/meta.js',
|
|
75
|
+
'MockServicer:docker init',
|
|
76
|
+
'MockServicer:docker starting db',
|
|
77
|
+
'>mac/folder1/init completed in',
|
|
78
|
+
|
|
79
|
+
'!Running: mac/folder1/t_test1.js, path: tests/folder1/t_test1.js',
|
|
80
|
+
'\x1B[32mOk:\x1B[0m Test 1 in docker folder',
|
|
81
|
+
'>mac/folder1/t_test1.js completed in',
|
|
82
|
+
|
|
83
|
+
'!Running: mac/folder1/uninit, path: tests/folder1/meta.js',
|
|
84
|
+
'MockServicer:docker deinit',
|
|
85
|
+
'MockServicer:docker stopping db',
|
|
86
|
+
'>mac/folder1/uninit completed in',
|
|
87
|
+
|
|
88
|
+
'\x1B[38;5;243mCompleted\x1B[0m mac/folder1',
|
|
89
|
+
'Logs are written to',
|
|
90
|
+
'\x1B[38;5;99mStarted\x1B[0m mac/folder2',
|
|
91
|
+
|
|
92
|
+
// Folder 2: switch to kubernetes servicer (no shutdown - servicer handles conflicts)
|
|
93
|
+
'!Running: mac/folder2/init, path: tests/folder2/meta.js',
|
|
94
|
+
'MockServicer:kubernetes init',
|
|
95
|
+
'MockServicer:kubernetes starting ws',
|
|
96
|
+
'>mac/folder2/init completed in',
|
|
97
|
+
|
|
98
|
+
'!Running: mac/folder2/t_test2.js, path: tests/folder2/t_test2.js',
|
|
99
|
+
'\x1B[32mOk:\x1B[0m Test 2 in kubernetes folder',
|
|
100
|
+
'>mac/folder2/t_test2.js completed in',
|
|
101
|
+
|
|
102
|
+
'!Running: mac/folder2/uninit, path: tests/folder2/meta.js',
|
|
103
|
+
'MockServicer:kubernetes deinit',
|
|
104
|
+
'MockServicer:kubernetes stopping ws',
|
|
105
|
+
'>mac/folder2/uninit completed in',
|
|
106
|
+
|
|
107
|
+
'\x1B[38;5;243mCompleted\x1B[0m mac/folder2',
|
|
108
|
+
'Logs are written to',
|
|
109
|
+
'\x1B[38;5;99mStarted\x1B[0m mac/folder3',
|
|
110
|
+
|
|
111
|
+
// Folder 3: switch back to docker servicer (no shutdown - servicer handles conflicts)
|
|
112
|
+
'!Running: mac/folder3/init, path: tests/folder3/meta.js',
|
|
113
|
+
'MockServicer:docker init',
|
|
114
|
+
'MockServicer:docker starting cache',
|
|
115
|
+
'>mac/folder3/init completed in',
|
|
116
|
+
|
|
117
|
+
'!Running: mac/folder3/t_test3.js, path: tests/folder3/t_test3.js',
|
|
118
|
+
'\x1B[32mOk:\x1B[0m Test 3 back to docker',
|
|
119
|
+
'>mac/folder3/t_test3.js completed in',
|
|
120
|
+
|
|
121
|
+
'!Running: mac/folder3/uninit, path: tests/folder3/meta.js',
|
|
122
|
+
'MockServicer:docker deinit',
|
|
123
|
+
'MockServicer:docker stopping cache',
|
|
124
|
+
'>mac/folder3/uninit completed in',
|
|
125
|
+
|
|
126
|
+
'\x1B[38;5;243mCompleted\x1B[0m mac/folder3',
|
|
127
|
+
'Logs are written to',
|
|
128
|
+
'\x1B[102mSuccess!\x1B[0m Total: 3',
|
|
129
|
+
'\x1B[38;5;243mCompleted\x1B[0m mac/',
|
|
130
|
+
'Logs are written to',
|
|
131
|
+
'Elapsed:',
|
|
132
|
+
'Logs are written to',
|
|
133
|
+
'MockServicer:docker shutdown',
|
|
134
|
+
'Testsuite: shutdown',
|
|
135
|
+
],
|
|
136
|
+
[],
|
|
137
|
+
'servicer type switching',
|
|
138
|
+
);
|
|
139
|
+
}
|