julia_v_iluhina

Untitled

Sep 2nd, 2016
91
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Java 14.80 KB | None | 0 0
  1. /*
  2.     Запускала твой тест
  3.     гугл что-то заподозрил))
  4.     просит подтвердить личность)))
  5.     зайди в свой тестовый аккаунт вручную, успокой его
  6. */
  7.  
  8. **************************************
  9. или у меня что-то с инетом, или я не знаю что)))
  10. запускаю тесты, а они странно падают, якобы по таймауту не может тест найти поле для ввода пароля
  11. (логин в жмейле), хотя оно есть
  12.  
  13. /*
  14.     ага, красиво )
  15.  
  16.     см какой таймаут установлен для gmail теста = 45
  17.  
  18.     45 чего?
  19.     миллисекунд)
  20.     вот и ответ)
  21.  
  22.     может и правда - стоит термин timeoutMs употреблять
  23.     чтобы уменьшить вероятность вот таких ошибок
  24.  
  25.     кстати, для параметра assertThat ты так и поступила)
  26.  
  27.     думаю - стоит и в других местах подправить
  28.  
  29.     собственно - этого достаточно, чтобы тест работал
  30. */
  31. ******************************
  32. Вопрос, почему для кондишенов мы выбрали <V>? Вроде там тоже параметризуется тип.
  33.  
  34. /*
  35.     да, все верно
  36.     и для кондишенов стоит подправить)
  37. */
  38. ************************************
  39. В иерархии классов/интерфейсов для кондишенов я решила оставить, как есть.
  40. Поскольку, действительно, “добавляемые в вариант 1 интерфейсы CollectionCondition & ElementCondition -
  41.       не используются как интерфейсы, от которых имплементированы классы
  42. ”, ну и по всем тем ссылкам, которые ты дала почиать, часто говориться,
  43. что, мол делай   те с умом, чтобы было удобно и не перегружать структуру излишними элементами,
  44. которые не будут реально использоваться.
  45.  
  46. /*
  47.  
  48.     ну, да)
  49.     можно
  50.  
  51.     только -  подумай еще вот над этим
  52. */
  53.  
  54. public class CollectionConditions {
  55.  
  56.     public static Condition<List<WebElement>> sizeOf(int expectedSize)
  57.     ....
  58.  
  59. или
  60.  
  61. public class CollectionConditions {
  62.  
  63.     public static  CollectionCondition sizeOf(int expectedSize)
  64.     ....
  65.  
  66.  
  67. и вот тут
  68.  
  69. public interface LazyCollection extends LazyEntity<List<WebElement>>, Iterable<LazyElement> {
  70.     List<WebElement> shouldHave(Condition<List<WebElement>> condition);
  71.  
  72. или
  73.  
  74. public interface LazyCollection extends LazyEntity<List<WebElement>>, Iterable<LazyElement> {
  75.     List<WebElement> shouldHave(CollectionCondition condition);
  76.  
  77. /*
  78.     техически - ты, конечно, права,
  79.     использовав тип интерфейса Condition<List<WebElement>>
  80.     а не абстрактрого класса  CollectionCondition
  81.     для типов параметров и возвращаемых значений
  82.  
  83.     но - согласись - кон гораздо проще чиатется
  84.     если использовать CollectionCondition )
  85.  
  86.     с Яковом ранее обсуждали этот момент )
  87.     Он - да, советовал не плодить лишних сущностей, и использовать
  88.     абстрактный класс CollectionCondition для типов параметров и возвращаемых знаений
  89.  
  90.     но и не говорил - что это единственно верный вариант)
  91.  
  92.     мне сначала показалось точнее - как ты реализовала )
  93.     а вотом  - захотелось внешней красоты (красоты со стороны человека,который фреймворк будет использовать)
  94.     и я таки добавила интерфейсы CollectionCondition и ElementCondition
  95.     а абстрактные классы назвала  Abstract....
  96.     Ну и в качестве типов параметров и возвращаемых значений -
  97.     использовала интерфейсы CollectionCondition и ElementCondition
  98.  
  99.     не знаю как лучше)))
  100.     мне нравится - когда юзер (человек, пишуший тест, используя наш фреймворк)
  101.     оперирует типами CollectionCondition и ElementCondition
  102.     это проще понимать
  103.     а что это - абстрактный класс или интерфейс - ну... )
  104.     может быть по-разному
  105.     как ты видишь - у обоих решений есть недостатки))
  106.  
  107.     ты можешь и свой вариант оставить
  108.  
  109.  
  110. */
  111. ******************************
  112.  
  113. а еще лучше - объявляй в интерфейсе и имплементируй метод с параметром Condition<List<WebElement>>... conditions
  114. Это на будущее? Или это уже сейчас надо где-то использовать? (мы делали аналогичный метод until в WaitFor)
  115.  
  116. /*
  117.     да, ты права, мы уже это слелали в until в WaitFor
  118.  
  119.     и реализуя такой should - нам достаточно вызвать уже реализованный с такими параметрами until в WaitFor
  120.  
  121.     тут  - уже не нало заново циклов и прочего
  122.     достаточно просто вызвать until в WaitFor - с правильными параметрами)
  123.  
  124.     что касается - зачем это надо
  125.     ну да, мы ни разу такого не использовали
  126.     но - теоретически, может понадобиться - проверить несколько вещей последовательно
  127.  
  128.  
  129.     реализовав should, который оперирует сразу перечнем кондишенов
  130.      мы сможем его вызвать - указывая как один кондишен, так и несколько
  131.      т е - достаточно метода
  132.           LazyElement should(ElementCondition... conditions);
  133.      а варианта
  134.           LazyElement should(ElementCondition condition); - уже и не понадобится
  135.  
  136.      это касается всех should-методов
  137.  
  138.      также - можно реализовать несколько should-методов (по аналогии с селениде)
  139.      с немного отличающимися именами - чтоб код читался как нормальные фразы англ языка
  140.      should / shouldBe / shouldHave
  141. */
  142. ***************************************************************
  143.  
  144. @Override
  145. public WebElement shouldBe(Condition<WebElement> condition) {
  146.    return waitFor(this).until(condition);
  147. }
  148.  
  149. Здесь надо так написать, или вот так:
  150.  
  151. @Override
  152. public WebElement shouldBe(Condition<WebElement> condition) {
  153.    return waitFor(this).until(visible(), condition);
  154. }
  155.  
  156. /*
  157.     однозначно - первый вариант
  158.  
  159.     когда мы вызываем should - мы сами в состоянии диктовать
  160.     какие проверки выполнить и в какой последовательности
  161.     (мы же реализуем параметр метода как Condition<WebElement>... conditions)
  162. */
  163. *********************************************
  164.  
  165.     @Override
  166.     public Iterator<LazyElement> iterator() {
  167.         List<LazyElement> list = null;
  168.         for (WebElement element: getWrappedEntity()) {
  169.             list.add(new LazyWrappedWebElement(element));
  170.         }
  171.         return list.iterator();
  172.     }
  173. /*
  174.     Да, тип возвращаешь верный)
  175.     сама реализация - верная
  176.  
  177.     за исключением первой строчки
  178.     List<LazyElement> list = null;
  179.  
  180.     тебе нужно инициализировать список
  181.     List<LazyElement> list = new ArrayList<>();
  182.  
  183.     как проверить - что метод рабочий - напиши тест-метод, типа такого(использую уже тудуэмвиси приложение):
  184. */
  185.     @Test
  186.     public void testIterator() {
  187.         givenAtAll(ACTIVE, "аb", "ааb", "ac", "bc");
  188.  
  189.         for (LazyElement element:tasks) {
  190.             System.out.println(element.getText());
  191.         }
  192.     }
  193. /*
  194.     не сказать - что это прямо полноценный тест
  195.  
  196.     можешь точно также - для gmail
  197.     перебрать в такого же рода цикле все мейлы и вывести их тексты
  198.  
  199.     если цикл типа for (LazyElement element:elements)  - работает
  200.     значит - метод iterator ты правильно реализовала
  201. */
  202. *************************************************
  203. public interface LazyElement extends LazyEntity<WebElement>, WebElement {
  204.  
  205. /*
  206.     помимо выше описанного по should-ам
  207.     объяви тут и реализуй в абстрактном классе
  208. */
  209. LazyElement pressEscape();
  210. *********************************************
  211. public interface LazyCollection extends LazyEntity<List<WebElement>>, Iterable<LazyElement> {
  212. /*
  213.     помимо выше описанного по should-ам
  214.     объяви тут и реализуй в абстрактном классе
  215.  
  216.     в эти методы - не надо встраивать ожиданий
  217.     т к на самом деле - чего ждать - сильно зависит от тестируемой задачи
  218.     на уровне написания фреймворка - мы не можем это сейчам решить
  219. */
  220.  
  221.     int size();
  222.  
  223.     boolean isEmpty();
  224.  
  225.     String[] getTexts();
  226. **********************************************************
  227.  
  228.     @Override
  229.     public LazyElement doubleClick() {
  230.         return null;
  231.     }
  232.  
  233.     @Override
  234.     public LazyElement hover() {
  235.         return null;
  236.     }
  237.  
  238. /*
  239.     вспомни свою работу - когда понижади версию Selenide  до 2.17
  240.     и реализовывали doubleClick() )
  241.     https://github.com/ljubanka/todomvctest/blob/oldselenide/src/main/java/ua/net/itlabs/Helpers.java
  242.  
  243.     осталось разобраться - откуда взять actions()
  244.     это не сложно)
  245.  
  246.     hover - схема аналогичная
  247. */
  248. ***********************************************************
  249.     public LazyElement setValue(String text) {
  250.         ...
  251.         element.sendKeys(text + Keys.ENTER);
  252.         ...
  253.     }
  254. /*
  255.    setValue = очистили поле и ввели текст
  256.    нажатие энтера сюда не входит
  257. */
  258. **************************************
  259.  
  260.     public Point getLocation() {
  261.     public Dimension getSize() {
  262.     public Rectangle getRect() {
  263. /*
  264.     тут лучше видимости ждать - речь про видимое расположение элемента
  265. */
  266. ********************************************
  267.  
  268.     public void sendKeys(CharSequence... var1) {
  269.         ...
  270.         element.clear();
  271.         ...
  272. /*
  273.     не надо тут clear()
  274.  
  275.     делаем только то, что обещали
  276.     обещали - sendKeys
  277. */
  278. *******************************************
  279.     public LazyElement pressEnter() {
  280.  /*
  281.     тут можно переиспользовать уже реализованный sendKeys (метод этого же класса)
  282.     будет лаконичнее
  283.  */
  284. ******************************************
  285.  
  286. public class LazyWrappedWebElement extends AbstractLazyElement{
  287.  
  288. /*
  289.     все ок реализовано
  290.     я бы советовала в конструктор передавать не только вебэлемент заворачиваемый
  291.     но и родительскую лейзи-сущность - из метода которой мы такое делали
  292.  
  293.     ну и в toString - выводила бы что-то типа
  294.     "WebElement " + element.toString() + " from " + parentEntity
  295.  
  296.     цель - когда проверка кондишена для такого элемента упадет -
  297.     будет легче понять - что  за вебэлемент
  298. */
  299. ******************************************************
  300.  
  301. public static LazyWebDriverElement $(By locator){
  302.         return new LazyWebDriverElement(locator);//waitFor(locator).until(visible());
  303. }
  304.  
  305. /*
  306.     вот этот момент еще надо понять
  307.  
  308.     да, объект мы создаем - как LazyWebDriverElement
  309.     но - в качестве типа возвращаемого значения = используем интерфейс LazyElement
  310.  
  311.     объект, имплементирующий такой интерфейс, спокойно приводится к типу интерфейса
  312.  
  313.     и далее - когда у нас будет несколько типов для лейзи-элементов -
  314.     какого бы типа лейзи-элемент мы не создавали -
  315.     возвращаем значение  одного и того же типа - интерфейс
  316.  
  317.      если ты четко заявляешь - мой объект поддерживает такие-то интерфейсы, тогда
  318.         все могут общаться с твоим объектом через четко прописанное API этого интерфейса
  319.  
  320.         именно поэтому SelenideElement - это интерфейс
  321.  
  322.         и List - тоже интерфейс
  323.         и мы используем
  324.             List<String> myListOfStrings = new ArrayList<String>()
  325.         а не
  326.             ArrayList<String> myListOfStrings = new ArrayList<String>()
  327.  
  328.      то же касается и коллекции
  329. */
  330. **************************************
  331.  
  332. public static By emails = byCSS("[role='main'] .zA");
  333. /*
  334.     это уже можно объявлять как LazyCollection и инициализировать как $$("[role='main'] .zA")
  335.     должно работать))
  336. */
Advertisement
Add Comment
Please, Sign In to add comment