Skip to content

Commit cdb42e8

Browse files
Added automated tests with cypress for Zone form
1 parent 2729d56 commit cdb42e8

File tree

1 file changed

+299
-0
lines changed
  • cypress/e2e/ui/Settings/Application-Settings

1 file changed

+299
-0
lines changed
Lines changed: 299 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,299 @@
1+
/* eslint-disable no-undef */
2+
import { flashClassMap } from '../../../../support/assertions/assertion_constants';
3+
4+
// Component route url
5+
const COMPONENT_ROUTE_URL = '/ops/explorer';
6+
7+
// Menu options
8+
const SETTINGS_OPTION = 'Settings';
9+
const APP_SETTINGS_OPTION = 'Application Settings';
10+
11+
// Accordion items
12+
const MANAGEIQ_REGION_ACCORDION_ITEM = /^ManageIQ Region:/;
13+
const ZONES_ACCORDION_ITEM = 'Zones';
14+
15+
// Config options
16+
const CONFIG_TOOLBAR_BUTTON = 'Configuration';
17+
const ADD_ZONE_CONFIG_OPTION = 'Add a new Zone';
18+
const EDIT_ZONE_CONFIG_OPTION = 'Edit this Zone';
19+
const DELETE_ZONE_CONFIG_OPTION = 'Delete this Zone';
20+
21+
// Field values
22+
const NAME_FIELD_LABEL = 'Name';
23+
const DESCRIPTION_FIELD_LABEL = 'Description';
24+
const SERVER_IP_FIELD_LABEL = 'Server IP';
25+
const MAX_SCAN_FIELD_LABEL = 'VM Scans';
26+
const FORM_HEADER_FRAGMENT = 'Zone';
27+
const INFO_SUB_HEADER = 'Info';
28+
const SETTINGS_SUB_HEADER = 'Settings';
29+
const ZONE_NAME = 'Test-Zone-Name';
30+
const INITIAL_ZONE_DESCRIPTION = 'Test-Zone-Description';
31+
const UPDATED_ZONE_DESCRIPTION = 'Test-Zone-Description-Updated';
32+
const INITIAL_SERVER_IP = '0.0.0.0';
33+
const UPDATED_SERVER_IP = '1.1.1.1';
34+
const INITIAL_MAX_SCAN_LIMIT = 5;
35+
const UPDATED_MAX_SCAN_LIMIT = 10;
36+
37+
// Element ids
38+
const IP_INPUT_FIELD_ID = 'settings\\.proxy_server_ip';
39+
const MAX_SCAN_SELECT_FIELD_ID = 'settings\\.concurrent_vm_scans';
40+
41+
// Buttons
42+
const SAVE_BUTTON_TEXT = 'Save';
43+
const CANCEL_BUTTON_TEXT = 'Cancel';
44+
const ADD_BUTTON_TEXT = 'Add';
45+
const RESET_BUTTON_TEXT = 'Reset';
46+
47+
// Flash message text snippets
48+
const FLASH_MESSAGE_OPERATION_CANCELED = 'cancel';
49+
const FLASH_MESSAGE_ZONE_UPDATED = 'queued';
50+
const FLASH_MESSAGE_OPERATION_RESET = 'reset';
51+
const DELETE_CONFIRM_TEXT = 'delete';
52+
53+
function addZone() {
54+
// Open add form
55+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, ADD_ZONE_CONFIG_OPTION);
56+
// Adding name, description, ip and scan limit
57+
cy.getFormInputFieldById('name').type(ZONE_NAME);
58+
cy.getFormInputFieldById('description').type(INITIAL_ZONE_DESCRIPTION);
59+
cy.getFormInputFieldById(IP_INPUT_FIELD_ID).type(INITIAL_SERVER_IP);
60+
cy.getFormSelectFieldById(MAX_SCAN_SELECT_FIELD_ID).select(
61+
INITIAL_MAX_SCAN_LIMIT
62+
);
63+
cy.interceptApi({
64+
alias: 'createZoneApi',
65+
urlPattern: '/api/zones',
66+
triggerFn: () =>
67+
cy
68+
.getFormFooterButtonByType(ADD_BUTTON_TEXT, 'submit')
69+
.should('be.enabled')
70+
.click(),
71+
});
72+
return cy.then(() => {
73+
return `Zone: ${INITIAL_ZONE_DESCRIPTION}`;
74+
});
75+
}
76+
77+
function validateFormElements(isEditForm = false) {
78+
// Assert form header is visible
79+
cy.expect_explorer_title(FORM_HEADER_FRAGMENT);
80+
// Assert Info sub header is visible
81+
cy.get('#main-content .bx--form h3').contains(INFO_SUB_HEADER);
82+
// Assert name field label is visible
83+
cy.getFormLabelByInputId('name')
84+
.should('be.visible')
85+
.and('contain.text', NAME_FIELD_LABEL);
86+
// Assert name field is visible and enabled
87+
cy.getFormInputFieldById('name')
88+
.should('be.visible')
89+
.then((nameField) => {
90+
if (isEditForm) {
91+
expect(nameField).to.be.disabled;
92+
} else {
93+
expect(nameField).to.not.be.disabled;
94+
}
95+
});
96+
// Assert description field label is visible
97+
cy.getFormLabelByInputId('description')
98+
.should('be.visible')
99+
.and('contain.text', DESCRIPTION_FIELD_LABEL);
100+
// Assert description field is visible and enabled
101+
cy.getFormInputFieldById('description')
102+
.should('be.visible')
103+
.and('be.enabled');
104+
// Assert IP field label is visible
105+
cy.getFormLabelByInputId(IP_INPUT_FIELD_ID)
106+
.should('be.visible')
107+
.and('contain.text', SERVER_IP_FIELD_LABEL);
108+
// Assert IP field is visible and enabled
109+
cy.getFormInputFieldById(IP_INPUT_FIELD_ID)
110+
.should('be.visible')
111+
.and('be.enabled');
112+
// Assert Settings sub header is visible
113+
cy.get('#main-content .bx--form h3').contains(SETTINGS_SUB_HEADER);
114+
// Assert max scan field label is visible
115+
cy.getFormLabelByInputId(MAX_SCAN_SELECT_FIELD_ID)
116+
.should('be.visible')
117+
.and('contain.text', MAX_SCAN_FIELD_LABEL);
118+
// Assert max scan field is visible and enabled
119+
cy.getFormSelectFieldById(MAX_SCAN_SELECT_FIELD_ID)
120+
.should('be.visible')
121+
.and('be.enabled');
122+
// Assert cancel button is visible and enabled
123+
cy.getFormFooterButtonByType(CANCEL_BUTTON_TEXT)
124+
.should('be.visible')
125+
.and('be.enabled');
126+
if (isEditForm) {
127+
// Assert reset button is visible and disabled
128+
cy.getFormFooterButtonByType(RESET_BUTTON_TEXT)
129+
.should('be.visible')
130+
.and('be.disabled');
131+
}
132+
// Assert add/save button is visible and disabled
133+
cy.getFormFooterButtonByType(
134+
isEditForm ? SAVE_BUTTON_TEXT : ADD_BUTTON_TEXT,
135+
'submit'
136+
)
137+
.should('be.visible')
138+
.and('be.disabled');
139+
}
140+
141+
function cleanUp() {
142+
cy.get('li.list-group-item').each((item) => {
143+
const text = item?.text()?.trim();
144+
if (text.includes(INITIAL_ZONE_DESCRIPTION)) {
145+
// Select the zone node if it hasn't been selected yet
146+
if (!item.hasClass('node-selected')) {
147+
cy.wrap(item).click();
148+
cy.wait('@treeSelectApi');
149+
}
150+
// Deleting the zone
151+
cy.expect_browser_confirm_with_text({
152+
confirmTriggerFn: () =>
153+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, DELETE_ZONE_CONFIG_OPTION),
154+
});
155+
return false; // exit the iteration
156+
}
157+
return null; // has no impact - just to get rid of eslint warning
158+
});
159+
}
160+
161+
function selectZoneAccordionItem(childZoneNode) {
162+
cy.interceptApi({
163+
alias: 'treeSelectApi',
164+
urlPattern: /\/ops\/tree_select\?id=.*&text=.*/,
165+
triggerFn: () =>
166+
cy.selectAccordionItem([
167+
MANAGEIQ_REGION_ACCORDION_ITEM,
168+
ZONES_ACCORDION_ITEM,
169+
...(childZoneNode ? [childZoneNode] : []),
170+
]),
171+
});
172+
}
173+
174+
describe('Automate Schedule form operations: Settings > Application Settings > Settings > Zones > Configuration > Add a new Zone', () => {
175+
beforeEach(() => {
176+
cy.login();
177+
// Navigate to Application-Settings
178+
cy.menu(SETTINGS_OPTION, APP_SETTINGS_OPTION);
179+
// Expand Settings accordion panel if not already expanded
180+
cy.accordion(SETTINGS_OPTION);
181+
// Select "Zones" accordion item
182+
selectZoneAccordionItem();
183+
});
184+
185+
it('Validate the visibility and state of add form elements', () => {
186+
// Open add form
187+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, ADD_ZONE_CONFIG_OPTION);
188+
// Validate fields
189+
validateFormElements();
190+
});
191+
192+
it('Checking whether cancel button works on the add form', () => {
193+
// Open add form
194+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, ADD_ZONE_CONFIG_OPTION);
195+
// Cancelling the form
196+
cy.getFormFooterButtonByType(CANCEL_BUTTON_TEXT).click();
197+
cy.expect_flash(flashClassMap.warning, FLASH_MESSAGE_OPERATION_CANCELED);
198+
});
199+
200+
it('Checking whether add, edit & delete zone works', () => {
201+
/* ===== Add ===== */
202+
// Adding zone
203+
addZone().then((createdZone) => {
204+
// Here the createdZone will have value "Zone: Test-Zone-Description",
205+
// which is the accordion item to be selected
206+
// Assert flash message
207+
cy.expect_flash(flashClassMap.success, FLASH_MESSAGE_ZONE_UPDATED);
208+
// Select the created zone
209+
selectZoneAccordionItem(createdZone);
210+
});
211+
/* ===== Edit ===== */
212+
// Open edit form
213+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, EDIT_ZONE_CONFIG_OPTION);
214+
// Update IP & scan limit
215+
cy.getFormInputFieldById('description').clear().type(UPDATED_SERVER_IP);
216+
cy.getFormSelectFieldById(MAX_SCAN_SELECT_FIELD_ID).select(
217+
UPDATED_MAX_SCAN_LIMIT
218+
);
219+
// Save the form
220+
cy.getFormFooterButtonByType(SAVE_BUTTON_TEXT, 'submit')
221+
.should('be.enabled')
222+
.click();
223+
cy.expect_flash(flashClassMap.success, FLASH_MESSAGE_ZONE_UPDATED);
224+
/* ===== Delete ===== */
225+
// Deleting the zone
226+
cy.expect_browser_confirm_with_text({
227+
confirmTriggerFn: () =>
228+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, DELETE_ZONE_CONFIG_OPTION),
229+
containsText: DELETE_CONFIRM_TEXT,
230+
});
231+
cy.expect_flash(flashClassMap.success, DELETE_CONFIRM_TEXT);
232+
});
233+
234+
it('Validate the visibility and state of edit form elements', () => {
235+
// Adding zone
236+
addZone().then((createdZone) => {
237+
// Here the createdZone will have value "Zone: Test-Zone-Description",
238+
// which is the accordion item to be selected
239+
// Select the created zone
240+
selectZoneAccordionItem(createdZone);
241+
});
242+
// Open edit form
243+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, EDIT_ZONE_CONFIG_OPTION);
244+
// Validate fields
245+
validateFormElements(true);
246+
// Cancelling the form
247+
cy.getFormFooterButtonByType(CANCEL_BUTTON_TEXT).click();
248+
});
249+
250+
it('Checking whether cancel & reset buttons work on the edit form', () => {
251+
// Adding zone
252+
addZone().then((createdZone) => {
253+
// Here the createdZone will have value "Zone: Test-Zone-Description",
254+
// which is the accordion item to be selected
255+
// Select the created zone
256+
selectZoneAccordionItem(createdZone);
257+
});
258+
// Open edit form
259+
cy.toolbar(CONFIG_TOOLBAR_BUTTON, EDIT_ZONE_CONFIG_OPTION);
260+
/* ===== Reset ===== */
261+
// Update description & IP
262+
cy.getFormInputFieldById('description')
263+
.clear()
264+
.type(UPDATED_ZONE_DESCRIPTION);
265+
cy.getFormInputFieldById(IP_INPUT_FIELD_ID).clear().type(UPDATED_SERVER_IP);
266+
// Resetting the form
267+
cy.getFormFooterButtonByType(RESET_BUTTON_TEXT)
268+
.should('be.enabled')
269+
.click();
270+
cy.expect_flash(flashClassMap.warning, FLASH_MESSAGE_OPERATION_RESET);
271+
// Confirming the edited fields contain the old values after resetting
272+
cy.getFormInputFieldById('description').should(
273+
'have.value',
274+
INITIAL_ZONE_DESCRIPTION
275+
);
276+
cy.getFormInputFieldById(IP_INPUT_FIELD_ID).should(
277+
'have.value',
278+
INITIAL_SERVER_IP
279+
);
280+
/* ===== Cancel ===== */
281+
// Cancelling the form
282+
cy.getFormFooterButtonByType(CANCEL_BUTTON_TEXT).click();
283+
cy.expect_flash(flashClassMap.warning, FLASH_MESSAGE_OPERATION_CANCELED);
284+
});
285+
286+
afterEach(() => {
287+
cy.url()
288+
?.then((url) => {
289+
// Ensures navigation to Settings -> Application-Settings in the UI
290+
if (!url?.includes(COMPONENT_ROUTE_URL)) {
291+
// Navigate to Settings -> Application-Settings before cleanup
292+
cy.menu(SETTINGS_OPTION, APP_SETTINGS_OPTION);
293+
}
294+
})
295+
.then(() => {
296+
cleanUp();
297+
});
298+
});
299+
});

0 commit comments

Comments
 (0)