1   
2   
3   
4   
5   
6   
7   
8   
9   
10  
11  
12  
13  
14  
15  
16  package org.kuali.rice.krad.demo.uif.library.collections;
17  
18  import org.apache.commons.lang.StringUtils;
19  import org.apache.commons.lang.math.RandomUtils;
20  import org.junit.After;
21  import org.junit.Before;
22  import org.junit.Test;
23  import org.kuali.rice.krad.demo.uif.library.LibraryBase;
24  import org.kuali.rice.krad.uif.UifConstants;
25  import org.kuali.rice.testtools.selenium.WebDriverUtils;
26  import org.openqa.selenium.By;
27  import org.openqa.selenium.WebElement;
28  
29  import java.util.List;
30  import java.util.concurrent.TimeUnit;
31  
32  
33  
34  
35  public class LibraryCollectionFeaturesEditLineAft extends LibraryBase {
36  
37      
38  
39  
40      public static final String BOOKMARK_URL = "/kr-krad/kradsampleapp?viewId=Demo-CollectionEditLineView";
41      public static final int FIVE_SECOND_WAIT_TIME = 5;
42      public static final int THREE_SECOND_WAIT_TIME = 3000;
43      public static final String LIBRARY_MENU_CATEGORY_NAME = "Collection Features";
44      public static final String DEMO_ITEM_NAME = "Edit Line";
45  
46      public enum SubCollectionType {
47          ROW_DETAILS, SUB_COLLECTION, CUSTOM_SUB_COLLECTION, NO_SUB_COLLECTION
48      }
49  
50      public static final String UIF_DIALOG_MODAL_SELECTOR = "#Uif-Dialogs .modal[aria-hidden='false']";
51      public static final String ADD_BUTTON_CSS_SELECTOR =
52              " .uif-collectionAddItem  .uif-collection-column-action button";
53      public static final String ADD_FIELDS_CSS_SELECTOR = " .uif-collectionAddItem input:not([type='hidden'])";
54      public static final String EDIT_BUTTON_CSS_SELECTOR =
55              " tr:not(.uif-collectionAddItem) .uif-collection-column-action button[data-onclick^='"
56                      + UifConstants.JsFunctions.SHOW_EDIT_LINE_DIALOG + "']";
57      public static final String ADD_FIELDS_IN_DIALOG_CSS_SELECTOR =
58              UIF_DIALOG_MODAL_SELECTOR + " .modal-body .uif-inputField input:not([type='hidden'])";
59      public static final String ADD_LINE_ACTIONS_IN_DIALOG_CSS_SELECTOR =
60              UIF_DIALOG_MODAL_SELECTOR + " .modal-footer button[id$='_add']";
61      public static final String EDIT_DIALOG_BUTTONS_CSS_SELECTOR =
62              UIF_DIALOG_MODAL_SELECTOR + " .modal-footer button";
63      public static final String EDIT_DIALOG_CLOSE_BUTTON_CSS_SELECTOR =
64              UIF_DIALOG_MODAL_SELECTOR + " .modal-header button.close";
65      public static final String EDIT_DIALOG_INPUT_FIELDS_CSS_SELECTOR =
66              UIF_DIALOG_MODAL_SELECTOR + " .modal-body input:not([type='hidden'])";
67      public static final String EDIT_DIALOG_LOOKUP_CSS_SELECTOR =
68              UIF_DIALOG_MODAL_SELECTOR + " .modal-body .input-group-btn > button";
69      public static final String EDIT_DIALOG_CSS_SELECTOR =
70              UIF_DIALOG_MODAL_SELECTOR + " .modal-body";
71      public static final String ROW_DETAILS_LINK_CSS_SELECTOR =
72              " table tbody tr:not(.uif-collectionAddItem) a.uif-detailsAction";
73      public static final String TABLE_ROWS_CSS_SELECTOR = " table tbody tr:not(.uif-collectionAddItem)";
74      public static final String SUB_COLLECTION_CSS_SELECTOR =
75              " table tbody > tr:not(.uif-collectionAddItem) > td > div.uif-subCollection";
76  
77      @Before
78      @Override
79      public void testSetUp() {
80          super.testSetUp();
81          getDriver().manage().timeouts().implicitlyWait(1, TimeUnit.SECONDS);
82      }
83  
84      @After
85      @Override
86      public void tearDown() {
87          getDriver().manage().timeouts().implicitlyWait(WebDriverUtils.configuredImplicityWait(), TimeUnit.SECONDS);
88          super.tearDown();
89      }
90  
91      
92  
93  
94      @Override
95      protected String getBookmarkUrl() {
96          return BOOKMARK_URL;
97      }
98  
99      
100 
101 
102     @Override
103     protected void navigate() throws Exception {
104         navigateToLibraryDemo(LibraryCollectionFeaturesEditLineAft.LIBRARY_MENU_CATEGORY_NAME,
105                 LibraryCollectionFeaturesEditLineAft.DEMO_ITEM_NAME);
106     }
107 
108     
109 
110 
111     protected void testDefaultEditLine() throws Exception {
112         testAllFeatures("Demo-CollectionEditLine-Example1", 1, 1, false, false, false,
113                 SubCollectionType.NO_SUB_COLLECTION, -1);
114     }
115 
116     
117 
118 
119     protected void testCustomDialogEditLine1() throws Exception {
120         waitAndSelectByName("exampleShown", "Custom Dialog Edit Line 1");
121         testAllFeatures("Demo-CollectionEditLine-Example2", 1, 1, false, false, false,
122                 SubCollectionType.NO_SUB_COLLECTION, -1);
123     }
124 
125     
126 
127 
128     protected void testCustomDialogEditLine2() throws Exception {
129         waitAndSelectByName("exampleShown", "Custom Dialog Edit Line 2");
130         testAllFeatures("Demo-CollectionEditLine-Example3", 2, 1, false, false, false,
131                 SubCollectionType.NO_SUB_COLLECTION, -1);
132     }
133 
134     
135 
136 
137     protected void testCustomDialogLineActionEditLine() throws Exception {
138         waitAndSelectByName("exampleShown", "Custom Dialog Line Action Edit Line");
139         testAllFeatures("Demo-CollectionEditLine-Example4", 2, 2, false, false, false,
140                 SubCollectionType.NO_SUB_COLLECTION, -1);
141     }
142 
143     
144 
145 
146     protected void testCustomDialogSaveActionEditLine() throws Exception {
147         waitAndSelectByName("exampleShown", "Custom Dialog Save Action Edit Line");
148         testAllFeatures("Demo-CollectionEditLine-Example5", 2, 2, true, false, false,
149                 SubCollectionType.NO_SUB_COLLECTION, -1);
150     }
151 
152     
153 
154 
155     protected void testReadOnlyEditLine() throws Exception {
156         waitAndSelectByName("exampleShown", "ReadOnly Edit Line");
157         testAllFeatures("Demo-CollectionEditLine-Example6", 2, 1, false, true, false,
158                 SubCollectionType.NO_SUB_COLLECTION, -1);
159     }
160 
161     
162 
163 
164     protected void testEditAuthorizationEditLineCollectionReadOnly() throws Exception {
165         waitAndSelectByName("exampleShown", "Edit Authorization Edit Line (collection readOnly)");
166         verifyCollectionRowFieldsAreNonEditable("Demo-CollectionEditLine-Example7");
167     }
168 
169     
170 
171 
172     protected void testEditAuthorizationEditLineLineAuthorization() throws Exception {
173         waitAndSelectByName("exampleShown", "Edit Authorization Edit Line (line authorization)");
174         testAllFeatures("Demo-CollectionEditLine-Example8", 1, 1, false, false, true,
175                 SubCollectionType.NO_SUB_COLLECTION, -1);
176     }
177 
178     
179 
180 
181     protected void testLookup() throws Exception {
182         waitAndSelectByName("exampleShown", "Lookup Collection Edit Line");
183         testAllFeatures("Demo-CollectionEditLine-Example9", 2, 2, false, false, false,
184                 SubCollectionType.NO_SUB_COLLECTION, 1);
185     }
186 
187     
188 
189 
190     protected void testRowDetailsGroup() throws Exception {
191         waitAndSelectByName("exampleShown", "Row Details Edit Line");
192         testAllFeatures("Demo-CollectionEditLine-Example10", 1, 1, false, false, false, SubCollectionType.ROW_DETAILS,
193                 -1);
194     }
195 
196     
197 
198 
199     protected void testSubCollection() throws Exception {
200         waitAndSelectByName("exampleShown", "SubCollection Edit Line");
201         testAllFeatures("Demo-CollectionEditLine-Example11", 1, 1, false, false, false,
202                 SubCollectionType.SUB_COLLECTION, -1);
203     }
204 
205     
206 
207 
208     protected void testCollectionFeaturesEditLine() throws Exception {
209         jGrowl("Calling testReadOnlyEditLine");
210         testReadOnlyEditLine();
211         jGrowl("Calling testEditAuthorizationEditLineCollectionReadOnly");
212         testEditAuthorizationEditLineCollectionReadOnly();
213         jGrowl("Calling testEditAuthorizationEditLineLineAuthorization");
214         testEditAuthorizationEditLineLineAuthorization();
215         jGrowl("Calling testLookup");
216         testLookup();
217         
218         
219     }
220 
221     
222 
223 
224 
225 
226 
227 
228 
229 
230 
231 
232 
233     protected void testAllFeatures(String exampleId, int lineFieldToEditIndex, int dialogFieldToEditIndex,
234             boolean custom, boolean readOnly, boolean auth, SubCollectionType subCollectionType,
235             int lookupFieldToEditIndex) throws Exception {
236         waitFor(By.cssSelector("jQuery('#" + exampleId + "')"));
237         verifyCollectionRowFieldsAreNonEditable(exampleId);
238         verifyAddLineAndDeleteLineStillWork(exampleId, readOnly, subCollectionType);
239         verifyEditInDialogWorks(exampleId, lineFieldToEditIndex, dialogFieldToEditIndex, custom, auth,
240                 subCollectionType, readOnly, lookupFieldToEditIndex);
241     }
242 
243     
244 
245 
246 
247 
248 
249 
250 
251 
252 
253 
254 
255     protected void verifyEditInDialogWorks(String exampleId, int lineFieldToEditIndex, int dialogFieldToEditIndex,
256             boolean custom, boolean auth, SubCollectionType subCollectionType, boolean readOnly,
257             int lookupFieldToEditIndex) throws Exception {
258         int rowElementsSize = 0;
259 
260         
261         if (subCollectionType != SubCollectionType.SUB_COLLECTION
262                 && subCollectionType != SubCollectionType.CUSTOM_SUB_COLLECTION) {
263             List<WebElement> rowElements = findVisibleElements(By.cssSelector(
264                     "#" + exampleId + TABLE_ROWS_CSS_SELECTOR));
265             rowElementsSize = rowElements.size();
266         } else {
267             List<WebElement> rowElements = findVisibleElements(By.cssSelector(
268                     "#" + exampleId + " table:nth-child(1) tbody > tr:not(.uif-collectionAddItem)"));
269             List<WebElement> subCollectionElements = findVisibleElements(By.cssSelector(
270                     "#" + exampleId + SUB_COLLECTION_CSS_SELECTOR));
271             rowElementsSize = rowElements.size() - subCollectionElements.size();
272         }
273         verifyCollectionRowsHaveEditButtons(exampleId, rowElementsSize);
274 
275         if (auth) {
276             return;
277         }
278 
279         
280         int index = RandomUtils.nextInt(rowElementsSize) + 1; 
281 
282         
283         if (subCollectionType == SubCollectionType.ROW_DETAILS) {
284             
285             WebElement rowDetailsAchorElement = findElements(By.cssSelector(
286                     "#" + exampleId + ROW_DETAILS_LINK_CSS_SELECTOR)).get(index - 1);
287             rowDetailsAchorElement.click();
288         }
289 
290         if (subCollectionType == SubCollectionType.NO_SUB_COLLECTION) {
291             
292             verifyDialogEdit(exampleId, lineFieldToEditIndex, dialogFieldToEditIndex, true, false, custom, index,
293                     readOnly, lookupFieldToEditIndex);
294 
295             
296             verifyDialogEdit(exampleId, lineFieldToEditIndex, dialogFieldToEditIndex, false, false, custom, index,
297                     readOnly, lookupFieldToEditIndex);
298 
299             
300             verifyDialogEdit(exampleId, lineFieldToEditIndex, dialogFieldToEditIndex, false, true, custom, index,
301                     readOnly, lookupFieldToEditIndex);
302         } else {
303             
304             
305             String dialogCssSelector = EDIT_DIALOG_CSS_SELECTOR;
306             String tableRowsCssSelector = "#" + exampleId + TABLE_ROWS_CSS_SELECTOR;
307 
308             
309             if (subCollectionType == SubCollectionType.ROW_DETAILS) {
310                 verifyRowDetails(exampleId, dialogCssSelector, tableRowsCssSelector, index);
311             } else if (subCollectionType == SubCollectionType.SUB_COLLECTION) {
312                 verifyRowSubCollections(exampleId, dialogCssSelector, tableRowsCssSelector, index);
313             }
314         }
315     }
316 
317     
318 
319 
320 
321 
322 
323 
324 
325     protected void verifyRowDetails(String exampleId, String dialogCssSelector, String tableRowsCssSelector, int index)
326             throws Exception {
327         String subCollectionFieldCssSelector =
328                 "#" + exampleId + " table tbody tr.detailsRow td.uif-rowDetails > div > div.uif-inputField > span";
329         String dialogSubCollectionFieldCssSelector =
330                 dialogCssSelector + " > div > div.uif-inputField > input:not([type='hidden'])";
331         String subCollectionRowsCssSelector =
332                 tableRowsCssSelector + " td.uif-rowDetails section " + TABLE_ROWS_CSS_SELECTOR;
333         String dialogSubCollectionRowsCssSelector = dialogCssSelector + " section " + TABLE_ROWS_CSS_SELECTOR;
334         String dialogSubCollectionAddLineButtonCssSelector = dialogCssSelector + " section " + ADD_BUTTON_CSS_SELECTOR;
335         String dialogSubCollectionAddLineFieldsCssSelector = dialogCssSelector + " section " + ADD_FIELDS_CSS_SELECTOR;
336         String dialogSubCollectionAddedLineFieldsCssSelector =
337                 dialogCssSelector + " section table tr:not(.uif-collectionAddItem)";
338         String dialogSubCollectionDeleteLineButtonCssSelector = dialogCssSelector
339                 + " section table tr:not(.uif-collectionAddItem) .uif-collection-column-action button";
340         int dialogSubCollectionFieldIndex = 2;
341 
342         verifySubCollections(exampleId, index, subCollectionFieldCssSelector, dialogSubCollectionFieldCssSelector,
343                 subCollectionRowsCssSelector, dialogSubCollectionRowsCssSelector,
344                 dialogSubCollectionAddLineButtonCssSelector, dialogSubCollectionAddLineFieldsCssSelector,
345                 dialogSubCollectionAddedLineFieldsCssSelector, dialogSubCollectionDeleteLineButtonCssSelector,
346                 dialogCssSelector, dialogSubCollectionFieldIndex);
347     }
348 
349     
350 
351 
352 
353 
354 
355 
356 
357     protected void verifyRowSubCollections(String exampleId, String dialogCssSelector, String tableRowsCssSelector,
358             int index) throws Exception {
359         int dialogSubCollectionFieldIndex = 0;
360         String subCollectionRowsCssSelector =
361                 "#" + exampleId + " table > tbody > tr:not(.uif-collectionAddItem):nth-child(" + Integer.toString(
362                         index * 2) + ") > td > div.uif-subCollection section " + TABLE_ROWS_CSS_SELECTOR;
363         String dialogSubCollectionRowsCssSelector =
364                 dialogCssSelector + " > div > div.uif-subCollection section " + TABLE_ROWS_CSS_SELECTOR;
365         String dialogSubCollectionAddLineButtonCssSelector =
366                 dialogCssSelector + " > div > div.uif-subCollection section " + ADD_BUTTON_CSS_SELECTOR;
367         String dialogSubCollectionAddLineFieldsCssSelector =
368                 dialogCssSelector + " > div > div.uif-subCollection section " + ADD_FIELDS_CSS_SELECTOR;
369         String dialogSubCollectionAddedLineFieldsCssSelector =
370                 dialogCssSelector + " > div > div.uif-subCollection section table tr:not(.uif-collectionAddItem)";
371         String dialogSubCollectionDeleteLineButtonCssSelector = dialogCssSelector
372                 + " > div > div.uif-subCollection section table tr:not(.uif-collectionAddItem) .uif-collection-column-action button";
373 
374         verifySubCollections(exampleId, index, null, null, subCollectionRowsCssSelector,
375                 dialogSubCollectionRowsCssSelector, dialogSubCollectionAddLineButtonCssSelector,
376                 dialogSubCollectionAddLineFieldsCssSelector, dialogSubCollectionAddedLineFieldsCssSelector,
377                 dialogSubCollectionDeleteLineButtonCssSelector, dialogCssSelector, dialogSubCollectionFieldIndex);
378     }
379 
380     
381 
382 
383 
384 
385 
386 
387 
388 
389 
390 
391 
392 
393 
394 
395 
396 
397     protected void verifySubCollections(String exampleId, int rowIndex, String subCollectionFieldCssSelector,
398             String dialogSubCollectionFieldCssSelector, String subCollectionRowsCssSelector,
399             String dialogSubCollectionRowsCssSelector, String dialogSubCollectionAddLineButtonCssSelector,
400             String dialogSubCollectionAddLineFieldsCssSelector, String dialogSubCollectionAddedLineFieldsCssSelector,
401             String dialogSubCollectionDeleteLineButtonCssSelector, String dialogCssSelector,
402             int dialogSubCollectionFieldIndex) throws Exception {
403 
404         String subCollectionFieldValue = null;
405         if (subCollectionFieldCssSelector != null) {
406             
407             WebElement subCollectionRowField = findElement(By.cssSelector(subCollectionFieldCssSelector));
408             subCollectionFieldValue = subCollectionRowField.getText();
409         }
410 
411         
412         openEditLineDialog(exampleId, rowIndex);
413 
414         WebElement dialogSubCollectionField = null;
415         String dialogSubCollectionFieldValue = null;
416         if (dialogSubCollectionFieldCssSelector != null) {
417             
418             List<WebElement> dialogFields = findElements(By.cssSelector(dialogSubCollectionFieldCssSelector));
419             dialogSubCollectionField = dialogFields.get(dialogSubCollectionFieldIndex);
420             dialogSubCollectionFieldValue = dialogSubCollectionField.getAttribute("value");
421         }
422 
423         if (subCollectionFieldValue != null && dialogSubCollectionFieldValue != null) {
424             assertEquals("Dialog field the sub-collection is in does not match that of the line.",
425                     subCollectionFieldValue, dialogSubCollectionFieldValue);
426         }
427 
428         
429         if (dialogSubCollectionField != null) {
430             dialogSubCollectionField.sendKeys("sub");
431         }
432 
433         
434         List<WebElement> dialogSubCollectionAddLineRowFields = findElements(By.cssSelector(
435                 dialogSubCollectionAddLineFieldsCssSelector));
436         int index = 1;
437         for (WebElement element : dialogSubCollectionAddLineRowFields) {
438             element.sendKeys("add" + Integer.toString(index));
439             index++;
440         }
441 
442         
443         WebElement subCollectionAddLineButton = findElement(By.cssSelector(
444                 dialogSubCollectionAddLineButtonCssSelector));
445         subCollectionAddLineButton.click();
446         waitForProgress("Adding Line...", WebDriverUtils.configuredImplicityWait() * 15);
447         waitFor(By.cssSelector(dialogCssSelector));
448 
449         
450         List<WebElement> dialogSubCollectionAddedLineRows = findElements(By.cssSelector(
451                 dialogSubCollectionAddedLineFieldsCssSelector));
452         assertTrue("Dialog rows count is 0", dialogSubCollectionAddedLineRows.size() > 0);
453         List<WebElement> dialogSubCollectionAddedLineRowFields = dialogSubCollectionAddedLineRows.get(0).
454                 findElements(By.cssSelector(" td > div.uif-inputField > input:not([type='hidden'])"));
455         index = 1;
456         for (WebElement element : dialogSubCollectionAddedLineRowFields) {
457             assertEquals("Added line fields in the sub-collection do not match.", "add" + Integer.toString(index),
458                     element.getText());
459             index++;
460         }
461 
462         
463         if (subCollectionFieldCssSelector != null && dialogSubCollectionFieldCssSelector != null) {
464             
465             WebElement subCollectionRowField = findElement(By.cssSelector(
466                     "#" + exampleId + subCollectionFieldCssSelector));
467             subCollectionFieldValue = subCollectionRowField.getText();
468             List<WebElement> dialogFields = findElements(By.cssSelector(dialogSubCollectionFieldCssSelector));
469             dialogSubCollectionField = dialogFields.get(dialogSubCollectionFieldIndex);
470             dialogSubCollectionFieldValue = dialogSubCollectionField.getAttribute("value");
471             assertEquals(
472                     "Changing the dialog' sub-collection field value also changed the value of that of the collection's.",
473                     subCollectionFieldValue + "sub", dialogSubCollectionFieldValue);
474         }
475 
476         
477         
478         List<WebElement> subCollectionRows = findElements(By.cssSelector(subCollectionRowsCssSelector));
479         List<WebElement> dialogSubCollectionRows = findElements(By.cssSelector(dialogSubCollectionRowsCssSelector));
480         assertEquals("Dialog sub-collection rows size after add line match those of the line.",
481                 subCollectionRows.size() + 1, dialogSubCollectionRows.size());
482 
483         
484         List<WebElement> buttonElements = findVisibleElements(By.cssSelector(EDIT_DIALOG_BUTTONS_CSS_SELECTOR));
485         WebElement saveButton = buttonElements.get(0);
486 
487         
488         saveButton.click();
489         waitForProgress("Editing Line...", WebDriverUtils.configuredImplicityWait() * 15);
490 
491         
492         if (subCollectionFieldCssSelector != null && dialogSubCollectionFieldCssSelector != null) {
493             WebElement subCollectionRowField = findElement(By.cssSelector(
494                     "#" + exampleId + subCollectionFieldCssSelector));
495             subCollectionFieldValue = subCollectionRowField.getText();
496             assertEquals("Saving the dialog' sub-collection field's new value did not change that of the collection's.",
497                     subCollectionFieldValue, dialogSubCollectionFieldValue);
498         }
499 
500         subCollectionRows = findElements(By.cssSelector(subCollectionRowsCssSelector));
501         assertEquals("Dialog sub-collection rows size do not match those of the line after saving changes.",
502                 subCollectionRows.size(), dialogSubCollectionRows.size());
503 
504         
505         verifySubCollectionActionMakesNoChanges(exampleId, rowIndex, dialogSubCollectionDeleteLineButtonCssSelector,
506                 subCollectionRowsCssSelector, dialogSubCollectionRowsCssSelector, false);
507 
508         
509         verifySubCollectionActionMakesNoChanges(exampleId, rowIndex, dialogSubCollectionDeleteLineButtonCssSelector,
510                 subCollectionRowsCssSelector, dialogSubCollectionRowsCssSelector, true);
511     }
512 
513     
514 
515 
516 
517 
518 
519 
520 
521 
522 
523 
524     protected void verifySubCollectionActionMakesNoChanges(String exampleId, int rowIndex,
525             String dialogSubCollectionDeleteLineButtonCssSelector, String subCollectionRowsCssSelector,
526             String dialogSubCollectionRowsCssSelector, boolean close) throws Exception {
527         
528         openEditLineDialog(exampleId, rowIndex);
529 
530         
531         WebElement subCollectionDeleteButton = waitAndGetElementsFor(By.cssSelector(
532                 dialogSubCollectionDeleteLineButtonCssSelector), "Could not find delete button.").get(0);
533         subCollectionDeleteButton.click();
534         waitForProgress("Editing Line...", WebDriverUtils.configuredImplicityWait() * 15);
535         waitFor(By.cssSelector(EDIT_DIALOG_CSS_SELECTOR));
536 
537         
538         List<WebElement> dialogSubCollectionRows = waitAndGetElementsFor(By.cssSelector(
539                 dialogSubCollectionRowsCssSelector), "Could not get sub-collection rows.");
540 
541         
542         WebElement button = null;
543         if (close) {
544             button = waitFor(By.cssSelector(EDIT_DIALOG_CLOSE_BUTTON_CSS_SELECTOR));
545         } else {
546             List<WebElement> buttons = waitAndGetElementsFor(By.cssSelector(
547                     EDIT_DIALOG_BUTTONS_CSS_SELECTOR), "Could not find buttons.");
548             button = buttons.get(1);
549         }
550         button.click();
551         waitForProgressLoading();
552 
553         
554         List<WebElement> subCollectionRows = waitAndGetElementsFor(By.cssSelector(subCollectionRowsCssSelector),
555                 "Cannot see elements.");
556         assertEquals("Dialog sub-collection rows size after delete line match those of the line.",
557                 subCollectionRows.size() - 1, dialogSubCollectionRows.size());
558     }
559 
560     
561 
562 
563 
564 
565 
566 
567 
568 
569 
570 
571 
572 
573 
574     protected void verifyDialogEdit(String exampleId, int lineFieldToEditIndex, int dialogFieldToEditIndex,
575             boolean save, boolean close, boolean custom, int rowIndex, boolean readOnly, int lookupFieldToEditIndex)
576             throws Exception {
577         String tableRowsCssSelector = "#" + exampleId + TABLE_ROWS_CSS_SELECTOR;
578 
579         
580         Thread.sleep(THREE_SECOND_WAIT_TIME); 
581         List<WebElement> spanElements = findVisibleElements(By.cssSelector(tableRowsCssSelector)).get(rowIndex - 1).
582                 findElements(By.cssSelector(" div.uif-inputField > span"));
583         String field1Value = spanElements.get(0).getText();
584         String field2Value = spanElements.get(1).getText();
585         String fieldValue = spanElements.get(lineFieldToEditIndex - 1).getText();
586 
587         
588         Thread.sleep(THREE_SECOND_WAIT_TIME); 
589         openEditLineDialog(exampleId, rowIndex);
590 
591         
592         List<WebElement> inputElements = findElements(By.cssSelector(EDIT_DIALOG_INPUT_FIELDS_CSS_SELECTOR));
593 
594         if (inputElements.isEmpty()) {
595             jiraAwareFail("inputElements should not be empty for example " + exampleId);
596         }
597 
598         if (custom && !save) {
599             fieldValue = inputElements.get(dialogFieldToEditIndex - 1).getAttribute("value");
600         }
601 
602         
603         if (lookupFieldToEditIndex >= 0) {
604             WebElement lookup = waitFor(By.cssSelector(EDIT_DIALOG_LOOKUP_CSS_SELECTOR));
605             lookup.click();
606 
607             
608             WebElement lookupDialogFrame = waitFor(By.cssSelector("#Uif-DialogGroup-Lookup iframe"));
609             getDriver().switchTo().frame(lookupDialogFrame);
610 
611             List<WebElement> buttons = findElements(By.cssSelector(".uif-footer button"));
612 
613             WebElement searchButton = buttons.get(2);
614             searchButton.click();
615             waitForProgressLoading();
616 
617             List<WebElement> searchResults = findElements(By.cssSelector(
618                     ".uif-lookupPage section table > tbody > tr > td.uif-collection-column-action a"));
619 
620             
621             int searchResultIndex = RandomUtils.nextInt(searchResults.size());
622 
623             List<WebElement> searchResultValues = findElements(By.cssSelector(
624                     ".uif-lookupPage section table > tbody > tr > td.sorting_1 a"));
625 
626             WebElement searchResultPickedAnchor = searchResults.get(searchResultIndex);
627             WebElement searchResultPicked = searchResultValues.get(searchResultIndex);
628 
629             String resultValue = searchResultPicked.getText();
630             searchResultPickedAnchor.click();
631 
632             
633             getDriver().switchTo().defaultContent();
634 
635             
636             waitFor(By.cssSelector(EDIT_DIALOG_CSS_SELECTOR));
637             inputElements = findElements(By.cssSelector(EDIT_DIALOG_INPUT_FIELDS_CSS_SELECTOR));
638             verifyDialogField(inputElements.get(lookupFieldToEditIndex - 1), "", resultValue);
639             if (save) {
640                 if (lookupFieldToEditIndex == 1) {
641                     field1Value = resultValue;
642                 } else if (lookupFieldToEditIndex == 2) {
643                     field2Value = resultValue;
644                 }
645             }
646         }
647 
648         
649         String editString = "edit";
650         verifyDialogField(inputElements.get(dialogFieldToEditIndex - 1), editString, fieldValue);
651 
652         
653         
654         if (!readOnly && lineFieldToEditIndex % 2 < inputElements.size() && spanElements.size() != inputElements
655                 .size()) {
656             verifyDialogField(inputElements.get(dialogFieldToEditIndex % 2), null, spanElements.get(
657                     lineFieldToEditIndex % 2).getText());
658         }
659 
660         
661         List<WebElement> buttonElements = waitAndGetElementsFor(By.cssSelector(
662                 EDIT_DIALOG_BUTTONS_CSS_SELECTOR), "Could not find buttons.");
663         WebElement saveButton = buttonElements.get(0);
664         WebElement noButton = buttonElements.get(1);
665 
666         
667         if (close) {
668             noButton = findElement(By.cssSelector(EDIT_DIALOG_CLOSE_BUTTON_CSS_SELECTOR));
669         }
670 
671         if (save) {
672             
673             saveButton.click();
674         } else {
675             
676             noButton.click();
677         }
678         waitForProgress("Editing Line...", WebDriverUtils.configuredImplicityWait() * 15);
679 
680         
681         spanElements = findVisibleElements(By.cssSelector(tableRowsCssSelector)).get(rowIndex - 1).
682                 findElements(By.cssSelector(" div.uif-inputField > span"));
683         String newField1Value = spanElements.get(0).getText();
684         String newField2Value = spanElements.get(1).getText();
685 
686         
687         if (save) {
688             if (lineFieldToEditIndex == 1) {
689                 assertEquals("Saving changes did not edit the value.", field1Value + editString, newField1Value);
690                 assertEquals("Saving changes did not edit the value.", field2Value, newField2Value);
691             } else {
692                 if (custom) {
693                     assertEquals("Saving changes did not edit the value.", "Custom Edit Line " + rowIndex,
694                             newField1Value);
695                 } else {
696                     assertEquals("Saving changes did not edit the value.", field1Value, newField1Value);
697                 }
698                 if (custom) {
699                     assertEquals("Saving changes did not edit the value.", field2Value, newField2Value);
700                 } else {
701                     assertEquals("Saving changes did not edit the value.", field2Value + editString, newField2Value);
702                 }
703             }
704         } else {
705             assertEquals("Cancelling the edit line still edits the value.", field1Value, newField1Value);
706             assertEquals("Cancelling the edit line still edits the value.", field2Value, newField2Value);
707         }
708     }
709 
710     
711 
712 
713 
714 
715 
716 
717 
718 
719 
720 
721 
722 
723 
724     protected void verifyDialogField(WebElement element, String randomString, String fieldValue) throws Exception {
725         
726         String inputFieldValue = element.getAttribute("value");
727 
728         
729         assertEquals("Value of input field in dialog does not match that of the line field's value.", fieldValue,
730                 inputFieldValue);
731 
732         if (StringUtils.isNotEmpty(randomString)) {
733             
734             element.sendKeys(randomString);
735 
736             
737             String newInputFieldValue = element.getAttribute("value");
738 
739             
740             assertEquals(inputFieldValue + randomString, newInputFieldValue);
741         }
742     }
743 
744     
745 
746 
747 
748 
749 
750     protected void openEditLineDialog(String exampleId, int index) throws Exception {
751         List<WebElement> elements = findVisibleElements(By.cssSelector("#" + exampleId + EDIT_BUTTON_CSS_SELECTOR));
752         elements.get(index - 1).click();
753 
754         
755         waitFor(By.cssSelector(EDIT_DIALOG_CSS_SELECTOR));
756     }
757 
758     
759 
760 
761 
762 
763 
764 
765 
766 
767 
768     protected void verifyAddLineAndDeleteLineStillWork(String exampleId, boolean readOnly,
769             SubCollectionType subCollectionType) throws Exception {
770         if (readOnly) {
771             return;
772         }
773 
774         String randomString = "add";
775 
776         verifyAddLineStillWorks(exampleId, randomString, subCollectionType);
777         verifyDeleteLineStillWorks(exampleId);
778     }
779 
780     
781 
782 
783 
784 
785 
786 
787     protected void verifyAddLineStillWorks(String exampleId, String randomString, SubCollectionType subCollectionType)
788             throws Exception {
789         String addFieldsCssSelector = null;
790         String addLineActionCssSelector = null;
791 
792         if (subCollectionType != SubCollectionType.NO_SUB_COLLECTION) {
793             String addInDialogButtonCssSelector = "#" + exampleId + " button:first-of-type";
794             WebElement addInDialogButton = findElement(By.cssSelector(addInDialogButtonCssSelector));
795             jGrowl("Click add in dialog button");
796             addInDialogButton.click();
797             addFieldsCssSelector = ADD_FIELDS_IN_DIALOG_CSS_SELECTOR;
798             addLineActionCssSelector = ADD_LINE_ACTIONS_IN_DIALOG_CSS_SELECTOR;
799         } else {
800             addFieldsCssSelector = "#" + exampleId + ADD_FIELDS_CSS_SELECTOR;
801             addLineActionCssSelector = "#" + exampleId +  ADD_BUTTON_CSS_SELECTOR;
802         }
803 
804         List<WebElement> addFields = findElements(By.cssSelector(addFieldsCssSelector));
805 
806         int index = 1;
807         for (WebElement addField : addFields) {
808             jGrowl("Type in " + addField.getAttribute("name") + " " + randomString + index);
809             addField.sendKeys(randomString + index);
810             index++;
811         }
812 
813         WebElement buttonElement = findElement(By.cssSelector(addLineActionCssSelector));
814         jGrowl("Click add line");
815         buttonElement.click();
816         waitForProgress("Adding Line...", WebDriverUtils.configuredImplicityWait() * 15);
817         waitFor(By.cssSelector("#" + exampleId + " .uif-newCollectionItem"));
818         List<WebElement> fields = null;
819 
820         
821         
822         if (subCollectionType == SubCollectionType.NO_SUB_COLLECTION) {
823             fields = findVisibleElements(By.cssSelector("#" + exampleId +
824                     " .uif-newCollectionItem .uif-inputField span"));
825             assertEquals(addFields.size(), fields.size());
826         } else if (subCollectionType == SubCollectionType.ROW_DETAILS) {
827             fields = findVisibleElements(By.cssSelector("#" + exampleId +
828                     " .uif-newCollectionItem td:nth-of-type(2) .uif-inputField span"));
829             fields.addAll(findVisibleElements(By.cssSelector("#" + exampleId +
830                     " .uif-newCollectionItem td:nth-of-type(3) .uif-inputField span")));
831             assertEquals(addFields.size(), fields.size() + 1);
832         } else {
833             fields = findVisibleElements(By.cssSelector("#" + exampleId +
834                     " .uif-newCollectionItem td:nth-of-type(1) .uif-inputField span"));
835             fields.addAll(findVisibleElements(By.cssSelector("#" + exampleId +
836                     " .uif-newCollectionItem td:nth-of-type(2) .uif-inputField span")));
837             assertEquals(addFields.size(), fields.size() + 1);
838         }
839 
840         index = 1;
841         for (WebElement field : fields) {
842             assertEquals("Added field does not match what is in the collection.", randomString + index,
843                     field.getText());
844             index++;
845         }
846     }
847 
848     
849 
850 
851 
852 
853     protected void verifyDeleteLineStillWorks(String exampleId) throws Exception {
854         WebElement deleteAction = findElement(By.cssSelector(
855                 "#" + exampleId + " .uif-newCollectionItem .uif-collection-column-action button"));
856         deleteAction.click();
857 
858         waitForProgress("Deleting Line...", WebDriverUtils.configuredImplicityWait() * 15);
859 
860         assertIsNotVisible(By.cssSelector("#" + exampleId + " .uif-newCollectionItem"));
861     }
862 
863     
864 
865 
866 
867 
868 
869 
870     protected void verifyCollectionRowsHaveEditButtons(String exampleId, int rowsSize) {
871         List<WebElement> buttonElements = findVisibleElements(By.cssSelector(
872                 "#" + exampleId + EDIT_BUTTON_CSS_SELECTOR));
873         int buttonsSize = buttonElements.size();
874         if (rowsSize != buttonsSize) {
875             buttonsSize += 2;
876         }
877         assertEquals("The number of rows do not match the number of edit line buttons.", rowsSize, buttonsSize);
878     }
879 
880     
881 
882 
883 
884 
885 
886     protected void verifyCollectionRowFieldsAreNonEditable(String exampleId) throws Exception {
887         List<WebElement> inputFields = findElements(By.cssSelector(
888                 "#" + exampleId + " tr:not(.uif-collectionAddItem) input:not([type='hidden'])"));
889         assertTrue(inputFields.isEmpty());
890     }
891 
892     @Test
893     public void testDefaultEditLineBookmark() throws Exception {
894         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
895         testDefaultEditLine();
896         passed();
897     }
898 
899     @Test
900     public void testDefaultEditLineNav() throws Exception {
901         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
902         testDefaultEditLine();
903         passed();
904     }
905 
906     @Test
907     public void testCustomDialogEditLine1Bookmark() throws Exception {
908         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
909         testCustomDialogEditLine1();
910         passed();
911     }
912 
913     @Test
914     public void testCustomDialogEditLine1Nav() throws Exception {
915         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
916         testCustomDialogEditLine1();
917         passed();
918     }
919 
920     @Test
921     public void testCustomDialogEditLine2Bookmark() throws Exception {
922         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
923         testCustomDialogEditLine2();
924         passed();
925     }
926 
927     @Test
928     public void testCustomDialogEditLine2Nav() throws Exception {
929         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
930         testCustomDialogEditLine2();
931         passed();
932     }
933 
934     @Test
935     public void testCustomDialogLineActionEditLineBookmark() throws Exception {
936         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
937         testCustomDialogLineActionEditLine();
938         passed();
939     }
940 
941     @Test
942     public void testCustomDialogLineActionEditLineNav() throws Exception {
943         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
944         testCustomDialogLineActionEditLine();
945         passed();
946     }
947 
948     @Test
949     public void testCustomDialogSaveActionEditLineBookmark() throws Exception {
950         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
951         testCustomDialogSaveActionEditLine();
952         passed();
953     }
954 
955     @Test
956     public void testCustomDialogSaveActionEditLineNav() throws Exception {
957         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
958         testCustomDialogSaveActionEditLine();
959         passed();
960     }
961 
962     @Test
963     public void testCollectionFeaturesEditLineBookmark() throws Exception {
964         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
965         testCollectionFeaturesEditLine();
966         passed();
967     }
968 
969     @Test
970     public void testCollectionFeaturesEditLineNav() throws Exception {
971         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
972         testCollectionFeaturesEditLine();
973         passed();
974     }
975 
976     @Test
977     public void testRowDetailsGroupBookmark() throws Exception {
978         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
979         testRowDetailsGroup();
980         passed();
981     }
982 
983     @Test
984     public void testRowDetailsGroupNav() throws Exception {
985         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
986         testRowDetailsGroup();
987         passed();
988     }
989 
990     @Test
991     public void testSubCollectionBookmark() throws Exception {
992         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
993         testSubCollection();
994         passed();
995     }
996 
997     @Test
998     public void testSubCollectionNav() throws Exception {
999         this.waitSeconds = FIVE_SECOND_WAIT_TIME;
1000         testSubCollection();
1001         passed();
1002     }
1003 }