Skip to content

Commit

Permalink
Add hooks support
Browse files Browse the repository at this point in the history
  • Loading branch information
Toilal committed Sep 1, 2016
1 parent 56389b9 commit 002ff5d
Show file tree
Hide file tree
Showing 49 changed files with 2,123 additions and 496 deletions.
Expand Up @@ -14,9 +14,11 @@
import org.fluentlenium.core.events.EventsRegistry; import org.fluentlenium.core.events.EventsRegistry;
import org.fluentlenium.core.events.AnnotationsComponentListener; import org.fluentlenium.core.events.AnnotationsComponentListener;
import org.fluentlenium.core.filter.Filter; import org.fluentlenium.core.filter.Filter;
import org.fluentlenium.core.hook.DefaultHookChainBuilder;
import org.fluentlenium.core.hook.HookChainBuilder;
import org.fluentlenium.core.inject.DefaultContainerInstanciator; import org.fluentlenium.core.inject.DefaultContainerInstanciator;
import org.fluentlenium.core.inject.FluentInjector; import org.fluentlenium.core.inject.FluentInjector;
import org.fluentlenium.core.proxy.Proxies; import org.fluentlenium.core.proxy.LocatorProxies;
import org.fluentlenium.core.script.FluentJavascript; import org.fluentlenium.core.script.FluentJavascript;
import org.fluentlenium.core.search.Search; import org.fluentlenium.core.search.Search;
import org.fluentlenium.core.wait.FluentWait; import org.fluentlenium.core.wait.FluentWait;
Expand Down Expand Up @@ -64,6 +66,8 @@ public class FluentDriver implements FluentDriverControl {


private KeyboardActions keyboardActions; private KeyboardActions keyboardActions;


private HookChainBuilder hookChainBuilder;

private WindowAction windowAction; private WindowAction windowAction;


public FluentDriver(WebDriver driver, ConfigurationProperties configuration, ComponentsManager componentsManager) { public FluentDriver(WebDriver driver, ConfigurationProperties configuration, ComponentsManager componentsManager) {
Expand Down Expand Up @@ -111,7 +115,8 @@ private void configureDriver() {


protected FluentDriver initFluent(WebDriver driver) { protected FluentDriver initFluent(WebDriver driver) {
this.driver = driver; this.driver = driver;
this.search = new Search(driver, componentsManager); this.hookChainBuilder = new DefaultHookChainBuilder(this.driver, this.componentsManager.getInstantiator());
this.search = new Search(driver, componentsManager, hookChainBuilder);
if (driver instanceof EventFiringWebDriver) { if (driver instanceof EventFiringWebDriver) {
this.events = new EventsRegistry((EventFiringWebDriver) driver); this.events = new EventsRegistry((EventFiringWebDriver) driver);
this.eventsComponentsAnnotations = new AnnotationsComponentListener(componentsManager); this.eventsComponentsAnnotations = new AnnotationsComponentListener(componentsManager);
Expand Down Expand Up @@ -414,7 +419,7 @@ public void switchTo(FluentWebElement element) {
if (null == element || !"iframe".equals(element.getTagName())) { if (null == element || !"iframe".equals(element.getTagName())) {
getDriver().switchTo().defaultContent(); getDriver().switchTo().defaultContent();
} else { } else {
getDriver().switchTo().frame(Proxies.getElement(element.getElement())); getDriver().switchTo().frame(LocatorProxies.getLocatorResult(element.getElement()));
} }
} }


Expand Down
Expand Up @@ -2,15 +2,14 @@


import org.fluentlenium.core.components.ComponentInstantiator; import org.fluentlenium.core.components.ComponentInstantiator;
import org.fluentlenium.core.domain.FluentList; import org.fluentlenium.core.domain.FluentList;
import org.fluentlenium.core.domain.FluentListImpl;
import org.fluentlenium.core.domain.FluentWebElement; import org.fluentlenium.core.domain.FluentWebElement;
import org.fluentlenium.core.proxy.Proxies; import org.fluentlenium.core.hook.HookChainBuilder;
import org.fluentlenium.core.proxy.LocatorProxies;
import org.openqa.selenium.By; import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver; import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement; import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.pagefactory.ElementLocator; import org.openqa.selenium.support.pagefactory.ElementLocator;


import java.util.ArrayList;
import java.util.Arrays; import java.util.Arrays;
import java.util.List; import java.util.List;


Expand All @@ -20,11 +19,12 @@
public class Axes { public class Axes {
private final WebElement webElement; private final WebElement webElement;
private final ComponentInstantiator instantiator; private final ComponentInstantiator instantiator;
private final HookChainBuilder hookChainBuilder;



public Axes(WebElement element, ComponentInstantiator instantiator, HookChainBuilder hookChainBuilder) {
public Axes(WebElement element, ComponentInstantiator instantiator) {
this.webElement = element; this.webElement = element;
this.instantiator = instantiator; this.instantiator = instantiator;
this.hookChainBuilder = hookChainBuilder;
} }




Expand All @@ -34,7 +34,7 @@ public Axes(WebElement element, ComponentInstantiator instantiator) {
* @return fluent web element * @return fluent web element
*/ */
public FluentWebElement parent() { public FluentWebElement parent() {
return Proxies.createComponent(new ElementLocator() { return LocatorProxies.createComponent(new ElementLocator() {
@Override @Override
public WebElement findElement() { public WebElement findElement() {
return Axes.this.webElement.findElement(By.xpath("parent::*")); return Axes.this.webElement.findElement(By.xpath("parent::*"));
Expand All @@ -48,7 +48,7 @@ public List<WebElement> findElements() {
} }


protected FluentList<FluentWebElement> handleAxe(final String axe) { protected FluentList<FluentWebElement> handleAxe(final String axe) {
return Proxies.createFluentList(new ElementLocator() { return LocatorProxies.createFluentList(new ElementLocator() {
@Override @Override
public WebElement findElement() { public WebElement findElement() {
return Axes.this.webElement.findElement(By.xpath(axe + "::*")); return Axes.this.webElement.findElement(By.xpath(axe + "::*"));
Expand All @@ -58,7 +58,7 @@ public WebElement findElement() {
public List<WebElement> findElements() { public List<WebElement> findElements() {
return Axes.this.webElement.findElements(By.xpath(axe + "::*")); return Axes.this.webElement.findElements(By.xpath(axe + "::*"));
} }
}, FluentWebElement.class, instantiator); }, FluentWebElement.class, instantiator, hookChainBuilder);
} }


/** /**
Expand Down
Expand Up @@ -2,7 +2,7 @@


import com.sun.jna.WeakIdentityHashMap; import com.sun.jna.WeakIdentityHashMap;
import org.fluentlenium.core.proxy.ProxyElementListener; import org.fluentlenium.core.proxy.ProxyElementListener;
import org.fluentlenium.core.proxy.Proxies; import org.fluentlenium.core.proxy.LocatorProxies;
import org.openqa.selenium.WebDriver; import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement; import org.openqa.selenium.WebElement;
import org.openqa.selenium.internal.WrapsElement; import org.openqa.selenium.internal.WrapsElement;
Expand Down Expand Up @@ -81,13 +81,13 @@ public <T> T newComponent(Class<T> componentClass, WebElement element) {
+ " is not a valid component class. No valid constructor found (WebElement) or (WebElement, WebDriver)", e); + " is not a valid component class. No valid constructor found (WebElement) or (WebElement, WebDriver)", e);
} }
WebElement webElement = unwrapElement(element); WebElement webElement = unwrapElement(element);
Proxies.addProxyListener(webElement, this); LocatorProxies.addProxyListener(webElement, this);
components.put(webElement, component); components.put(webElement, component);
return component; return component;
} }


@Override @Override
public void proxyElementSearch(WebElement proxy, ElementLocator locator) { public void proxyElementSearch(Object proxy, ElementLocator locator) {
} }


/** /**
Expand All @@ -99,10 +99,10 @@ public void proxyElementSearch(WebElement proxy, ElementLocator locator) {
* @param element found element. * @param element found element.
*/ */
@Override @Override
public synchronized void proxyElementFound(WebElement proxy, ElementLocator locator, WebElement element) { public synchronized void proxyElementFound(Object proxy, ElementLocator locator, WebElement element) {
Object component = components.remove(proxy); Object component = components.remove(proxy);
if (component != null) { if (component != null) {
components.put(unwrapElement(proxy), component); components.put(unwrapElement(element), component);
} }
} }


Expand All @@ -121,7 +121,7 @@ private WebElement unwrapElement(WebElement element) {
*/ */
public void release() { public void release() {
for (WebElement element : components.keySet()) { for (WebElement element : components.keySet()) {
Proxies.removeProxyListener(element, this); LocatorProxies.removeProxyListener(element, this);
} }
components.clear(); components.clear();
} }
Expand Down
@@ -1,6 +1,5 @@
package org.fluentlenium.core.components; package org.fluentlenium.core.components;


import org.fluentlenium.core.inject.FluentInjectException;
import org.fluentlenium.utils.ReflectionUtils; import org.fluentlenium.utils.ReflectionUtils;
import org.openqa.selenium.WebDriver; import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement; import org.openqa.selenium.WebElement;
Expand Down
Expand Up @@ -3,6 +3,7 @@
import org.fluentlenium.core.action.FluentActions; import org.fluentlenium.core.action.FluentActions;
import org.fluentlenium.core.conditions.FluentListConditions; import org.fluentlenium.core.conditions.FluentListConditions;
import org.fluentlenium.core.filter.Filter; import org.fluentlenium.core.filter.Filter;
import org.fluentlenium.core.hook.HookControl;
import org.fluentlenium.core.proxy.FluentProxyState; import org.fluentlenium.core.proxy.FluentProxyState;
import org.fluentlenium.core.search.SearchControl; import org.fluentlenium.core.search.SearchControl;
import org.openqa.selenium.WebElement; import org.openqa.selenium.WebElement;
Expand All @@ -12,7 +13,7 @@
/** /**
* *
*/ */
public interface FluentList<E extends FluentWebElement> extends List<E>, FluentActions<FluentList<E>, E>, FluentProxyState<FluentList<E>>, SearchControl<E> { public interface FluentList<E extends FluentWebElement> extends List<E>, FluentActions<FluentList<E>, E>, FluentProxyState<FluentList<E>>, SearchControl<E>, HookControl<FluentList<E>> {


/** /**
* Return the first element of the list * Return the first element of the list
Expand Down
Expand Up @@ -9,17 +9,20 @@
import org.fluentlenium.core.conditions.EachElementConditions; import org.fluentlenium.core.conditions.EachElementConditions;
import org.fluentlenium.core.conditions.FluentListConditions; import org.fluentlenium.core.conditions.FluentListConditions;
import org.fluentlenium.core.filter.Filter; import org.fluentlenium.core.filter.Filter;
import org.fluentlenium.core.hook.DefaultHookChainBuilder;
import org.fluentlenium.core.hook.FluentHook;
import org.fluentlenium.core.hook.HookChainBuilder;
import org.fluentlenium.core.hook.HookDefinition;
import org.fluentlenium.core.proxy.ListElementAccessor; import org.fluentlenium.core.proxy.ListElementAccessor;
import org.fluentlenium.core.proxy.Proxies; import org.fluentlenium.core.proxy.LocatorProxies;
import org.openqa.selenium.By; import org.openqa.selenium.By;
import org.openqa.selenium.NoSuchElementException; import org.openqa.selenium.NoSuchElementException;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement; import org.openqa.selenium.WebElement;
import sun.reflect.generics.reflectiveObjects.NotImplementedException;


import java.util.ArrayList; import java.util.ArrayList;
import java.util.Arrays; import java.util.Arrays;
import java.util.Collection; import java.util.Collection;
import java.util.Iterator;
import java.util.List; import java.util.List;


/** /**
Expand All @@ -29,6 +32,9 @@ public class FluentListImpl<E extends FluentWebElement> extends ArrayList<E> imp
private Class<E> componentClass; private Class<E> componentClass;
private ComponentInstantiator instantiator; private ComponentInstantiator instantiator;


private final List<HookDefinition<?>> hookDefinitions = new ArrayList<>();
private HookChainBuilder hookChainBuilder;

public FluentListImpl() { public FluentListImpl() {
} }


Expand All @@ -40,22 +46,25 @@ public FluentListImpl(Collection<E> listFiltered) {
super(listFiltered); super(listFiltered);
} }


public FluentListImpl(Class<E> componentClass, ComponentInstantiator instantiator) { public FluentListImpl(Class<E> componentClass, ComponentInstantiator instantiator, HookChainBuilder hookChainBuilder) {
super(); super();
this.componentClass = componentClass; this.componentClass = componentClass;
this.instantiator = instantiator; this.instantiator = instantiator;
this.hookChainBuilder = hookChainBuilder;
} }


public FluentListImpl(Class<E> componentClass, ComponentInstantiator instantiator, E... listFiltered) { public FluentListImpl(Class<E> componentClass, ComponentInstantiator instantiator, HookChainBuilder hookChainBuilder, E... listFiltered) {
super(new ArrayList<E>(Arrays.asList(listFiltered))); super(new ArrayList<E>(Arrays.asList(listFiltered)));
this.componentClass = componentClass; this.componentClass = componentClass;
this.instantiator = instantiator; this.instantiator = instantiator;
this.hookChainBuilder = hookChainBuilder;
} }


public FluentListImpl(Class<E> componentClass, ComponentInstantiator instantiator, Collection<E> listFiltered) { public FluentListImpl(Class<E> componentClass, ComponentInstantiator instantiator, HookChainBuilder hookChainBuilder, Collection<E> listFiltered) {
super(listFiltered); super(listFiltered);
this.componentClass = componentClass; this.componentClass = componentClass;
this.instantiator = instantiator; this.instantiator = instantiator;
this.hookChainBuilder = hookChainBuilder;
} }


/** /**
Expand All @@ -64,8 +73,8 @@ public FluentListImpl(Class<E> componentClass, ComponentInstantiator instantiato
* @param elements array of Selenium elements * @param elements array of Selenium elements
* @return FluentList of FluentWebElement * @return FluentList of FluentWebElement
*/ */
public static FluentListImpl<FluentWebElement> fromElements(ComponentInstantiator instantiator, WebElement... elements) { public static FluentListImpl<FluentWebElement> fromElements(ComponentInstantiator instantiator, HookChainBuilder hookChainBuilder, WebElement... elements) {
return fromElements(instantiator, Arrays.asList(elements)); return fromElements(instantiator, hookChainBuilder, Arrays.asList(elements));
} }


/** /**
Expand All @@ -74,8 +83,8 @@ public static FluentListImpl<FluentWebElement> fromElements(ComponentInstantiato
* @param elements iterable of Selenium elements * @param elements iterable of Selenium elements
* @return FluentList of FluentWebElement * @return FluentList of FluentWebElement
*/ */
public static FluentListImpl<FluentWebElement> fromElements(ComponentInstantiator instantiator, Iterable<? extends WebElement> elements) { public static FluentListImpl<FluentWebElement> fromElements(ComponentInstantiator instantiator, HookChainBuilder hookChainBuilder, Iterable<? extends WebElement> elements) {
FluentListImpl<FluentWebElement> fluentWebElements = new FluentListImpl<>(FluentWebElement.class, instantiator); FluentListImpl<FluentWebElement> fluentWebElements = new FluentListImpl<>(FluentWebElement.class, instantiator, hookChainBuilder);
for (WebElement element : elements) { for (WebElement element : elements) {
fluentWebElements.add(instantiator.newComponent(FluentWebElement.class, element)); fluentWebElements.add(instantiator.newComponent(FluentWebElement.class, element));
} }
Expand Down Expand Up @@ -121,12 +130,12 @@ public E index(int index) {


@Override @Override
public boolean isPresent() { public boolean isPresent() {
return Proxies.isPresent(this); return LocatorProxies.isPresent(this);
} }


@Override @Override
public FluentList<E> now() { public FluentList<E> now() {
Proxies.now(this); LocatorProxies.now(this);
if (this.size() == 0) { if (this.size() == 0) {
throw new NoSuchElementException("Element not found"); throw new NoSuchElementException("Element not found");
} }
Expand All @@ -135,13 +144,13 @@ public FluentList<E> now() {


@Override @Override
public FluentList<E> reset() { public FluentList<E> reset() {
Proxies.reset(this); LocatorProxies.reset(this);
return this; return this;
} }


@Override @Override
public boolean isLoaded() { public boolean isLoaded() {
return Proxies.isLoaded(this); return LocatorProxies.isLoaded(this);
} }


@Override @Override
Expand Down Expand Up @@ -384,7 +393,7 @@ public FluentList<E> find(String selector, Filter... filters) {
for (FluentWebElement e : this) { for (FluentWebElement e : this) {
finds.addAll((Collection<E>) e.find(selector, filters)); finds.addAll((Collection<E>) e.find(selector, filters));
} }
return new FluentListImpl<E>(componentClass, instantiator, finds); return new FluentListImpl<E>(componentClass, instantiator, hookChainBuilder, finds);
} }


@Override @Override
Expand All @@ -393,7 +402,7 @@ public FluentList<E> find(By locator, Filter... filters) {
for (FluentWebElement e : this) { for (FluentWebElement e : this) {
finds.addAll((Collection<E>) e.find(locator, filters)); finds.addAll((Collection<E>) e.find(locator, filters));
} }
return new FluentListImpl<E>(componentClass, instantiator, finds); return new FluentListImpl<E>(componentClass, instantiator, hookChainBuilder, finds);
} }


@Override @Override
Expand All @@ -402,7 +411,7 @@ public FluentList<E> find(Filter... filters) {
for (FluentWebElement e : this) { for (FluentWebElement e : this) {
finds.addAll((Collection<E>) e.find(filters)); finds.addAll((Collection<E>) e.find(filters));
} }
return new FluentListImpl<E>(componentClass, instantiator, finds); return new FluentListImpl<E>(componentClass, instantiator, hookChainBuilder, finds);
} }


@Override @Override
Expand Down Expand Up @@ -491,7 +500,28 @@ public <T extends FluentWebElement> FluentList<T> as(Class<T> componentClass) {
elements.add(e.as(componentClass)); elements.add(e.as(componentClass));
} }


return new FluentListImpl<>(componentClass, instantiator, elements); return new FluentListImpl<>(componentClass, instantiator, hookChainBuilder, elements);
}

@Override
public FluentList<E> noHook() {
hookDefinitions.clear();
LocatorProxies.setHooks(hookChainBuilder, this, hookDefinitions);
return this;
}

@Override
public <O, H extends FluentHook<O>> FluentList<E> withHook(Class<H> hook) {
hookDefinitions.add(new HookDefinition<>(hook));
LocatorProxies.setHooks(hookChainBuilder, this, hookDefinitions);
return this;
}

@Override
public <O, H extends FluentHook<O>> FluentList<E> withHook(Class<H> hook, O options) {
hookDefinitions.add(new HookDefinition<>(hook, options));
LocatorProxies.setHooks(hookChainBuilder, this, hookDefinitions);
return this;
} }
} }


0 comments on commit 002ff5d

Please sign in to comment.