Name: Selone
Owner: Kontur
Description: Flexible Selenium WebDriver extension
Created: 2018-05-03 09:26:46.0
Updated: 2018-05-16 14:46:45.0
Pushed: 2018-05-16 14:46:44.0
Homepage: null
Size: 53
Language: C#
GitHub Committers
User | Most Recent Commit | # Commits |
---|
Other Committers
User | Most Recent Commit | # Commits |
---|
Selone is a kit with base infrastructure for quick start of your own set of browser tests or web crawler.
Selone is not yet another Selenium.WebDriver wrapper. Selone does not wrap, does not hide or narrow WebDriver functionality and does not prohibit it from being used.
Selone is not about assertions but it provides abilitily for easy connect of third-party assertion library. For example NUnit with Assert.That
and IResolveConstraint
or FluentAssertions with Should()
method.
Selenium.WebDriver - it is low-level API for web browsers. So its direct usage in your high-level code may be inconvenient.
Selone looks like extension that brings stability and more convenient API for your high-level code
If element doesn't exist then native method FindElement
will throw ElementNotFoundException
element = searchContext.FindElement(By.Id("absent-element-id")); //throws ElementNotFoundException
Alternative is to use SearchElement
. It is the extension method for native ISearchContext
that returns implementation of native IWebElement
element = searchContext.SearchElement(By.Id("absent-element-id"));
me actions
ent.Click();
Of course you can search nested elements inside absent elements
container = searchContext.SearchElement(By.Id("absent-container-id"));
element = container.SearchElement(By.Id("absent-element-id"));
me actions
ent.Click();
So, using SearchElement
method you can pre-declare and initialize all necessary controls in one place
You can't work with reattached element which was found using FindElement
method. If element was detached from DOM and then attached it becomes another element and you will get StaleElementReferenceException
interacting with it.
element = searchContext.FindElement(By.Id("disappearing-element"));
chContext.FindElement(By.Id("remove-from-dom-button")).Click();
chContext.FindElement(By.Id("insert-into-dom-button")).Click();
ent.Click(); //throws StaleElementReferenceException
Alternative is to use SearchElement
method. Element searched by SearchElement
will handle StaleElementReferenceException
itself and action with such element would be successfuly done.
element = searchContext.SearchElement(By.Id("disappearing-element"));
chContext.FindElement(By.Id("remove-from-dom-button")).Click();
chContext.FindElement(By.Id("insert-into-dom-button")).Click();
ent.Click(); //ok
Native IsDisplayed
property throws exception for absent element and there is no IsPresent
property.
Selone provides three extension methods for IWebElement
interface: Displayed()
, Visible()
, Present()
. Of course it's better to use them with element searched by SearchElement
but you can also use it with element received from FindElement
method.
element = searchContext.SearchElement(By.Id("target"));
isDisplayed = element.Displayed().Get();
isVisible = element.Visible().Get();
isPresent = element.Present().Get();
Native FindElement
method receives instance of By
class as selector. There are built-in selectors can be created with static methods like By.Id(...)
or By.Css(...)
etc. One trouble - there is no way to add selectors same way, because all methods are static. So we need something non-static. SearchElement
has overload that receives ByLambda
delegate. This technique allows to add new selectors
ic static class SelectorExtensions
blic static By WithCustomAttribute(this ByDummy dummy, string value)
return By.Css($"[data-x-custom='{value}']");
element = searchContext.SearchElement(x => x.WithCustomAttribute("attr-value"));
It is also posible to create something fluent-like
element = searchContext.SearchElement(x => x.MyCustomSelector().MayBe().Fluent());
Selone provides SearchElements
method as alternative for FindElements
It is lazy and it allows search for absent elements
elements = searchContext.SearchElements(x => x.......);
…