Merge pull request #50 from dougmorato/testing_work
Adding headless Integration Tests with Sauce Labs
This commit is contained in:
commit
c67bd73768
13
.travis.yml
13
.travis.yml
@ -1,17 +1,14 @@
|
||||
language: java
|
||||
|
||||
jdk:
|
||||
- oraclejdk7
|
||||
- oraclejdk8
|
||||
install: "/bin/true"
|
||||
|
||||
script:
|
||||
- mvn clean compile install
|
||||
- git clone https://github.com/WebGoat/WebGoat-Lessons.git
|
||||
- mvn -file ./WebGoat-Lessons/pom.xml package
|
||||
- cp -fa ./WebGoat-Lessons/target/plugins/*.jar ./webgoat-container/src/main/webapp/plugin_lessons/
|
||||
- mvn package
|
||||
|
||||
- mvn -Prun-integration-tests package verify install
|
||||
before_deploy:
|
||||
- export WEBGOAT_ARTIFACT_VERSION=$(grep "<version>" $HOME/build/$TRAVIS_REPO_SLUG/pom.xml | cut -d ">" -f 2 | cut -d "<" -f 1)
|
||||
- export WEBGOAT_JAR_FILE=$HOME/build/$TRAVIS_REPO_SLUG/webgoat-container/target/webgoat-container-$WEBGOAT_ARTIFACT_VERSION.jar
|
||||
@ -24,12 +21,11 @@ before_deploy:
|
||||
- mv $WEBGOAT_WAR_FILE $WEBGOAT_ARTIFACTS_FOLDER
|
||||
- echo "Contents of artifcts folder:"
|
||||
- ls $WEBGOAT_ARTIFACTS_FOLDER
|
||||
|
||||
deploy:
|
||||
provider: s3
|
||||
access_key_id: AKIAJQLKPGHXRH2AH5QA
|
||||
secret_access_key:
|
||||
secure: "45+SwWlPFujD9FOOFLA9Lz0CaePVrn/SEsAhAn0Ve9sYpI0VsijZNymh6D29t93jBXgZoGhu/v0QJkcAA/71fQM+nGMBJjB5wmVFJ1c2A4k7tfWCVbBRI0aHGpJu12j+7BLuSfPCmCAFQGoVo7dWzfqeODe5j9Qpe9fsiQVnrKI="
|
||||
secure: 45+SwWlPFujD9FOOFLA9Lz0CaePVrn/SEsAhAn0Ve9sYpI0VsijZNymh6D29t93jBXgZoGhu/v0QJkcAA/71fQM+nGMBJjB5wmVFJ1c2A4k7tfWCVbBRI0aHGpJu12j+7BLuSfPCmCAFQGoVo7dWzfqeODe5j9Qpe9fsiQVnrKI=
|
||||
bucket: webgoat-war
|
||||
skip_cleanup: true
|
||||
acl: public_read
|
||||
@ -38,8 +34,9 @@ deploy:
|
||||
repo: WebGoat/WebGoat
|
||||
branch: master
|
||||
jdk: oraclejdk8
|
||||
|
||||
notifications:
|
||||
slack:
|
||||
rooms:
|
||||
secure: "neH9u/VMnwh214CvS2QAsbohqQpcoi7dDM0djTqHe0gpBjtOhEeqBJV3mQYLTvgOBvHuKXVLSVufSb/sqh8KzmpblGpcXp6XSvGqBuXgIIZ3MhkGCIU8QtDfzOuYKS80cmB4EHh1EfvlqJQeLD+FCIql5IZfKmZysEekBuuXqBA="
|
||||
secure: "RS/QCVjDAt8y7c816d8UIJUl2OLaRRU6gjh//7Kb4f9TyKRACtP0Qa9NVNhSXuvb2kzUTOFb76Lz8utnt2a3iZ+elZMvnQu8+HioKr9wWJPKml8TLC+tCclQnSAz7orsQ0ubgUlsVycs7bsaQ79aKw1C9YdH+QNDgMKDxvfrEKk="
|
||||
addons:
|
||||
sauce_connect: true
|
||||
|
@ -18,6 +18,99 @@
|
||||
<tiles.version>2.2.2</tiles.version>
|
||||
</properties>
|
||||
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>run-integration-tests</id>
|
||||
<activation>
|
||||
<activeByDefault>false</activeByDefault>
|
||||
<property>
|
||||
<name>run-integration</name>
|
||||
<value>true</value>
|
||||
</property>
|
||||
</activation>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.tomcat.maven</groupId>
|
||||
<artifactId>tomcat7-maven-plugin</artifactId>
|
||||
<version>2.2</version>
|
||||
<configuration>
|
||||
<server>local_tomcat</server>
|
||||
<url>http://localhost:8080/manager</url>
|
||||
<path>/WebGoat</path>
|
||||
<attachArtifactClassifier>exec</attachArtifactClassifier>
|
||||
<contextReloadable>true</contextReloadable>
|
||||
<useSeparateTomcatClassLoader>true</useSeparateTomcatClassLoader>
|
||||
<contextFile>${project.basedir}/src/main/webapp/WEB-INF/context.xml</contextFile>
|
||||
</configuration>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.owasp.webgoat</groupId>
|
||||
<artifactId>webgoat-classloader</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.owasp.webgoat</groupId>
|
||||
<artifactId>webgoat-container</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>tomcat-run</id>
|
||||
<goals>
|
||||
<goal>exec-war-only</goal>
|
||||
</goals>
|
||||
<phase>package</phase>
|
||||
<configuration>
|
||||
<extraDependencies>
|
||||
<extraDependency>
|
||||
<groupId>org.owasp.webgoat</groupId>
|
||||
<artifactId>webgoat-classloader</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</extraDependency>
|
||||
</extraDependencies>
|
||||
</configuration>
|
||||
</execution>
|
||||
<execution>
|
||||
<id>start-tomcat</id>
|
||||
<phase>pre-integration-test</phase>
|
||||
<goals>
|
||||
<goal>run-war-only</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<port>8888</port>
|
||||
<fork>true</fork>
|
||||
</configuration>
|
||||
</execution>
|
||||
<!-- At post-integration-test phase, stop the embedded Tomcat server. -->
|
||||
<execution>
|
||||
<id>stop-tomcat</id>
|
||||
<phase>post-integration-test</phase>
|
||||
<goals>
|
||||
<goal>shutdown</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-failsafe-plugin</artifactId>
|
||||
<version>2.18.1</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>integration-test</goal>
|
||||
<goal>verify</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</profile>
|
||||
</profiles>
|
||||
|
||||
<build>
|
||||
<resources>
|
||||
<resource>
|
||||
@ -96,10 +189,10 @@
|
||||
<plugin>
|
||||
<groupId>org.apache.tomcat.maven</groupId>
|
||||
<artifactId>tomcat7-maven-plugin</artifactId>
|
||||
<version>2.1</version>
|
||||
<version>2.2</version>
|
||||
<configuration>
|
||||
<server>local_tomcat</server>
|
||||
<url>http://localhost:8080/manager/text</url>
|
||||
<url>http://localhost:8080/manager</url>
|
||||
<path>/WebGoat</path>
|
||||
<attachArtifactClassifier>exec</attachArtifactClassifier>
|
||||
<contextReloadable>true</contextReloadable>
|
||||
@ -137,6 +230,16 @@
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-surefire-plugin</artifactId>
|
||||
<version>2.18.1</version>
|
||||
<configuration>
|
||||
<excludes>
|
||||
<exclude>**/*IT.java</exclude>
|
||||
</excludes>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
@ -260,7 +363,7 @@
|
||||
<dependency>
|
||||
<groupId>org.apache.tomcat</groupId>
|
||||
<artifactId>tomcat-catalina</artifactId>
|
||||
<version>7.0.27</version>
|
||||
<version>7.0.63</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
|
||||
@ -364,12 +467,6 @@
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>junit</groupId>
|
||||
<artifactId>junit</artifactId>
|
||||
<version>4.8.1</version>
|
||||
<type>jar</type>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.tiles</groupId>
|
||||
<artifactId>tiles-core</artifactId>
|
||||
@ -388,9 +485,26 @@
|
||||
<version>1.7.7</version>
|
||||
<type>jar</type>
|
||||
</dependency>
|
||||
<!-- ************* END spring MVC and related dependencies ************** -->
|
||||
<!-- ************* START: Dependencies for Unit and Integration Testing ************** -->
|
||||
<dependency>
|
||||
<groupId>junit</groupId>
|
||||
<artifactId>junit</artifactId>
|
||||
<version>4.12</version>
|
||||
<type>jar</type>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.seleniumhq.selenium</groupId>
|
||||
<artifactId>selenium-java</artifactId>
|
||||
<version>2.47.1</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.saucelabs</groupId>
|
||||
<artifactId>sauce_junit</artifactId>
|
||||
<version>2.1.18</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<!-- ************* END: Dependencies for Unit and Integration Testing ************** -->
|
||||
<!-- ************* END: <dependencies> ************** -->
|
||||
</dependencies>
|
||||
|
||||
|
||||
<!-- ************* END spring MVC and related dependencies ************** -->
|
||||
|
||||
</project>
|
||||
|
@ -0,0 +1,287 @@
|
||||
package org.owasp.webgoat.plugins;
|
||||
|
||||
import com.saucelabs.common.SauceOnDemandAuthentication;
|
||||
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Rule;
|
||||
import org.junit.Test;
|
||||
import org.junit.rules.TestName;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.openqa.selenium.By;
|
||||
import org.openqa.selenium.WebDriver;
|
||||
import org.openqa.selenium.WebElement;
|
||||
import org.openqa.selenium.remote.CapabilityType;
|
||||
import org.openqa.selenium.remote.DesiredCapabilities;
|
||||
import org.openqa.selenium.remote.RemoteWebDriver;
|
||||
|
||||
import com.saucelabs.junit.ConcurrentParameterized;
|
||||
import com.saucelabs.junit.SauceOnDemandTestWatcher;
|
||||
|
||||
import java.net.URL;
|
||||
import java.util.LinkedList;
|
||||
|
||||
import static org.junit.Assert.*;
|
||||
|
||||
import com.saucelabs.common.SauceOnDemandSessionIdProvider;
|
||||
|
||||
import org.openqa.selenium.support.ui.ExpectedConditions;
|
||||
import org.openqa.selenium.support.ui.WebDriverWait;
|
||||
|
||||
|
||||
/**
|
||||
* Created by Doug Morato <dm@corp.io> on 8/21/15.
|
||||
*
|
||||
*/
|
||||
@RunWith(ConcurrentParameterized.class)
|
||||
public class WebGoatIT implements SauceOnDemandSessionIdProvider {
|
||||
|
||||
// Since most Tomcat deployments run on port 8080, let's set the automated integration tests to
|
||||
// spawn tomcat on port 8888 so that we don't interfere with local Tomcat's
|
||||
private String baseWebGoatUrl = "http://localhost:8888/WebGoat";
|
||||
private String loginUser = "webgoat";
|
||||
private String loginPassword = "webgoat";
|
||||
|
||||
// Sauce Labs settings
|
||||
public String username = System.getenv("SAUCE_USER_NAME") != null ? System.getenv("SAUCE_USER_NAME") : System.getenv("SAUCE_USERNAME");
|
||||
public String accesskey = System.getenv("SAUCE_API_KEY") != null ? System.getenv("SAUCE_API_KEY") : System.getenv("SAUCE_ACCESS_KEY");
|
||||
|
||||
/**
|
||||
* Constructs a {@link SauceOnDemandAuthentication} instance using the supplied user name/access key. To use the authentication
|
||||
* supplied by environment variables or from an external file, use the no-arg {@link SauceOnDemandAuthentication} constructor.
|
||||
*/
|
||||
public SauceOnDemandAuthentication authentication = new SauceOnDemandAuthentication(username, accesskey);
|
||||
|
||||
/**
|
||||
* JUnit Rule which will mark the Sauce Job as passed/failed when the test succeeds or fails.
|
||||
*/
|
||||
@Rule
|
||||
public SauceOnDemandTestWatcher resultReportingTestWatcher = new SauceOnDemandTestWatcher(this, authentication);
|
||||
|
||||
@Rule public TestName name = new TestName() {
|
||||
public String getMethodName() {
|
||||
return String.format("%s : (%s %s %s)", super.getMethodName(), os, browser, version);
|
||||
};
|
||||
};
|
||||
|
||||
/**
|
||||
* Represents the browser to be used as part of the test run.
|
||||
*/
|
||||
private String browser;
|
||||
/**
|
||||
* Represents the operating system to be used as part of the test run.
|
||||
*/
|
||||
private String os;
|
||||
/**
|
||||
* Represents the version of the browser to be used as part of the test run.
|
||||
*/
|
||||
private String version;
|
||||
/**
|
||||
* Represents the deviceName of mobile device
|
||||
*/
|
||||
private String deviceName;
|
||||
/**
|
||||
* Represents the device-orientation of mobile device
|
||||
*/
|
||||
private String deviceOrientation;
|
||||
/**
|
||||
* Instance variable which contains the Sauce Job Id.
|
||||
*/
|
||||
private String sessionId;
|
||||
|
||||
/**
|
||||
* The {@link WebDriver} instance which is used to perform browser interactions with.
|
||||
*/
|
||||
private WebDriver driver;
|
||||
|
||||
|
||||
/**
|
||||
* Constructs a new instance of the test. The constructor requires three string parameters, which represent the operating
|
||||
* system, version and browser to be used when launching a Sauce VM. The order of the parameters should be the same
|
||||
* as that of the elements within the {@link #browsersStrings()} method.
|
||||
* @param os
|
||||
* @param version
|
||||
* @param browser
|
||||
* @param deviceName
|
||||
* @param deviceOrientation
|
||||
*/
|
||||
|
||||
public WebGoatIT(String os, String version, String browser, String deviceName, String deviceOrientation) {
|
||||
super();
|
||||
this.os = os;
|
||||
this.version = version;
|
||||
this.browser = browser;
|
||||
this.deviceName = deviceName;
|
||||
this.deviceOrientation = deviceOrientation;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a LinkedList containing String arrays representing the browser combinations the test should be run against. The values
|
||||
* in the String array are used as part of the invocation of the test constructor
|
||||
*/
|
||||
@ConcurrentParameterized.Parameters
|
||||
public static LinkedList browsersStrings() {
|
||||
LinkedList browsers = new LinkedList();
|
||||
|
||||
// windows 7, Chrome 41
|
||||
browsers.add(new String[]{"Windows 7", "41", "chrome", null, null});
|
||||
|
||||
// windows 7, IE 9
|
||||
//browsers.add(new String[]{"Windows 7", "9", "internet explorer", null, null});
|
||||
|
||||
// windows 8, IE 10
|
||||
//browsers.add(new String[]{"Windows 8", "10", "internet explorer", null, null});
|
||||
|
||||
// windows 8.1, IE 11
|
||||
//browsers.add(new String[]{"Windows 8.1", "11", "internet explorer", null, null});
|
||||
|
||||
// OS X 10.9, Safari 7
|
||||
//browsers.add(new String[]{"OSX 10.9", "7", "safari", null, null});
|
||||
|
||||
// OS X 10.10, Safari 7
|
||||
//browsers.add(new String[]{"OSX 10.10", "8", "safari", null, null});
|
||||
|
||||
// Linux, Firefox 37
|
||||
//browsers.add(new String[]{"Linux", "37", "firefox", null, null});
|
||||
|
||||
return browsers;
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructs a new {@link RemoteWebDriver} instance which is configured to use the capabilities defined by the {@link #browser},
|
||||
* {@link #version} and {@link #os} instance variables, and which is configured to run against ondemand.saucelabs.com, using
|
||||
* the username and access key populated by the {@link #authentication} instance.
|
||||
*
|
||||
* @throws Exception if an error occurs during the creation of the {@link RemoteWebDriver} instance.
|
||||
*/
|
||||
@Before
|
||||
public void setUp() throws Exception {
|
||||
DesiredCapabilities capabilities = new DesiredCapabilities();
|
||||
|
||||
if (browser != null) capabilities.setCapability(CapabilityType.BROWSER_NAME, browser);
|
||||
if (version != null) capabilities.setCapability(CapabilityType.VERSION, version);
|
||||
if (deviceName != null) capabilities.setCapability("deviceName", deviceName);
|
||||
if (deviceOrientation != null) capabilities.setCapability("device-orientation", deviceOrientation);
|
||||
|
||||
if ( System.getenv("CI") != null && System.getenv("TRAVIS").equals("true")) {
|
||||
capabilities.setCapability("tunnelIdentifier", System.getenv("TRAVIS_JOB_NUMBER"));
|
||||
capabilities.setCapability("tags", System.getenv("TRAVIS_PULL_REQUEST"));
|
||||
capabilities.setCapability("build", System.getenv("TRAVIS_BUILD_NUMBER"));
|
||||
}
|
||||
|
||||
capabilities.setCapability(CapabilityType.PLATFORM, os);
|
||||
|
||||
String methodName = name.getMethodName();
|
||||
capabilities.setCapability("name", methodName);
|
||||
|
||||
this.driver = new RemoteWebDriver(
|
||||
new URL("http://" + authentication.getUsername() + ":" + authentication.getAccessKey() +
|
||||
"@ondemand.saucelabs.com:80/wd/hub"),
|
||||
capabilities);
|
||||
this.sessionId = (((RemoteWebDriver) driver).getSessionId()).toString();
|
||||
|
||||
String message = String.format("SauceOnDemandSessionID=%1$s job-name=%2$s", this.sessionId, methodName);
|
||||
System.out.println(message);
|
||||
}
|
||||
|
||||
public void doLoginWebgoatUser() {
|
||||
|
||||
driver.get(baseWebGoatUrl + "/login.mvc");
|
||||
|
||||
WebDriverWait wait = new WebDriverWait(driver, 10); // wait for a maximum of 5 seconds
|
||||
wait.until(ExpectedConditions.presenceOfElementLocated(By.id("exampleInputEmail1")));
|
||||
wait.until(ExpectedConditions.presenceOfElementLocated(By.id("exampleInputPassword1")));
|
||||
|
||||
|
||||
WebElement usernameElement = driver.findElement(By.name("username"));
|
||||
WebElement passwordElement = driver.findElement(By.name("password"));
|
||||
usernameElement.sendKeys(loginUser);
|
||||
passwordElement.sendKeys(loginPassword);
|
||||
passwordElement.submit();
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs a simple test verifying the UI and title of the WebGoat home page.
|
||||
* @throws Exception
|
||||
*/
|
||||
@Test
|
||||
public void verifyWebGoatLoginPage() throws Exception {
|
||||
driver.get(baseWebGoatUrl + "/login.mvc");
|
||||
WebDriverWait wait = new WebDriverWait(driver, 10); // wait for a maximum of 5 seconds
|
||||
wait.until(ExpectedConditions.presenceOfElementLocated(By.id("exampleInputEmail1")));
|
||||
wait.until(ExpectedConditions.presenceOfElementLocated(By.id("exampleInputPassword1")));
|
||||
|
||||
assertTrue(driver.getTitle().equals("Login Page"));
|
||||
|
||||
WebElement usernameElement = driver.findElement(By.name("username"));
|
||||
WebElement passwordElement = driver.findElement(By.name("password"));
|
||||
assertNotNull(usernameElement);
|
||||
assertNotNull(passwordElement);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testStartMvc() {
|
||||
|
||||
driver.get(baseWebGoatUrl + "/start.mvc");
|
||||
|
||||
WebDriverWait wait = new WebDriverWait(driver, 10); // wait for a maximum of 5 seconds
|
||||
wait.until(ExpectedConditions.presenceOfElementLocated(By.name("username")));
|
||||
wait.until(ExpectedConditions.presenceOfElementLocated(By.name("password")));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testWebGoatUserLogin() {
|
||||
|
||||
doLoginWebgoatUser();
|
||||
|
||||
assertTrue("user: webgoat is not in the page source", driver.getPageSource().contains("User: webgoat"));
|
||||
WebElement cookieParameters = driver.findElement(By.id("cookies-and-params"));
|
||||
assertNotNull("element id=cookieParameters should be displayed to user upon successful login", cookieParameters);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testServiceLessonMenuMVC() {
|
||||
|
||||
doLoginWebgoatUser();
|
||||
|
||||
driver.get(baseWebGoatUrl + "/service/lessonmenu.mvc");
|
||||
|
||||
String pageSource = driver.getPageSource();
|
||||
|
||||
assertTrue("Page source should contain lessons: Test 1", pageSource.contains("Bypass a Path Based Access Control Scheme"));
|
||||
assertTrue("Page source should contain lessons: Test 2", pageSource.contains("Access Control Flaws"));
|
||||
assertTrue("Page source should contain lessons: Test 3", pageSource.contains("Improper Error Handling"));
|
||||
assertTrue("Page source should contain lessons: Test 34", pageSource.contains("Fail Open Authentication Scheme"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testLogoutMvc() {
|
||||
|
||||
doLoginWebgoatUser();
|
||||
|
||||
driver.get(baseWebGoatUrl + "/logout.mvc");
|
||||
|
||||
assertTrue("Page title should be Logout Page", driver.getTitle().contains("Logout Page"));
|
||||
assertTrue("Logout message should be displayed to user when successful logout", driver.getPageSource().contains("You have logged out successfully"));
|
||||
}
|
||||
|
||||
/**
|
||||
* Closes the {@link WebDriver} session.
|
||||
*
|
||||
* @throws Exception
|
||||
*/
|
||||
@After
|
||||
public void tearDown() throws Exception {
|
||||
driver.quit();
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* @return the value of the Sauce Job id.
|
||||
*/
|
||||
@Override
|
||||
public String getSessionId() {
|
||||
return sessionId;
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user