org.openqa.selenium.WebDriver Scala Examples

The following examples show how to use org.openqa.selenium.WebDriver. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example.
Example 1
Source File: AcceptanceSpec.scala    From renku   with Apache License 2.0 5 votes vote down vote up
package ch.renku.acceptancetests.tooling

import org.openqa.selenium.WebDriver
import org.openqa.selenium.chrome.ChromeOptions
import org.openqa.selenium.remote.RemoteWebDriver
import org.scalatest.{BeforeAndAfterAll, FeatureSpec, GivenWhenThen, Matchers => ScalatestMatchers}
import org.scalatestplus.selenium.{Chrome, Driver, WebBrowser}

trait AcceptanceSpec
    extends FeatureSpec
    with GivenWhenThen
    with BeforeAndAfterAll
    with Matchers
    with ScalatestMatchers
    with WebBrowser
    with Driver
    with Grammar
    with ScreenCapturingSpec
    with AcceptanceSpecData
    with AcceptanceSpecPatience {

  protected implicit val browser: AcceptanceSpec = this
  implicit lazy val webDriver:    WebDriver      = getWebDriver

  private def getWebDriver: WebDriver =
    sys.env.get("DOCKER") match {
      // NOTE We could also support running against the selenium container from the host machine:
      // RemoteWebDriver.builder().url("http://localhost:4444/wd/hub").addAlternative(new ChromeOptions()).build()
      case Some(_) =>
        RemoteWebDriver.builder().url("http://chrome:4444/wd/hub").addAlternative(new ChromeOptions()).build()
      case None =>
        Chrome.webDriver
    }
} 
Example 2
Source File: package.scala    From korolev   with Apache License 2.0 5 votes vote down vote up
import akka.actor.ActorSystem
import org.openqa.selenium.{JavascriptExecutor, WebDriver, WebElement}
import org.slf4j.LoggerFactory

import scala.concurrent.duration._

package object tools {

  val logger = LoggerFactory.getLogger("tools")

  def step(caption: String)(lambda: WebDriver => StepResult) =
    Step(caption, lambda)

  def scenario(name: String)(steps: Step*)(implicit as: ActorSystem): Scenario =
    Scenario(name, steps)

  def assert(message: String, f: => Boolean) = {
    if (!f) {
      val exception = new AssertionError(message)
      throw exception
    } else {
      StepResult.Ok
    }
  }

  def fail(message: String): Unit = {
    throw new AssertionError(message)
  }

  def sleep(duration: FiniteDuration): Unit = {
    Thread.sleep(duration.toMillis)
  }

  implicit final class WebElementOps(val el: WebElement) extends AnyVal {
    def scrollTo()(implicit webDriver: WebDriver): Unit = webDriver match {
      case executor: JavascriptExecutor =>
        executor.executeScript("arguments[0].scrollIntoView(true);", el)
        ()
      case _ =>
        throw new UnsupportedOperationException("WebDriver is not javascript executor")
    }
  }
} 
Example 3
Source File: UISeleniumSuite.scala    From BigDatalog   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.{BeforeAndAfterAll, Matchers}
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._

import org.apache.spark.ui.SparkUICssErrorHandler

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver {
      getWebClient.setCssErrorHandler(new SparkUICssErrorHandler)
    }
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }

  ignore("thrift server ui test") {
    withJdbcStatement { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 4
Source File: UISeleniumSuite.scala    From Spark-2.3.1   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.{BeforeAndAfterAll, Matchers}
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._

import org.apache.spark.ui.SparkUICssErrorHandler

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver {
      getWebClient.setCssErrorHandler(new SparkUICssErrorHandler)
    }
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }

  ignore("thrift server ui test") {
    withJdbcStatement("test_map") { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 5
Source File: UISeleniumSuite.scala    From spark1.52   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.{BeforeAndAfterAll, Matchers}
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._

import org.apache.spark.ui.SparkUICssErrorHandler

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver {
      getWebClient.setCssErrorHandler(new SparkUICssErrorHandler)
    }
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }
  //thrift服务器ui测试
  ignore("thrift server ui test") {
    withJdbcStatement { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        //检查是否存在语句
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 6
Source File: UISeleniumSuite.scala    From iolap   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._
import org.scalatest.{BeforeAndAfterAll, Matchers}

import org.apache.spark.sql.hive.HiveContext

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  var hc: HiveContext = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }

  ignore("thrift server ui test") {
    withJdbcStatement { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 7
Source File: UISeleniumSuite.scala    From multi-tenancy-spark   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.{BeforeAndAfterAll, Matchers}
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._

import org.apache.spark.ui.SparkUICssErrorHandler

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver {
      getWebClient.setCssErrorHandler(new SparkUICssErrorHandler)
    }
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }

  ignore("thrift server ui test") {
    withJdbcStatement { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 8
Source File: HtmlUnitConfiguration.scala    From ScalaWebTest   with Apache License 2.0 5 votes vote down vote up
package org.scalawebtest.core.configuration

import org.openqa.selenium.WebDriver
import org.scalawebtest.core.WebClientExposingDriver

trait HtmlUnitConfiguration {
  self: BaseConfiguration =>
  //initialize with sensible default configuration
  disableJavaScript()
  swallowJavaScriptErrors()
  disableCss()

  override def enableJavaScript(throwOnError: Boolean): Unit = {
    configurations += "enableJavaScript" ->
      ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setJavaScriptEnabled(true))
    configurations += "throwOnJSError" ->
      ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setThrowExceptionOnScriptError(throwOnError))
  }

  override def disableJavaScript(): Unit = {
    configurations += "enableJavaScript" -> ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setJavaScriptEnabled(false))
    configurations += "throwOnJSError" -> ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setThrowExceptionOnScriptError(false))
  }

  override def throwOnJavaScriptError(): Unit = configurations += "throwOnJSError" ->
    ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setThrowExceptionOnScriptError(true))

  override def swallowJavaScriptErrors(): Unit = configurations += "throwOnJSError" ->
    ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setThrowExceptionOnScriptError(false))

  override def enableCss(): Unit = configurations += "enableCss" ->
    ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setCssEnabled(true))

  override def disableCss(): Unit = configurations += "enableCss" ->
    ((webDriver: WebDriver) => asWebClientExposingDriverOrError(webDriver).getOptions.setCssEnabled(false))

  private def asWebClientExposingDriverOrError(webDriver: WebDriver): WebClientExposingDriver = webDriver match {
    case w: WebClientExposingDriver => w
    case _ => throw new RuntimeException(s"This configuration can only be applied to a webDriver of type ${classOf[WebClientExposingDriver].getCanonicalName}")
  }
} 
Example 9
Source File: AemTweaks.scala    From ScalaWebTest   with Apache License 2.0 5 votes vote down vote up
package org.scalawebtest.aem

import org.openqa.selenium.WebDriver
import org.scalawebtest.aem.WcmMode._
import org.scalawebtest.core._
import org.scalawebtest.core.configuration.BaseConfiguration


  def withWcmMode[X](mode: WcmMode): (X => Unit) => X => Unit = withWcmModeInternal(mode, _: X => Unit)

  private def withWcmModeInternal[X](mode: WcmMode, f: X => Unit): X => Unit = {
    x: X => {
      setWcmModeCookie(mode)
      try {
        f(x)
      } finally {
        setWcmModeCookie(DISABLED)
      }
    }
  }
} 
Example 10
Source File: JsonSpec.scala    From ScalaWebTest   with Apache License 2.0 5 votes vote down vote up
package org.scalawebtest.integration.json

import org.openqa.selenium.WebDriver
import org.scalawebtest.integration.ScalaWebTestBaseSpec
import play.api.libs.json.Json

class JsonSpec extends ScalaWebTestBaseSpec {
  path = "/jsonResponse.json.jsp"
  val model = new Scientist

  "A computer scientist" should "have the correct firstname" in {
    model.firstName should equal("Edsger")
  }
  it should "have the correct lastname" in {
    model.name should equal("Dijkstra")
  }
  it should "have the correct theories" in {
    model.theories should contain("graph theory")
  }
  it should "have the correct university names" in {
    model.universityNames should contain allOf(
      "Universität Leiden",
      "Mathematisch Centrum Amsterdam",
      "Technische Universiteit Eindhoven",
      "University of Texas at Austin"
      )
  }

  class Scientist(implicit webDriver: WebDriver) {
    def json = Json.parse(webDriver.getPageSource)
    def firstName = (json \ "firstName").as[String]
    def name = (json \ "name").as[String]
    def theories = (json \ "theories").as[List[String]]
    def universityNames = (json \ "universities" \\ "name").map(_.as[String])
  }
} 
Example 11
Source File: SeleniumTestContainerSuite.scala    From testcontainers-scala   with MIT License 5 votes vote down vote up
package com.dimafeng.testcontainers

import java.io.File
import java.net.URL
import java.util.Optional

import com.dimafeng.testcontainers.lifecycle.TestLifecycleAware
import org.openqa.selenium.WebDriver
import org.openqa.selenium.remote.{DesiredCapabilities, RemoteWebDriver}
import org.scalatest.Suite
import org.testcontainers.containers.BrowserWebDriverContainer
import org.testcontainers.lifecycle.TestDescription

trait SeleniumTestContainerSuite extends ForEachTestContainer {
  self: Suite =>

  def desiredCapabilities: DesiredCapabilities

  def recordingMode: (BrowserWebDriverContainer.VncRecordingMode, File) = null

  val container = SeleniumContainer(desiredCapabilities, recordingMode)

  implicit def webDriver: WebDriver = container.webDriver
}

class SeleniumContainer(desiredCapabilities: Option[DesiredCapabilities] = None,
                        recordingMode: Option[(BrowserWebDriverContainer.VncRecordingMode, File)] = None)
  extends SingleContainer[BrowserWebDriverContainer[_]] with TestLifecycleAware {
  require(desiredCapabilities.isDefined, "'desiredCapabilities' is required parameter")

  override val container: BrowserWebDriverContainer[_] = new BrowserWebDriverContainer()
  desiredCapabilities.foreach(container.withDesiredCapabilities)
  recordingMode.foreach(Function.tupled(container.withRecordingMode))

  def password: String = container.getPassword

  def port: Int = container.getPort

  def seleniumAddress: URL = container.getSeleniumAddress

  def vncAddress: String = container.getVncAddress

  def webDriver: RemoteWebDriver = container.getWebDriver

  override def afterTest(description: TestDescription, throwable: Option[Throwable]): Unit = {
    val javaThrowable: Optional[Throwable] = throwable match {
      case Some(error) => Optional.of(error)
      case None => Optional.empty()
    }
    container.afterTest(description, javaThrowable)
  }
}

object SeleniumContainer {
  def apply(desiredCapabilities: DesiredCapabilities = null, recordingMode: (BrowserWebDriverContainer.VncRecordingMode, File) = null): SeleniumContainer =
    new SeleniumContainer(Option(desiredCapabilities), Option(recordingMode))
} 
Example 12
Source File: UISeleniumSuite.scala    From drizzle-spark   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.{BeforeAndAfterAll, Matchers}
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._

import org.apache.spark.ui.SparkUICssErrorHandler

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver {
      getWebClient.setCssErrorHandler(new SparkUICssErrorHandler)
    }
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }

  ignore("thrift server ui test") {
    withJdbcStatement { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 13
Source File: TopBar.scala    From renku   with Apache License 2.0 5 votes vote down vote up
package ch.renku.acceptancetests.pages

import org.openqa.selenium.{WebDriver, WebElement}
import org.scalatestplus.selenium.WebBrowser.{cssSelector, find}

trait TopBar {
  self: RenkuPage =>

  object TopBar {

    def projects(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("ul.navbar-nav.mr-auto a[href='/projects']")) getOrElse fail(
        "Top Right 'Projects' link not found"
      )
    }

    def plusDropdown(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("#plus-dropdown")) getOrElse fail("Top Right '+' not found")
    }

    def projectOption(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("#navbar-project-new")) getOrElse fail("Project option not found")
    }

    def topRightDropDown(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("#profile-dropdown"))
        .getOrElse(fail("Top Right dropdown not found"))
    }

    def logoutLink(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("#logout-link")) getOrElse fail("Logout link not found")
    }
  }
} 
Example 14
Source File: NewProjectPage.scala    From renku   with Apache License 2.0 5 votes vote down vote up
package ch.renku.acceptancetests.pages

import ch.renku.acceptancetests.model.projects.ProjectDetails
import ch.renku.acceptancetests.pages.Page.{Path, Title}
import ch.renku.acceptancetests.tooling.ScreenCapturing
import eu.timepit.refined.auto._
import org.openqa.selenium.{WebDriver, WebElement}
import org.scalatestplus.selenium.{Driver, WebBrowser}
import org.scalatestplus.selenium.WebBrowser.{cssSelector, find}

import scala.concurrent.duration._
import scala.language.postfixOps

case object NewProjectPage extends RenkuPage with TopBar with ScreenCapturing {

  override val path:  Path  = "/project_new"
  override val title: Title = "Renku"

  override def pageReadyElement(implicit webDriver: WebDriver): Option[WebElement] = Some(createButton)

  def submitFormWith(
      project:          ProjectDetails
  )(implicit webDriver: WebDriver, browser: WebBrowser with Driver, captureScreenshots: Boolean = false): Unit =
    eventually {
      titleField.clear() sleep (1 second)
      titleField.enterValue(project.title.value) sleep (1 second)

      descriptionField.clear() sleep (1 second)
      descriptionField.enterValue(project.description.value) sleep (1 second)

      if (captureScreenshots) saveScreenshot

      createButton.click() sleep (2 seconds)
    }

  private def titleField(implicit webDriver: WebDriver): WebElement = eventually {
    find(cssSelector("input#title")) getOrElse fail("Title field not found")
  }

  private def descriptionField(implicit webDriver: WebDriver): WebElement = eventually {
    find(cssSelector("textarea#description")) getOrElse fail("Description field not found")
  }

  def createButton(implicit webDriver: WebDriver): WebElement = eventually {
    find(cssSelector("#create-new-project")) getOrElse fail("Create button not found")
  }
} 
Example 15
Source File: ProjectsPage.scala    From renku   with Apache License 2.0 5 votes vote down vote up
package ch.renku.acceptancetests.pages

import ch.renku.acceptancetests.model.projects.ProjectDetails
import ch.renku.acceptancetests.model.projects.ProjectDetails._
import ch.renku.acceptancetests.model.users.UserCredentials
import ch.renku.acceptancetests.pages.Page.{Path, Title}
import eu.timepit.refined.auto._
import org.openqa.selenium.{WebDriver, WebElement}
import org.scalatestplus.selenium.WebBrowser.{cssSelector, find}

case object ProjectsPage extends RenkuPage with TopBar {
  override val path:  Path  = "/projects"
  override val title: Title = "Renku"

  override def pageReadyElement(implicit webDriver: WebDriver): Option[WebElement] = Some(YourProjects.tab)

  object YourProjects {

    def tab(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("li.nav-item a[href='/projects']")) getOrElse fail("Projects -> Your Projects tab not found")
    }

    def linkTo(
        project:          ProjectDetails
    )(implicit webDriver: WebDriver, userCredentials: UserCredentials): WebElement =
      maybeLinkTo(project) getOrElse fail(s"Projects -> Your Projects -> '${project.title}' link not found")

    def maybeLinkTo(
        project:          ProjectDetails
    )(implicit webDriver: WebDriver, userCredentials: UserCredentials): Option[WebElement] = eventually {
      find(cssSelector(s"a[href='/projects/${userCredentials.username}/${project.title.toPathSegment}']"))
    }
  }
} 
Example 16
Source File: GitLabPages.scala    From renku   with Apache License 2.0 5 votes vote down vote up
package ch.renku.acceptancetests.pages

import ch.renku.acceptancetests.model.projects.ProjectDetails
import ch.renku.acceptancetests.model.projects.ProjectDetails._
import ch.renku.acceptancetests.model.users.UserCredentials
import ch.renku.acceptancetests.pages.Page.{Path, Title}
import ch.renku.acceptancetests.tooling.BaseUrl
import eu.timepit.refined.api.Refined
import eu.timepit.refined.auto._
import eu.timepit.refined.string.Url
import org.openqa.selenium.{WebDriver, WebElement}
import org.scalatestplus.selenium.WebBrowser.{cssSelector, find}

object GitLabPages {

  def apply()(implicit projectDetails: ProjectDetails, userCredentials: UserCredentials): GitLabPages =
    new GitLabPages(projectDetails, userCredentials)

  case class GitLabBaseUrl(value: String Refined Url) extends BaseUrl(value)

  sealed abstract class GitLabPage extends Page[GitLabBaseUrl]
}

class GitLabPages(
    projectDetails:  ProjectDetails,
    userCredentials: UserCredentials
) {

  import GitLabPages._

  case object ProjectPage extends GitLabPage {

    override val path: Path = Refined.unsafeApply(
      s"/gitlab/${userCredentials.userNamespace}/${projectDetails.title.toPathSegment}"
    )

    override val title: Title = Refined.unsafeApply(
      s"${userCredentials.fullName} / ${projectDetails.title} · GitLab"
    )

    override def pageReadyElement(implicit webDriver: WebDriver): Option[WebElement] = Some(settingsLink)

    def settingsLink(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("span.nav-item-name.qa-settings-item")) getOrElse fail("Settings link not found")
    }
  }

  case object GitLabProjectsPage extends GitLabPage {
    override val path:  Path  = "/gitlab/dashboard/projects"
    override val title: Title = "Projects · Dashboard · GitLab"
    override def pageReadyElement(implicit webDriver: WebDriver): Option[WebElement] = Some(newProjectButton)

    private def newProjectButton(implicit webDriver: WebDriver): WebElement = eventually {
      find(cssSelector("a[href='/gitlab/projects/new']")) getOrElse fail("New Project button not found")
    }
  }

  case object SettingsPage extends GitLabPage {

    override val path: Path = Refined.unsafeApply(
      s"/gitlab/${userCredentials.userNamespace}/${projectDetails.title.toPathSegment}/edit"
    )

    override val title: Title = Refined.unsafeApply(
      s"General · Settings · ${userCredentials.fullName} / ${projectDetails.title} · GitLab"
    )

    override def pageReadyElement(implicit webDriver: WebDriver): Option[WebElement] = Some(Advanced.expandButton)

    object Advanced {

      def expandButton(implicit webDriver: WebDriver): WebElement = eventually {
        find(cssSelector("section.advanced-settings button.js-settings-toggle")) getOrElse fail(
          "Advanced -> Expand button not found"
        )
      }

      def removeProject(implicit webDriver: WebDriver): WebElement = eventually {
        find(cssSelector("form > input[value='Remove project'")) getOrElse fail(
          "Advanced -> Remove project button not found"
        )
      }

      def confirmRemoval(project: ProjectDetails)(implicit webDriver: WebDriver): Unit = eventually {
        find(cssSelector("input#confirm_name_input"))
          .getOrElse(fail("Advanced -> Project removal name confirmation input not found"))
          .enterValue(project.title.toPathSegment)

        find(cssSelector("input[value='Confirm'"))
          .getOrElse(fail("Advanced -> Project removal Confirm button not found"))
          .click()
      }
    }
  }
} 
Example 17
Source File: JupyterLabPage.scala    From renku   with Apache License 2.0 5 votes vote down vote up
package ch.renku.acceptancetests.pages

import ch.renku.acceptancetests.model.projects.{ProjectDetails, ProjectIdentifier}
import ch.renku.acceptancetests.model.projects.ProjectDetails._
import ch.renku.acceptancetests.model.users.UserCredentials
import ch.renku.acceptancetests.pages.Page.{Path, Title}
import eu.timepit.refined.api.Refined
import eu.timepit.refined.auto._
import org.openqa.selenium.Keys.RETURN
import org.openqa.selenium.interactions.Actions
import org.openqa.selenium.{WebDriver, WebElement}
import org.scalatestplus.selenium.WebBrowser.{cssSelector, find}

object JupyterLabPage {
  def apply()(implicit projectDetails: ProjectDetails, userCredentials: UserCredentials): JupyterLabPage =
    new JupyterLabPage(projectDetails.title.toPathSegment, userCredentials.userNamespace)

  def apply(projectId: ProjectIdentifier): JupyterLabPage =
    new JupyterLabPage(projectId.slug, projectId.namespace)
}

class JupyterLabPage(projectSlug: String, namespace: String) extends RenkuPage {

  override val title: Title = "JupyterLab"
  override val path: Path = Refined.unsafeApply(
    s"/jupyterhub/user/${namespace}/${projectSlug}"
  )

  override def pageReadyElement(implicit webDriver: WebDriver): Option[WebElement] = Some(terminalIcon)

  def terminalIcon(implicit webDriver: WebDriver): WebElement = eventually {
    find(cssSelector("div.jp-LauncherCard [data-icon='ui-components:terminal']")) getOrElse fail(
      "Terminal icon not found"
    )
  }

  object terminal {

    def %>(command: String)(implicit webDriver: WebDriver): Unit = eventually {
      val terminalElement = find(cssSelector("#jp-Terminal-0 > div > div.xterm-screen > canvas.xterm-cursor-layer")) getOrElse fail(
        "Terminal not found"
      )

      new Actions(webDriver)
        .moveToElement(terminalElement)
        .click()
        .sendKeys(s"$command$RETURN")
        .build()
        .perform()
    }
  }
} 
Example 18
Source File: Page.scala    From renku   with Apache License 2.0 5 votes vote down vote up
package ch.renku.acceptancetests.pages

import ch.renku.acceptancetests.pages.Page._
import ch.renku.acceptancetests.pages.RenkuPage.RenkuBaseUrl
import ch.renku.acceptancetests.tooling._
import eu.timepit.refined.W
import eu.timepit.refined.api.Refined
import eu.timepit.refined.collection.NonEmpty
import eu.timepit.refined.string._
import org.openqa.selenium.{By, WebDriver, WebElement}
import org.scalatest.concurrent.Eventually
import org.scalatest.time.{Seconds, Span}
import org.scalatest.{Matchers => ScalatestMatchers}
import org.scalatestplus.selenium.WebBrowser

import scala.concurrent.duration._
import scala.language.{implicitConversions, postfixOps}

abstract class Page[Url <: BaseUrl] extends ScalatestMatchers with Eventually with AcceptanceSpecPatience {

  val path:  Path
  val title: Title
  def pageReadyElement(implicit webDriver: WebDriver): Option[WebElement]
  def url(implicit baseUrl:                Url): String = s"$baseUrl$path"

  protected implicit def toWebElement(element: WebBrowser.Element): WebElement =
    element.underlying
  protected implicit def toMaybeWebElement(maybeElement: Option[WebBrowser.Element]): Option[WebElement] =
    maybeElement.map(_.underlying)

  protected implicit class ElementOps(element: WebBrowser.Element) {

    def parent: WebElement = element.findElement(By.xpath("./.."))

    def enterValue(value: String): Unit = value foreach { char =>
      element.sendKeys(char.toString) sleep (100 millis)
    }
  }

  protected implicit class WebElementOps(element: WebElement) {

    def enterValue(value: String): Unit = value foreach { char =>
      element.sendKeys(char.toString) sleep (100 millis)
    }
  }

  object sleep {
    def apply(duration: Duration): Unit = Page.SleepThread(duration)
  }

  protected implicit class OperationOps(unit: Unit) {
    def sleep(duration: Duration): Unit = Page.SleepThread(duration)
  }

  protected def waitUpTo(duration: Duration): PatienceConfig =
    PatienceConfig(
      // Wait up to 2 minutes for this operation
      timeout  = scaled(Span(AcceptanceSpecPatience.WAIT_SCALE * duration.toSeconds, Seconds)),
      interval = scaled(Span(2, Seconds))
    )
}

object Page {
  type Path  = String Refined StartsWith[W.`"/"`.T]
  type Title = String Refined NonEmpty

  // Use a unique name to avoid problems on case-insensitive and preserving file systems
  object SleepThread {
    def apply(duration: Duration): Unit = Thread sleep duration.toMillis
  }
}

abstract class RenkuPage extends Page[RenkuBaseUrl]

object RenkuPage {
  case class RenkuBaseUrl(value: String Refined Url) extends BaseUrl(value)
} 
Example 19
Source File: UISeleniumSuite.scala    From sparkoscope   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.{BeforeAndAfterAll, Matchers}
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._

import org.apache.spark.ui.SparkUICssErrorHandler

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver {
      getWebClient.setCssErrorHandler(new SparkUICssErrorHandler)
    }
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }

  ignore("thrift server ui test") {
    withJdbcStatement { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 20
Source File: UISeleniumSuite.scala    From XSQL   with Apache License 2.0 5 votes vote down vote up
package org.apache.spark.sql.hive.thriftserver

import scala.util.Random

import org.apache.hadoop.hive.conf.HiveConf.ConfVars
import org.openqa.selenium.WebDriver
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.scalatest.{BeforeAndAfterAll, Matchers}
import org.scalatest.concurrent.Eventually._
import org.scalatest.selenium.WebBrowser
import org.scalatest.time.SpanSugar._

import org.apache.spark.ui.SparkUICssErrorHandler

class UISeleniumSuite
  extends HiveThriftJdbcTest
  with WebBrowser with Matchers with BeforeAndAfterAll {

  implicit var webDriver: WebDriver = _
  var server: HiveThriftServer2 = _
  val uiPort = 20000 + Random.nextInt(10000)
  override def mode: ServerMode.Value = ServerMode.binary

  override def beforeAll(): Unit = {
    webDriver = new HtmlUnitDriver {
      getWebClient.setCssErrorHandler(new SparkUICssErrorHandler)
    }
    super.beforeAll()
  }

  override def afterAll(): Unit = {
    if (webDriver != null) {
      webDriver.quit()
    }
    super.afterAll()
  }

  override protected def serverStartCommand(port: Int) = {
    val portConf = if (mode == ServerMode.binary) {
      ConfVars.HIVE_SERVER2_THRIFT_PORT
    } else {
      ConfVars.HIVE_SERVER2_THRIFT_HTTP_PORT
    }

    s"""$startScript
        |  --master local
        |  --hiveconf hive.root.logger=INFO,console
        |  --hiveconf ${ConfVars.METASTORECONNECTURLKEY}=$metastoreJdbcUri
        |  --hiveconf ${ConfVars.METASTOREWAREHOUSE}=$warehousePath
        |  --hiveconf ${ConfVars.HIVE_SERVER2_THRIFT_BIND_HOST}=localhost
        |  --hiveconf ${ConfVars.HIVE_SERVER2_TRANSPORT_MODE}=$mode
        |  --hiveconf $portConf=$port
        |  --driver-class-path ${sys.props("java.class.path")}
        |  --conf spark.ui.enabled=true
        |  --conf spark.ui.port=$uiPort
     """.stripMargin.split("\\s+").toSeq
  }

  ignore("thrift server ui test") {
    withJdbcStatement("test_map") { statement =>
      val baseURL = s"http://localhost:$uiPort"

      val queries = Seq(
        "CREATE TABLE test_map(key INT, value STRING)",
        s"LOAD DATA LOCAL INPATH '${TestData.smallKv}' OVERWRITE INTO TABLE test_map")

      queries.foreach(statement.execute)

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to baseURL
        find(cssSelector("""ul li a[href*="sql"]""")) should not be None
      }

      eventually(timeout(10 seconds), interval(50 milliseconds)) {
        go to (baseURL + "/sql")
        find(id("sessionstat")) should not be None
        find(id("sqlstat")) should not be None

        // check whether statements exists
        queries.foreach { line =>
          findAll(cssSelector("""ul table tbody tr td""")).map(_.text).toList should contain (line)
        }
      }
    }
  }
} 
Example 21
Source File: TodoListTest.scala    From scala-json-rpc   with MIT License 5 votes vote down vote up
package io.github.shogowada.scala.jsonrpc.example.e2e.websocket.integrationtest

import io.github.shogowada.scala.jsonrpc.example.e2e.websocket.ElementIds
import org.openqa.selenium.support.ui.{ExpectedCondition, ExpectedConditions, WebDriverWait}
import org.openqa.selenium.{By, WebDriver}
import org.scalatest.concurrent.Eventually
import org.scalatest.selenium.{Chrome, Firefox}
import org.scalatest.{Matchers, path}

class TodoListTest extends path.FreeSpec
    with Chrome
    with Eventually
    with Matchers {

  def waitFor[T](condition: ExpectedCondition[T])(implicit webDriver: WebDriver): T = {
    new WebDriverWait(webDriver, 3).until[T](condition)
  }

  "given I am on TODO list" - {
    go to Target.url

    waitFor(ExpectedConditions.textToBe(By.id(ElementIds.Ready), "Ready!"))

    clearTodos()

    "when I add TODO item" - {
      val newTodoDescription = "Say hello"

      waitFor(ExpectedConditions.visibilityOfElementLocated(By.id(ElementIds.NewTodoDescription)))
      textField(id(ElementIds.NewTodoDescription)).value = newTodoDescription
      clickOn(id(ElementIds.AddTodo))

      "then it should add the item" in {
        verifyTodoExists(newTodoDescription)
      }

      "and I reload the page" - {
        reloadPage()

        "then it should still show the item" in {
          verifyTodoExists(newTodoDescription)
        }
      }

      "and removed the item" - {
        find(cssSelector("li>button")).foreach(element => clickOn(element))

        "then it should remove the item" in {
          eventually {
            findAll(tagName("li")) shouldBe empty
          }
        }
      }
    }
  }

  def clearTodos(): Unit = {
    findAll(cssSelector("li>button")).foreach(element => clickOn(element))
  }

  def verifyTodoExists(description: String): Unit = {
    eventually {
      findAll(tagName("li")).exists(element => element.text.contains(description)) should equal(true)
    }
  }

  quit()
}