Download - Easy tests with Selenide and Easyb
![Page 2: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/2.jpg)
Conventions :)
● Sympathy colors***:
Green =
Orange =
Red =
*** often are subjective and applied to specific context ;)
![Page 3: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/3.jpg)
● At project with no Web UI automation, no unit testing
● With 4(5) Manual QA
– Using checklists + long detailed End to End test cases
● With 1 QA Automation found
![Page 4: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/4.jpg)
Testing single page web app
● Ajax
● only <div>, <a>, <input>
– Inconsistent implementation
● No confident urls
● One current Frame/Page with content per user step
– Deep structure: ● Authorization > Menus > SubMenus > Tabs > Extra > Extra
– Modal dialogs
![Page 5: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/5.jpg)
Met Requirements
● Automate high level scenarios
– use AC from stories
– existed Manual Scenarios
● Use 3rd party solutions
– Java Desired
● Involve Manual QA
– provide easy to use solution
– BDD Desired
● In Tough Deadlines :)
![Page 6: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/6.jpg)
Dreaming of framework...● Fast in development
– Using instruments quite agile to adapt to project specifics
● Extremely easy to use and learn
● Simple DSL for tests
● BDD – light and DRY as much as possible
![Page 7: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/7.jpg)
![Page 8: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/8.jpg)
“Raw” Webdriver with tunings (HtmlElements, Matchers, etc.)
● No convenient and concise Ajax support out of the box
● Code redundancy
– Driver creation
– Finding elements
– Assert element states
● Harmcrest Matchers are easy, but assertThat() knows nothing about Ajax
– HtmlElements gives powerful but bulky “waiting” decorators (see links [1][2])
![Page 9: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/9.jpg)
Concordion
● Hard to extend
– Custom commands (asserts)
<html xmlns:concordion="http://www.concordion.org/2007/concordion"> <body> <p concordion:assertEquals="getGreeting()">Hello World!</p> </body></html>
![Page 10: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/10.jpg)
Thucydides
● No convenient Ajax support
– Asserts and Conditions are bound● Hard to extend
● Framework, not a Lib
– Not agile● It's hard to use some patterns (e.g. LoadableComponent)
● Monstrous Manual :)
![Page 11: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/11.jpg)
= Redundancy
![Page 12: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/12.jpg)
Not BDD
![Page 13: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/13.jpg)
Easy:) Instruments
![Page 14: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/14.jpg)
![Page 15: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/15.jpg)
@Test
public void userCanLoginByUsername() {
open("/login");
$(By.name("user.name")).setValue("johny");
$("#submit").click();
$(".loading_progress").should(disappear);
$("#username").shouldHave(text("Hello, Johny!"));
}
![Page 16: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/16.jpg)
Selenide Pros● Wrapper over Selenium with Concise API
● Lib, not a Framework
– You still have your raw WebDriver when needed
● should style asserts
– Independent from Conditions
– Waiting for conditions (Ajax friendly)
● Screenshot reporting on each failed should
● Screenshot API
– Providing screenshots' context
– Get all screenshots for context
● Actively supported by authors
![Page 17: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/17.jpg)
Killer FeatureSelenide Conditions
![Page 18: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/18.jpg)
public static final Condition checked = new Condition("checked") {
@Override
public boolean apply(WebElement element) {
return isChecked(element);
}
@Override
public String actualValue(WebElement element) {
return isChecked(element) ? "checked" : "unchecked";
}
@Override
public String toString(){
return "checked";
}
};
![Page 19: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/19.jpg)
Or even shorter
public static final Condition checked = new Condition("checked") {
@Override
public boolean apply(WebElement element) {
return isChecked(element);
}
};
![Page 20: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/20.jpg)
Custom Condition Examples
![Page 21: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/21.jpg)
Aliases
![Page 22: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/22.jpg)
Implementation
public static final Condition checked =
Condition.hasClass("checked");
public static final Condition enabled =
Condition.hasNotClass("disabled");
public static final Condition expanded =
Condition.attribute("area-expanded", "true");
![Page 23: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/23.jpg)
Usage
showPasswordCheckBox().shouldBe(not(checked));
applyButton().shouldBe(enabled);
treeItem.shouldBe(expanded);
![Page 24: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/24.jpg)
Usage: is
public static void ensureExpanded(SelenideElement item){
if (item.is(not(expanded))){
expand(item); }}
![Page 25: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/25.jpg)
Own implementation
![Page 26: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/26.jpg)
Implementation (1)public static final Condition inRadioMode(final String radioMode){ return new Condition("in radio mode: " + radioMode) { @Override public boolean apply(WebElement webElement) {
boolean res = true; for(WebElement mode: Mode.modes(webElement)){
if (Mode.value(mode).equals(radioMode)){ res = res &&
mode.getAttribute("class").contains("active"); } else { res = res && !
mode.getAttribute("class").contains("active"); } } return res; } };}
![Page 27: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/27.jpg)
Implementation (2)
public static final Condition faded = new Condition("faded with backdrop") {
@Override public boolean apply(WebElement element) {
return backDropFor(element).exists(); }};
![Page 28: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/28.jpg)
Implementation (3)
public static Condition leftSliderPosition(final Integer position)
{
return new Condition("left slider position " + position)
{ @Override public boolean apply(WebElement webElement) {
return
getLeftSliderCurrentPosition(webElement).equals(position); } };}
![Page 29: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/29.jpg)
Usage
tabContainer().shouldBe(faded);
accessRadioButtons().shouldBe(inRadioMode(PRIVATE));
scheduler.shouldHave(leftSliderPosition(100));
![Page 30: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/30.jpg)
Composition*
* public static final will be omitted for simplicity
![Page 31: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/31.jpg)
ImplementationCondition loadingDialog = condition(loadingDialog(), exist);Condition applyButtonDisabled = condition(primeBtn(), disabled);Condition cancelButtonDisabled = condition(scndBtn(), disabled);
Condition processed = with_(no(Modal.dialog()));Condition loaded = and(processed, with_(no(loadingDialog)), with_(applyButtonDisabled));
Condition savedForSure = and(loaded, with_(saveSuccessMsg()));
Condition failedToSave = and( processed, with_(no(loadingDialog)), with_(not(applyButtonDisabled)), with_(no(saveSuccessMsg())), with_(not(cancelButtonDisabled)), with_(saveErrorsMsg()));
![Page 32: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/32.jpg)
Usage
//fill page with valid/invalid data...
Page.save()
Page.shouldBe(and( failedToSave, with(usernameValidation(), currentPassValidation()), with(no(newPassValidation(), matchPassValidation()))))
//fix errors and save...
Page.shouldBe(savedForSure)
![Page 33: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/33.jpg)
Selenide Cons
● Young:)
– Many things can be improved● Error messages● Condition helpers● Screenshot API
– Tones of them have been resolved so far
– Others can be implemented as your own extensions
● Not all-powerfull
– For some things you will still need raw WebDriver
![Page 34: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/34.jpg)
![Page 35: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/35.jpg)
Easyb Pros● Gherkin (given/when/then) and its implementation live at
the same file
– better maintainability
– more DRY code
● no implementation => “pending” test
● simple but nice looking reports
● groovy as a script language for tests
– scenarios are ordered
![Page 36: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/36.jpg)
Easyb Cons
● bad support of framework from authors.● some features are broken
– before_each
● no tags per scenario/step– only tags per story
● Stack trace of error messages is clipped● No out of the box way to put listeners on
steps/scenarios● “Shared steps” feature is present but not quite
handy
![Page 37: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/37.jpg)
Easyb Selenide Integration
![Page 38: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/38.jpg)
Problem Selenide shoulds vs Easyb shoulds
Easyb catches any 'should' (shouldBe, shouldHave, ...) except “should” and “shouldNot”
showPasswordCheckBox().shouldNot(checked);
//Less readable:(
![Page 39: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/39.jpg)
Solution => Decorators
showPasswordCheckBox().shouldNot(be(checked));
showPasswordCheckBox().should(be(not(checked)));
![Page 40: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/40.jpg)
All Together :)
![Page 41: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/41.jpg)
Preconditions to BDD
● PO knows what is Criteria of Good Requirement
● Manual QA knows how to write “Automatable” Scenarios
Team is competent :)
![Page 42: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/42.jpg)
Pending Easyb Story by PO
description "Products List page"
scenario "Add new product", {
given "On Products List page"
then "new product can be added"
}
![Page 43: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/43.jpg)
Pending Detailed Easyb Story by Manual QA
description "Products List page"
scenario "Add new product", {
given "On Products List page"
and "No custom product with 'Product_1' name exist"
then "new product with 'Product_1' name can be added"
and "after relogin still present"
}
![Page 44: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/44.jpg)
Implemented Easyb Storydescription "ProductsList test"tags "functional"BaseTest.setup() scenario "Add new product", { given "On ProductsList page",{ ProductsList.page().get() } and "No custom product with '" + TEST_PRODUCT + "' name exist", { Table.ensureHasNo(cellByText(TEST_PRODUCT)) } then "new product with '" + TEST_PRODUCT + "' name can be added", { ProductsList.addProductForSure(TEST_PRODUCT) } and "after relogin still present", { cleanReLogin() Table.cellByText(TEST_PRODUCT).should(be(visible)); }}
![Page 45: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/45.jpg)
Easyb Report
![Page 46: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/46.jpg)
FailedEasyb Report
![Page 47: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/47.jpg)
Alternative: TestNG testpublic class ProductManagement extends AbstractTest {
@Test
public void testNewProductCanBeAdded() {
ProductsList.page().get();
Table.ensureHasNo(cellByText(TEST_PRODUCT));
ProductsList.addProductForSure(TEST_PRODUCT);
cleanReLogin();
Table.cellByText(TEST_PRODUCT).should(Be.visible);
}
}
![Page 48: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/48.jpg)
Alternative: TestNG Report
![Page 49: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/49.jpg)
Failed TestNG Report
![Page 50: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/50.jpg)
When Easyb ?
● Detailed reporting of test steps
● Ordered tests execution (as present in the file)
● “Somebody” wants Gherkin
– Automation resources are limited, and help may come from PO or Manual QA providing detailed 'steps to code'
![Page 51: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/51.jpg)
When TestNG/Junit ?
● When you have strong 'agile' devs/automation which know why what and how to test and do write tests.
– Hence you never need pretty looking reports to please your manager customer because you just have high quality product.
![Page 52: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/52.jpg)
Ideas for improvements
● Kill Kenny
– if he is the only who wants Gherkin:)
– and stay KISS with TestNG/Junit
● Contribute to Easyb:)
● Bless Selenide:)
– Authors will contribute nevertheless
![Page 53: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/53.jpg)
![Page 54: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/54.jpg)
Q&A
![Page 55: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/55.jpg)
Resources, Links
● Src of example test framework: https://github.com/yashaka/gribletest
● Application under test used in easyb examples: http://grible.org/download.php
● Instruments
– http://selenide.org/
– http://easyb.org/
![Page 56: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/56.jpg)
● To Artem Chernysh for implementation of main base part of the test framework for this presentation
– https://github.com/elaides/gribletest● To Maksym Barvinskyi for application under test
– http://grible.org/● To Andrei Solntsev, creator of Selenide, for close
collaboration on Selenide Q&A, and new features implemented:)
![Page 57: Easy tests with Selenide and Easyb](https://reader033.vdocuments.net/reader033/viewer/2022042623/5481f6785906b5d8048b4608/html5/thumbnails/57.jpg)
Contacts
● skype: yashaolin
● http://www.linkedin.com/in/iakivkramarenko