001package org.nuxeo.functionaltests.pages.wizard;
002
003import java.util.concurrent.TimeUnit;
004
005import org.apache.commons.logging.Log;
006import org.apache.commons.logging.LogFactory;
007import org.nuxeo.functionaltests.AbstractTest;
008import org.nuxeo.functionaltests.Locator;
009import org.openqa.selenium.By;
010import org.openqa.selenium.NoSuchFrameException;
011import org.openqa.selenium.StaleElementReferenceException;
012import org.openqa.selenium.TimeoutException;
013import org.openqa.selenium.WebDriver;
014import org.openqa.selenium.WebElement;
015import org.openqa.selenium.support.ui.FluentWait;
016import org.openqa.selenium.support.ui.Wait;
017
018import com.google.common.base.Function;
019
020/**
021 * Wizard and Connect use frames and callback pages to communicate. So focusing the right frame can be tricky because,
022 * for example we never want to do any test on the callback pages.
023 *
024 * @author Tiry (tdelprat@nuxeo.com)
025 */
026public class IFrameHelper {
027
028    protected static final Log log = LogFactory.getLog(IFrameHelper.class);
029
030    public static final String CONNECT_IFRAME_URL_PATTERN = "/register/";
031
032    public static final String CALLBACK_URL_PATTERN = "ConnectCallback";
033
034    public static final String CONNECT_FRAME_NAME = "connectForm";
035
036    private static void switchToIFrame(final WebDriver driver, final WebElement iframe) {
037        Wait<WebDriver> wait = new FluentWait<WebDriver>(driver).withTimeout(AbstractTest.LOAD_TIMEOUT_SECONDS,
038                TimeUnit.SECONDS).pollingEvery(AbstractTest.POLLING_FREQUENCY_MILLISECONDS, TimeUnit.MILLISECONDS).ignoring(
039                NoSuchFrameException.class, StaleElementReferenceException.class);
040        wait.until(new Function<WebDriver, Boolean>() {
041            @Override
042            public Boolean apply(WebDriver driver) {
043                if (iframe == null) {
044                    return driver.switchTo().defaultContent() != null;
045                } else {
046                    return driver.switchTo().frame(iframe) != null;
047                }
048            };
049        });
050    }
051
052    public static boolean focusOnConnectFrame(WebDriver driver) {
053        if (!driver.getCurrentUrl().contains(CONNECT_IFRAME_URL_PATTERN)) {
054            try {
055                WebElement connectFormIFrame = Locator.findElementWithTimeout(By.id(CONNECT_FRAME_NAME));
056                switchToIFrame(driver, connectFormIFrame);
057            } catch (TimeoutException e) {
058                log.error("Unable to find IFrame on page " + driver.getCurrentUrl());
059                return false;
060            }
061            return true;
062        }
063        return false;
064    }
065
066    public static boolean focusOnWizardPage(WebDriver driver) {
067
068        Locator.waitUntilURLNotContain(CALLBACK_URL_PATTERN);
069
070        // if we're coming from an iframe, driver.getCurrentUrl() can be empty
071        // switch back to main frame without testing the URL
072        try {
073            switchToIFrame(driver, null);
074            return true;
075        } catch (TimeoutException e) {
076            log.error("Unable to find top windows on page " + driver.getCurrentUrl());
077            return false;
078        }
079    }
080}