@suffolklitlab/alkiln 4.3.0 → 4.5.0
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/CHANGELOG.md +11 -0
- package/action.yml +8 -1
- package/cucumber.js +3 -0
- package/lib/scope.js +95 -23
- package/lib/steps.js +36 -6
- package/lib/utils/clean_reports.js +23 -0
- package/package.json +3 -3
- package/tests/features/interactive_steps.feature +22 -0
- package/tests/features/reports.feature +15 -3
package/CHANGELOG.md
CHANGED
|
@@ -40,6 +40,17 @@ Format:
|
|
|
40
40
|
-->
|
|
41
41
|
<!-- ## [Unreleased] -->
|
|
42
42
|
|
|
43
|
+
## [4.5.0] - 2022-05-23
|
|
44
|
+
- Steps that tap tabs (made using the `tabbed_templates_html` function from ALToolbox) and other arbitrary elements on the page.
|
|
45
|
+
|
|
46
|
+
## [4.4.0] - 2022-05-23
|
|
47
|
+
### Added
|
|
48
|
+
- Appends the results of the cucumber [summary formatter](https://github.com/cucumber/cucumber-js/blob/main/docs/formatters.md#summary) to the `debug_log.txt`, which includes useful stack traces into the Kiln code when tests fail.
|
|
49
|
+
|
|
50
|
+
### Fixed
|
|
51
|
+
- Prevent login info from being saved in the report or screenshots being taken on error. [#599](https://github.com/SuffolkLITLab/ALKiln/issues/559).
|
|
52
|
+
- Prevent error screenshots of screens that used a secret.
|
|
53
|
+
|
|
43
54
|
## [4.3.0] - 2022-04-07
|
|
44
55
|
### Added
|
|
45
56
|
- GitHub environment variable `MAX_SECONDS_FOR_SETUP` to set a custom maximum time for setup and takedown for packages that take a long time to load.
|
package/action.yml
CHANGED
|
@@ -29,7 +29,7 @@ inputs:
|
|
|
29
29
|
required: false
|
|
30
30
|
default: '^4.0.0'
|
|
31
31
|
MAX_SECONDS_FOR_SETUP:
|
|
32
|
-
description:
|
|
32
|
+
description: "Amount of time to give the Project to upload your package's GitHub code."
|
|
33
33
|
required: false
|
|
34
34
|
default: '120'
|
|
35
35
|
|
|
@@ -86,6 +86,13 @@ runs:
|
|
|
86
86
|
"@suffolklitlab/alkiln": "$ALKILN_VERSION"
|
|
87
87
|
}
|
|
88
88
|
}
|
|
89
|
+
EOF
|
|
90
|
+
# Keep in sync with the cucumber.js in root
|
|
91
|
+
cat << EOF > "cucumber.js"
|
|
92
|
+
module.exports = {
|
|
93
|
+
default: "--require ./lib/index.js --format progress --format summary:cucumber-report.txt"
|
|
94
|
+
}
|
|
95
|
+
EOF
|
|
89
96
|
shell: bash
|
|
90
97
|
|
|
91
98
|
# Install node
|
package/cucumber.js
ADDED
package/lib/scope.js
CHANGED
|
@@ -244,10 +244,37 @@ module.exports = {
|
|
|
244
244
|
if ( showif ) { await scope.page.waitForTimeout( scope.showif_timeout ); }
|
|
245
245
|
},
|
|
246
246
|
|
|
247
|
-
|
|
247
|
+
waitForTab: async function waitForTab(scope, tab_to_show) {
|
|
248
|
+
/**
|
|
249
|
+
* @param {tab_to_show} the aria-labeledby text of the tab panel, which
|
|
250
|
+
* we use to query and wait for that tab panel to be shown.
|
|
251
|
+
*/
|
|
252
|
+
// Implementation linked to https://github.com/SuffolkLITLab/docassemble-ALToolbox/blob/4aa1069389d2ca9cadb586f309dd73d791f081d1/docassemble/ALToolbox/misc.py#L127
|
|
253
|
+
// I think `.$()` does not use a timeout
|
|
254
|
+
if ( tab_to_show.length == 0) { return }
|
|
255
|
+
// waiting for the transitionend event: https://stackoverflow.com/a/57955251/11416267
|
|
256
|
+
await scope.page.evaluate((element_query) => {
|
|
257
|
+
return new Promise((resolve) => {
|
|
258
|
+
const elem = document.querySelector(element_query);
|
|
259
|
+
// Taken from jQuery: https://stackoverflow.com/a/33456469/11416267
|
|
260
|
+
const is_visible = !!( elem.offsetWidth || elem.offsetHeight || elem.getClientRects().length );
|
|
261
|
+
if (!is_visible) {
|
|
262
|
+
const onEnd = function() {
|
|
263
|
+
elem.removeEventListener('transitionend', onEnd);
|
|
264
|
+
resolve();
|
|
265
|
+
};
|
|
266
|
+
elem.addEventListener('transitionend', onEnd);
|
|
267
|
+
} else {
|
|
268
|
+
resolve();
|
|
269
|
+
}
|
|
270
|
+
});
|
|
271
|
+
}, `div[aria-labelledby="${tab_to_show}"]`);
|
|
272
|
+
},
|
|
273
|
+
|
|
274
|
+
afterStep: async function afterStep(scope, options = {waitForShowIf: false, tabToWaitFor: '', navigated: false, waitForTimeout: 0}) {
|
|
248
275
|
/* Common things to do after a step, including take care of errors.
|
|
249
276
|
* TODO: discuss splitting into `afterField` and `afterStep` or something. Or just change name
|
|
250
|
-
* TODO: Update to latest cucumberjs, which
|
|
277
|
+
* TODO: Update to latest cucumberjs, which has `AfterStep` */
|
|
251
278
|
|
|
252
279
|
if ( scope.page ) {
|
|
253
280
|
// Use a while loop until the below does not error with `Error: Execution context was destroyed`
|
|
@@ -274,17 +301,24 @@ module.exports = {
|
|
|
274
301
|
|
|
275
302
|
// Wait for elements that might get revealed
|
|
276
303
|
if ( options.waitForShowIf ) { await scope.waitForShowIf( scope ); }
|
|
304
|
+
if ( options.tabToWaitFor ) { await scope.waitForTab( scope, options.tabToWaitFor); }
|
|
277
305
|
} // ends if scope.page
|
|
278
306
|
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
307
|
+
if ( options.navigated ) {
|
|
308
|
+
// Reset navigation (TODO: discuss use for observational steps)
|
|
309
|
+
// TODO: Consider `daPageLoad` event
|
|
310
|
+
scope.navigated = true;
|
|
311
|
+
// Allow screenshots of the next page (may have been disabled in order to hide secret values)
|
|
312
|
+
scope.disable_error_screenshot = false;
|
|
313
|
+
} else {
|
|
314
|
+
scope.navigated = false;
|
|
315
|
+
}
|
|
282
316
|
|
|
283
317
|
// Plain old waiting. Here to avoid doing this in each individual place
|
|
284
318
|
if ( options.waitForTimeout ) { await time.waitForTimeout( options.waitForTimeout ); }
|
|
285
319
|
}, // Ends afterStep
|
|
286
320
|
|
|
287
|
-
tapElement: async function tapElement(scope, elem) {
|
|
321
|
+
tapElement: async function tapElement(scope, elem, tabToWaitFor='', waitForTimeout=0) {
|
|
288
322
|
/* Tap a given element, detect navigation, and do appropriate related things. */
|
|
289
323
|
|
|
290
324
|
// This check might never be needed now as we try to match fields on the page
|
|
@@ -297,25 +331,32 @@ module.exports = {
|
|
|
297
331
|
|
|
298
332
|
let start_url = await scope.page.url(); // so we can later check for navigation
|
|
299
333
|
|
|
300
|
-
let
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
334
|
+
let clickWait;
|
|
335
|
+
// Can't use elem[ scope.activate ](). It works locally, but errors on GitHub
|
|
336
|
+
// with "Node is not visible or not an HTMLElement". We're not using a custom Chromium version
|
|
337
|
+
// Unfortunately, this won't catch an invisible element. Hopefully we'd catch it before now...?
|
|
338
|
+
// "Tap" on mobile is more complex to implement ourselves.
|
|
339
|
+
// See https://stackoverflow.com/a/56547605/14144258
|
|
340
|
+
// and other convos around it. We haven't made it public that the device
|
|
341
|
+
// can customized. Until we do that, we'll just use "click" all the time.
|
|
342
|
+
if (!tabToWaitFor) {
|
|
343
|
+
// Click with no navigation will end immediately
|
|
344
|
+
clickWait = Promise.all([
|
|
311
345
|
elem.evaluate( (el) => { return el.click(); }),
|
|
312
346
|
scope.page.waitForNavigation({ waitUntil: 'domcontentloaded' }),
|
|
313
|
-
])
|
|
347
|
+
]);
|
|
348
|
+
} else {
|
|
349
|
+
// Same thing as above, but the promise doesn't wait for navigation.
|
|
350
|
+
clickWait = elem.evaluate( (el) => {return el.click(); });
|
|
351
|
+
}
|
|
352
|
+
// Error loads page, so no need to detect to keep things short
|
|
353
|
+
let winner = await Promise.race([
|
|
354
|
+
clickWait,
|
|
314
355
|
// This is meant to detect user-visible alerts/errors,
|
|
315
356
|
// not breaking errors in the testing code.
|
|
316
357
|
scope.page.waitForSelector('.alert-danger', { visible: true }),
|
|
317
358
|
scope.page.waitForSelector('.da-has-error', { visible: true }),
|
|
318
|
-
])
|
|
359
|
+
])
|
|
319
360
|
|
|
320
361
|
// TODO: Not sure how to detect navigation landing at same page.
|
|
321
362
|
// Maybe url change + trigger var change? Maybe just trigger var?
|
|
@@ -329,8 +370,12 @@ module.exports = {
|
|
|
329
370
|
// If navigation, wait for 200ms to let things settle down
|
|
330
371
|
await scope.afterStep(scope, {waitForTimeout: 200, navigated: navigated});
|
|
331
372
|
} else {
|
|
332
|
-
// If stay on page, wait for `show if
|
|
333
|
-
|
|
373
|
+
// If stay on page, wait for `show if`, the new tab to be loaded, or feedback elements to be move around
|
|
374
|
+
options = {waitForShowIf: !tabToWaitFor, tabToWaitFor: tabToWaitFor, navigated: navigated};
|
|
375
|
+
if (waitForTimeout > 0) {
|
|
376
|
+
options = {waitForTimeout: waitForTimeout, navigated: navigated};
|
|
377
|
+
}
|
|
378
|
+
await scope.afterStep(scope, options);
|
|
334
379
|
}
|
|
335
380
|
|
|
336
381
|
return winner;
|
|
@@ -420,13 +465,33 @@ module.exports = {
|
|
|
420
465
|
await scope.tapElement( scope, elem );
|
|
421
466
|
},
|
|
422
467
|
|
|
468
|
+
tapTab: async function ( scope, tab_id ) {
|
|
469
|
+
let elem = await scope.page.$(`#${tab_id}`);
|
|
470
|
+
let error_msg = `Couldn't find the tab with id "#${tab_id}" on the page, is there a typo?`;
|
|
471
|
+
if ( !elem ) {
|
|
472
|
+
await scope.addToReport(scope, { type: `error`, value: error_msg });
|
|
473
|
+
}
|
|
474
|
+
expect( elem, error_msg ).to.exist;
|
|
475
|
+
await scope.tapElement( scope, elem, tab_id );
|
|
476
|
+
},
|
|
477
|
+
|
|
478
|
+
tapElementBySelector: async function ( scope, selector, waitForTimeout ) {
|
|
479
|
+
let elem = await scope.page.$(`${selector}`);
|
|
480
|
+
let error_msg = `Couldn't find "${selector}" on the page, is there a typo?`;
|
|
481
|
+
if ( !elem ) {
|
|
482
|
+
await scope.addToReport(scope, { type: `error`, value: error_msg });
|
|
483
|
+
}
|
|
484
|
+
expect( elem, error_msg ).to.exist;
|
|
485
|
+
await scope.tapElement( scope, elem, '', waitForTimeout );
|
|
486
|
+
},
|
|
487
|
+
|
|
423
488
|
load: async function ( scope, file_name ) {
|
|
424
489
|
/* Try to load the page. Should we also pass a `timeout` arg or just
|
|
425
490
|
* use scope.timeout? */
|
|
426
491
|
|
|
427
492
|
// If there is no browser open, start a new one
|
|
428
493
|
if (!scope.browser) {
|
|
429
|
-
scope.browser = await scope.driver.launch({ headless: !session_vars.get_debug() });
|
|
494
|
+
scope.browser = await scope.driver.launch({ headless: !session_vars.get_debug(), devtools: session_vars.get_debug() });
|
|
430
495
|
}
|
|
431
496
|
if ( !scope.page ) { scope.page = await scope.browser.newPage(); }
|
|
432
497
|
|
|
@@ -1836,6 +1901,8 @@ module.exports = {
|
|
|
1836
1901
|
|
|
1837
1902
|
set_secret_var: async ( scope, var_name, set_to_env_name ) => {
|
|
1838
1903
|
/** Sets a non-story table variable to a "secret" value (i.e. an env var) */
|
|
1904
|
+
// Prevent pictures of a screen with a secret.
|
|
1905
|
+
scope.disable_error_screenshot = true;
|
|
1839
1906
|
let var_data = await scope.normalizeTable( scope, {
|
|
1840
1907
|
var_data: [{
|
|
1841
1908
|
var: var_name,
|
|
@@ -1963,6 +2030,9 @@ module.exports = {
|
|
|
1963
2030
|
/** Allow the developer to log a user into their server using GitHub
|
|
1964
2031
|
* secrets to authenticate.
|
|
1965
2032
|
*/
|
|
2033
|
+
// Don't take a picture of a failed login in case one of the inputs is correct
|
|
2034
|
+
scope.disable_error_screenshot = true;
|
|
2035
|
+
|
|
1966
2036
|
// If there is no browser open, start a new one
|
|
1967
2037
|
if (!scope.browser) {
|
|
1968
2038
|
scope.browser = await scope.driver.launch({ headless: !session_vars.DEBUG });
|
|
@@ -2003,8 +2073,10 @@ module.exports = {
|
|
|
2003
2073
|
|
|
2004
2074
|
await scope.addToReport( scope, {
|
|
2005
2075
|
type: `row`,
|
|
2006
|
-
value: `
|
|
2076
|
+
value: `Signed into ${ session_vars.get_da_server_url() }/user/sign-in successfully.`
|
|
2007
2077
|
});
|
|
2078
|
+
|
|
2079
|
+
await scope.afterStep(scope, {waitForShowIf: false});
|
|
2008
2080
|
}, // Ends sign_in
|
|
2009
2081
|
|
|
2010
2082
|
}, // ends scope.steps
|
package/lib/steps.js
CHANGED
|
@@ -83,6 +83,7 @@ Before(async (scenario) => {
|
|
|
83
83
|
// Device interaction
|
|
84
84
|
scope.device = 'pc';
|
|
85
85
|
scope.activate = click_with[ scope.device ];
|
|
86
|
+
scope.disable_error_screenshot = false;
|
|
86
87
|
|
|
87
88
|
scope.page_id = null;
|
|
88
89
|
|
|
@@ -390,7 +391,7 @@ When(/^(?:the user gets)?(?:I get)? to ?(?:the)?(?: ?question)?(?: id)? "([^"]+)
|
|
|
390
391
|
//#####################################
|
|
391
392
|
//#####################################
|
|
392
393
|
|
|
393
|
-
When(/I wait (\d*\.?\d+) seconds?/, { timeout: -1 }, async ( seconds ) => {
|
|
394
|
+
When(/I wait ?(?:for)? (\d*\.?\d+) seconds?/, { timeout: -1 }, async ( seconds ) => {
|
|
394
395
|
/** Wait for a specified amount of time. Can help with some race conditions.
|
|
395
396
|
* We're working on reducing race conditions, but it'll never be perfect.
|
|
396
397
|
*
|
|
@@ -706,6 +707,27 @@ When('I tap to continue', { timeout: -1 }, async () => {
|
|
|
706
707
|
);
|
|
707
708
|
});
|
|
708
709
|
|
|
710
|
+
When(/I tap the "([^"]+)" tab/i, { timeout: -1 }, async ( tabId ) => {
|
|
711
|
+
return wrapPromiseWithTimeout(
|
|
712
|
+
scope.tapTab( scope, tabId ),
|
|
713
|
+
scope.timeout
|
|
714
|
+
)
|
|
715
|
+
});
|
|
716
|
+
|
|
717
|
+
When(/I tap the "([^"]+)" element$/i, { timeout: -1 }, async ( elemSelector ) => {
|
|
718
|
+
return wrapPromiseWithTimeout(
|
|
719
|
+
scope.tapElementBySelector( scope, elemSelector, 2000 ),
|
|
720
|
+
scope.timeout
|
|
721
|
+
)
|
|
722
|
+
});
|
|
723
|
+
|
|
724
|
+
When(/I tap the "([^"]+)" element and wait ([0-9]+) second(?:s)?/i, { timeout: -1 }, async ( elemSelector, waitTime ) => {
|
|
725
|
+
return wrapPromiseWithTimeout(
|
|
726
|
+
scope.tapElementBySelector( scope, elemSelector, waitTime * 1000 ),
|
|
727
|
+
scope.timeout
|
|
728
|
+
)
|
|
729
|
+
});
|
|
730
|
+
|
|
709
731
|
|
|
710
732
|
//#####################################
|
|
711
733
|
// UI element interaction
|
|
@@ -882,11 +904,19 @@ After(async function(scenario) {
|
|
|
882
904
|
|
|
883
905
|
await scope.addToReport(scope, { type: `outcome`, value: `**-- Scenario Failed --**` });
|
|
884
906
|
if ( scope.page ) {
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
907
|
+
if ( scope.disable_error_screenshot ) {
|
|
908
|
+
scope.addToReport(scope, {
|
|
909
|
+
type: `row`,
|
|
910
|
+
value: `For security, ALKiln will not create a screenshot for this error. It's possible a secret is being used on this screen.`
|
|
911
|
+
});
|
|
912
|
+
} else {
|
|
913
|
+
// Save/download a picture of the screen that's showing during the unexpected status
|
|
914
|
+
let safe_filename = await scope.getSafeScenarioFilename( scope, { prefix: `error` });
|
|
915
|
+
await scope.page.screenshot({ path: `${ safe_filename }.jpg`, type: `jpeg`, fullPage: true });
|
|
916
|
+
} // ends if scope.disable_error_screenshot
|
|
917
|
+
} // ends if scope.page exists
|
|
918
|
+
|
|
919
|
+
} // ends if not passed
|
|
890
920
|
|
|
891
921
|
if (scenario.result.status === `FAILED`) {
|
|
892
922
|
await scope.addToReport(scope, { type: `outcome`, value: `**-- Scenario Failed --**` });
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
const fs = require('fs');
|
|
4
|
+
|
|
5
|
+
// This is hardcoded information from `cucumber.js`. Once we move to cucumber 8, we should
|
|
6
|
+
// change that the cucumber.json and actually parse the info from it.
|
|
7
|
+
let summary_file_name = 'cucumber-report.txt';
|
|
8
|
+
fs.readFile(summary_file_name, 'utf8', (err, data) => {
|
|
9
|
+
if (err) {
|
|
10
|
+
console.error(err);
|
|
11
|
+
return;
|
|
12
|
+
}
|
|
13
|
+
// Replace terminal color codes, if present
|
|
14
|
+
// https://gist.github.com/fnky/458719343aabd01cfb17a3a4f7296797#colors--graphics-mode
|
|
15
|
+
data = data.replace(/\x1b\[[0-9][0-9]?[0-9]?m/g, '');
|
|
16
|
+
const debug_log_file = 'debug_log.txt';
|
|
17
|
+
fs.appendFile(debug_log_file, data, err => {
|
|
18
|
+
if (err) {
|
|
19
|
+
console.error(err);
|
|
20
|
+
return;
|
|
21
|
+
}
|
|
22
|
+
});
|
|
23
|
+
});
|
package/package.json
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@suffolklitlab/alkiln",
|
|
3
|
-
"version": "4.
|
|
3
|
+
"version": "4.5.0",
|
|
4
4
|
"description": "Integrated automated end-to-end testing with docassemble, puppeteer, and cucumber.",
|
|
5
5
|
"main": "lib/index.js",
|
|
6
6
|
"scripts": {
|
|
7
7
|
"test": "npm run unit && npm run langs_setup && npm run cucumber -- $@",
|
|
8
|
-
"cucumber_base": "./node_modules/.bin/cucumber-js
|
|
9
|
-
"cucumber": "
|
|
8
|
+
"cucumber_base": "run_cucumber(){ ./node_modules/.bin/cucumber-js \"$@\"; status=$?; ./lib/utils/clean_reports.js; return $status; }; run_cucumber",
|
|
9
|
+
"cucumber": "run_base(){ npm run cucumber_base -- \"$@\" tests/features/*.feature; }; run_base",
|
|
10
10
|
"langs": "npm run langs_setup && ./node_modules/.bin/cucumber-js --require ./lib/index.js tests/features/*_lang*.feature",
|
|
11
11
|
"langs_setup": "./lib/utils/langs.js 'tests/features/*.feature'",
|
|
12
12
|
"langs_local": "npm run langs_setup && npm run local",
|
|
@@ -101,3 +101,25 @@ Scenario: handles settings from Github secrets
|
|
|
101
101
|
Then I see the phrase "secret-var2-value"
|
|
102
102
|
When I tap to continue
|
|
103
103
|
And I set the variable "third_text_entry" to secret "SECRET_NOT_THERE"
|
|
104
|
+
|
|
105
|
+
@i3 @tap-elements @tabs
|
|
106
|
+
Scenario: tap elements
|
|
107
|
+
Given I start the interview at "test_taps"
|
|
108
|
+
And I tap the "Tests-first_template-tab" tab
|
|
109
|
+
Then I see the phrase "Mechanics"
|
|
110
|
+
And I tap the "Tests-second_template-tab" tab
|
|
111
|
+
Then I see the phrase "villify"
|
|
112
|
+
And I tap the "Tests-third_template-tab" tab
|
|
113
|
+
Then I see the phrase "museum"
|
|
114
|
+
And I tap the "#special_event" element and wait 1 second
|
|
115
|
+
Then I see the phrase "Portishead"
|
|
116
|
+
|
|
117
|
+
@i4 @tap-elements @tabs
|
|
118
|
+
Scenario: tap element with an error
|
|
119
|
+
Given the final Scenario status should be "failed"
|
|
120
|
+
And the Scenario report should include:
|
|
121
|
+
"""
|
|
122
|
+
is there a typo?
|
|
123
|
+
"""
|
|
124
|
+
Given I start the interview at "test_taps"
|
|
125
|
+
And I tap the "Tests-not_there-tab" tab
|
|
@@ -346,7 +346,7 @@ Scenario: I can't match JSON page var to str
|
|
|
346
346
|
"""
|
|
347
347
|
|
|
348
348
|
@fast @rf22 @signin
|
|
349
|
-
Scenario: Fail with wrong email secret
|
|
349
|
+
Scenario: Fail with wrong email secret name
|
|
350
350
|
Given the final Scenario status should be "failed"
|
|
351
351
|
Given the Scenario report should include:
|
|
352
352
|
"""
|
|
@@ -355,7 +355,7 @@ Scenario: Fail with wrong email secret
|
|
|
355
355
|
Given I log on with the email "WRONG_EMAIL_NAME" and the password "USER1_PASSWORD"
|
|
356
356
|
|
|
357
357
|
@fast @rf23 @signin
|
|
358
|
-
Scenario: Fail with wrong password secret
|
|
358
|
+
Scenario: Fail with wrong password secret name
|
|
359
359
|
Given the final Scenario status should be "failed"
|
|
360
360
|
Given the Scenario report should include:
|
|
361
361
|
"""
|
|
@@ -364,7 +364,7 @@ Scenario: Fail with wrong password secret
|
|
|
364
364
|
Given I sign in with the email "USER1_EMAIL" and the password "WRONG_PASSWORD_NAME"
|
|
365
365
|
|
|
366
366
|
@fast @rf24 @signin
|
|
367
|
-
Scenario: Fail with 2 wrong signin
|
|
367
|
+
Scenario: Fail with 2 wrong signin secret names
|
|
368
368
|
Given the final Scenario status should be "failed"
|
|
369
369
|
Given the Scenario report should include:
|
|
370
370
|
"""
|
|
@@ -393,6 +393,10 @@ Scenario: Fail to find var while keeping value secret
|
|
|
393
393
|
"""
|
|
394
394
|
Did not find a field on this page for the variable "missing_var" that could be set to "SECRET_FOR_MISSING_FIELD"
|
|
395
395
|
"""
|
|
396
|
+
And the Scenario report should include:
|
|
397
|
+
"""
|
|
398
|
+
For security, ALKiln will not create a screenshot for this error.
|
|
399
|
+
"""
|
|
396
400
|
And I start the interview at "test_secret_vars"
|
|
397
401
|
And I set the var "missing_var" to the secret "SECRET_FOR_MISSING_FIELD"
|
|
398
402
|
|
|
@@ -518,3 +522,11 @@ Scenario: Report lists unused table rows
|
|
|
518
522
|
| button_continue | True | |
|
|
519
523
|
| buttons_other | button_2 | |
|
|
520
524
|
| buttons_yesnomaybe | True | |
|
|
525
|
+
|
|
526
|
+
@fast @rp3 @signin
|
|
527
|
+
Scenario: Sign in to server successfully
|
|
528
|
+
Given the Scenario report should include:
|
|
529
|
+
"""
|
|
530
|
+
Signed in
|
|
531
|
+
"""
|
|
532
|
+
Given I sign in with the email "USER1_EMAIL" and the password "USER1_PASSWORD"
|