Alien Driven Development
Integrationstests with Pleasure
http://blog.eisele.net/
@myfear
http://myfear.com/+
markus@eisele.net
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net4
Testing is too hard.
Testing isn’t fun.
Testing is so sloow.
Testing sucks!
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net5
Unit Tests Integration Tests System Tests
Complexity
Functional
Test Code
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net6
You can’t fix what you can’t run.
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net7
You can’t fix what you can’t debug.
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net8
You can’t fix what you can’t test.
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net9
You can’t develop what you can’t test.
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net10
Not testing needs to be more painful
And time consuming than using testing.
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net11
What is touched
by testing?
Frameworks
Build
IDE
Server
Client
Code
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net12
Frameworks
Build
IDE
Server
Client
EE Spring DI
Maven Ant Gradle
Eclipse NetBeans IntelliJ
GlassFish Tomcat AS7
IE Chrome FF
…
…
…
…
…
Code Source Test Other …
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net13
http://www.youtube.com/watch?v=VpZmIiIXuZ0
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net14
An Innovative Testing Platform for the JVM
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net15
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net16
Guiding Principles
 Tests should be portable to any supported container
 Tests should be executable from IDE and build tool
 Should extend or integrate existing test frameworks
https://docs.jboss.org/author/display/ARQ/Reference+Guide
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net17
SourceTest
IDE
Build
Frameworks
Tests Classes
Server
Deps
Package
~
Client
arquillian
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net18
SourceTest
IDE
Build
Tests Classes
Server
Deps
Package
ClientPackage
Client
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net19
Lifecycle
 Select Container
 Start Container
 Package Archive
 Run Test in Container
 Show Results
 Undeploy / Disconnect
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net20
Basic Setup
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.jboss.arquillian</groupId>
<artifactId>arquillian-bom</artifactId>
<version>1.0.4.Final</version>
<scope>import</scope>
<type>pom</type>
</dependency>
</dependencies>
</dependencyManagement>
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net21
<dependencies>
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-web-api</artifactId>
<version>7.0</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.8.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.jboss.arquillian.junit</groupId>
<artifactId>arquillian-junit-container</artifactId>
<scope>test</scope>
</dependency>
<!-- … -->
</dependencies>
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net22
Java EE Container Support
Embedded Managed Remote
https://docs.jboss.org/author/display/ARQ/Container+adapters
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net23
<profiles>
<profile>
<id>arquillian-glassfish-managed</id>
<dependencies>
<dependency>
<groupId>org.jboss.arquillian.container</groupId>
<artifactId>arquillian-glassfish-managed-3.1</artifactId>
<version>1.0.0.CR4</version>
<scope>test</scope>
</dependency>
</dependencies>
</profile>
</profiles>
https://docs.jboss.org/author/display/ARQ/Container+adapters
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net24
<?xml version="1.0" encoding="UTF-8"?>
<arquillian xmlns="http://jboss.org/schema/arquillian"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://jboss.org/schema/arquillian
http://jboss.org/schema/arquillian/arquillian_1_0.xsd">
<container qualifier="glassfish" default="true">
<configuration>
<property name="glassFishHome">D:glassfish4-b85</property>
<property name="adminHost">localhost</property>
<property name="adminPort">4848</property>
</configuration>
</container>
</arquillian>
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net25
@Stateless
public class HelloBean {
public String sayHello(String name) {
return "Hello " + name + "!";
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net26
@RunWith(Arquillian.class)
public class HelloBeanIntegrationTest {
@EJB
HelloBean hello;
@Deployment
public static WebArchive createDeployment() {
return ShrinkWrap.create(WebArchive.class)
.addClass(HelloBean.class)
.addAsWebInfResource(EmptyAsset.INSTANCE, "beans.xml");
}
@Test
public void shouldSayHello() throws Exception {
Assert.assertEquals("Hello Earthling!", hello.sayHello("Earthling"));
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net27
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net28
http://www.youtube.com/watch?v=VpZmIiIXuZ0
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net29
https://docs.jboss.org/author/display/ARQ/Drone
Drone
…brings power of Selenium into Arquillian framework.
@Drone
WebDriver driver;
@Test
@InSequence(1)
public void login() {
driver.get(contextPath + "home.jsf");
driver.findElement(USERNAME_FIELD).sendKeys(USERNAME);
driver.findElement(PASSWORD_FIELD).sendKeys(PASSWORD);
driver.findElement(LOGIN_BUTTON).click();
Assert.isTrue("User is logged in.",
driver.findElement(LOGGED_IN).isDisplayed());
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net30
Graphene
https://docs.jboss.org/author/display/ARQ/Graphene
…brings power of Selenium and AJAX into Arquillian
framework.
@RunWith(Arquillian.class)
public class TestLogin {
@Drone
WebDriver browser;
@Page
HomePage homePage;
@Test(expects = LoginFailedException.class)
public void testLoginFailed(){
homePage.login("non-existent", "user");
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net31
Warp
https://github.com/arquillian/arquillian-extension-warp/blob/master/README.md
…client-side test which asserts server-side logic.
@RunWith(Arquillian.class)
@WarpTest
@RunAsClient
public class BasicTest {
//...
}
Warp
.initiate(Activity)
.inspect(Inspection);
@BeforeServlet
@AfterServlet
@BeforePhase
@AfterPhase
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net32
Warp
.initiate(new Activity() {
public void perform() {
WebElement nameInput =
browser.findElement(By.id("helloWorldJsf:nameInput"));
nameInput.sendKeys("X");
browser.findElement(By.tagName("body")).click();
}})
.inspect(new Inspection() {
private static final long serialVersionUID = 1L;
@Inject
CdiBean myBean;
private String updatedName;
@BeforePhase(UPDATE_MODEL_VALUES)
public void initial_state_havent_changed_yet() {
assertEquals("John", myBean.getName());
}
});
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net33
Transaction
https://github.com/arquillian/arquillian-extension-transaction
…enhances your tests with transaction support.
@RunWith(Arquillian.class)
public class TransactionTest {
@Deployment
public static WebArchive deployment() {
//...
}
@Test
@Transactional(TransactionMode.ROLLBACK)
public void test() {
//….
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net34
Persistence
https://docs.jboss.org/author/display/ARQ/Persistence
…helps with database wrangling.
@RunWith(Arquillian.class)
public class PersistenceTest {
@Deployment
public static WebArchive deployment() {
//...
.addAsResource("test-persistence.xml", "persistence.xml");
}
@Test
@UsingDataSet("datasets/users.yml")
@ShouldMatchDataSet("datasets/expected-users.yml")
public void test() {
//….
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net35
https://docs.jboss.org/author/display/ARQ/Persistence
@RunWith(Arquillian.class)
@CreateSchema("scripts/ddl.sql")
public class PersistenceTest {
@Deployment
public static WebArchive deployment() {
//...
.addAsManifestResource("test-persistence.xml", "persistence.xml");
}
@Test
@UsingDataSet("datasets/users.yml")
@ShouldMatchDataSet("datasets/expected-users.yml")
@CleanupUsingScript("drop-schema.sql")
public void test() {
//….
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net36
Performance
https://docs.jboss.org/author/display/ARQ/Performance
…keeps your tests in time.
@RunWith(Arquillian.class)
@PerformanceTest(resultsThreshold = 2)
public class PersformanceTest {
@Deployment
public static WebArchive deployment() {
//...
}
@Test
@Performance(time = 575)
public void test() {
//….
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net37
Seam 2
https://docs.jboss.org/author/display/ARQ/Seam+2
…bringing Seam 2 Context to Arquillian.
@RunWith(Arquillian.class)
public class ComponentInjectionTest {
@Deployment
public static WebArchive deployment() {
//...
.addAsResource(EmptyAsset.INSTANCE, "seam.properties");
}
@In
SomeSeamComponent component;
@Test
public void test() {
assertThat(component).isNotNull();
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net38
Spring
https://github.com/arquillian/arquillian-extension-spring
…bringing Spring 2 and 3 to Arquillian.
• Injection of Spring beans into test classes
• Configuration from both XML and Java-based config
• Injecting beans configured in web application (e.g. DispatcherServlet)
for tests annotated with @SpringWebConfiguration
• Support for both Spring(@Autowired, @Qualifier, @Required) and
JSR-330(@Inject, @Named) annotations
• Bean initialization support (@PostConstruct)
• Auto packaging the spring-context and spring-web artifacts.
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net39
Guice
https://github.com/arquillian/arquillian-extension-guice
…bringing Guice DI to Arquillian.
@RunWith(Arquillian.class)
@GuiceConfiguration(AppointmentModule.class)
public class ComponentInjectionTest {
@Deployment
public static WebArchive deployment() {
//...
}
@Inject
@Named("appointmentService")
private AppointmentService appointmentService;
@Test
public void test() {
assertThat(appointmentService).isNotNull();
}
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net40
Spock
https://github.com/arquillian/arquillian-testrunner-spock
…bringing Spock Testing to Arquillian.
@Inject
AccountService service
def "transferring between accounts should result in account withdrawal and
deposit"() {
when:
service.transfer(from, to, amount)
then:
from.balance == fromBalance
to.balance == toBalance
where:
from << [new Account(100), new Account(10)]
to << [new Account(50), new Account(90)]
amount << [50, 10]
fromBalance << [50, 0]
toBalance << [100, 100]
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net41
Screen Recorder
https://github.com/arquillian/arquillian-extension-screenrecorder
…records your tests.
<dependency>
<groupId>org.jboss.arquillian.extension</groupId>
<artifactId>arquillian-screen-recorder</artifactId>
<version>1.0.0.Alpha1</version>
</dependency>
<extension qualifier="screenRecorder">
<property name="rootFolder">target</property>
<property name="videoFolder">video</property>
<property name="videoName">myTestVideo</property>
<property name="video">suite</property>
<property name="screenshot">test</property>
</extension>
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net42
Jacoco
https://github.com/arquillian/arquillian-extension-jacoco
…gives you test-coverage.
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>0.6.3.201306030806</version>
</plugin>
<dependency>
<groupId>org.jboss.arquillian.extension</groupId>
<artifactId>arquillian-jacoco</artifactId>
<version>1.0.0.Alpha5</version>
</dependency>
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net43
Google Web Toolkit
https://github.com/arquillian/arquillian-extension-gwt
… brings Arquillian to GWT.
@Test
@RunAsGwtClient(moduleName = "org.myapp.MyGwtModule")
public void testGreetingService() {
GreetingServiceAsync greetingService = GWT.create(GreetingService.class);
greetingService.greetServer("Hello!", new AsyncCallback<String>() {
@Override
public void onFailure(Throwable caught) {
Assert.fail("Request failure: " + caught.getMessage());
}
@Override
public void onSuccess(String result) {
assertEquals("Received invalid response from Server", "Welcome!", result);
finishTest();
}
});
delayTestFinish(5000);
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net44
Portal
https://github.com/arquillian/arquillian-extension-portal
…help you write tests for portlets.
@RunWith(Arquillian.class)
@PortalTest
public class PortletTest {
@Deployment
public static WebArchive deployment() {
//...
}
@ArquillianResource
@PortalURL
URL portalURL;
@Test
@RunAsClient
public void renderFacesPortlet() throws Exception {
browser.get(portalURL.toString());
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net45
https://github.com/arquillian/arquillian-extension-byteman
Byteman …gives you runtime bytecode manipulation.
@RunWith(Arquillian.class)
@BMRules(
@BMRule(
name = "Throw exception on success", targetClass =
"StatelessManagerBean", targetMethod = "forcedClassLevelFailure",
action = "throw new java.lang.RuntimeException()")
)
public class BytemanFaultInjectionTestCase {
//…
@EJB(mappedName = "java:module/StatelessManagerBean")
private StatelessManager bean;
@Test(expected = EJBException.class) {
Assert.assertNotNull("Verify bean was injected", bean);
bean.forcedMethodLevelFailure();
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net46
JRebel
https://github.com/arquillian/arquillian-extension-jrebel
… hot-deploy your integration tests.
<dependency>
<groupId>org.jboss.arquillian.extension</groupId>
<artifactId>arquillian-jrebel-impl</artifactId>
<version>1.0.0.Alpha1</version>
</dependency>
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net47
OSGi
https://github.com/arquillian/arquillian-container-osgi
… brings Arquillian to OSGi Frameworks.
@RunWith(Arquillian.class)
public class SimpleBundleTestCase {
@ArquillianResource
BundleContext context;
@Deployment
public static JavaArchive createdeployment() {
final JavaArchive archive = ShrinkWrap.create(JavaArchive.class,
"test.jar");
archive.setManifest(new Asset() {
public InputStream openStream() {
OSGiManifestBuilder builder = OSGiManifestBuilder.newInstance();
builder.addBundleSymbolicName(archive.getName());
builder.addBundleManifestVersion(2);
builder.addImportPackages(Bundle.class);
return builder.openStream(); } });
return archive;
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net48
@Test
public void testBundleContextInjection() {
assertNotNull("BundleContext injected", context);
assertEquals("System Bundle ID", 0, context.getBundle().getBundleId());
}
@Test
public void testBundleInjection(@ArquillianResource Bundle bundle) {
// Assert that the bundle is injected
assertNotNull("Bundle injected", bundle);
// Assert that the bundle is in state RESOLVED
// Note when the test bundle contains the test case it
// must be resolved already when this test method is called
assertEquals("Bundle RESOLVED", Bundle.RESOLVED, bundle.getState());
// Start the bundle
bundle.start();
assertEquals("Bundle ACTIVE", Bundle.ACTIVE, bundle.getState());
https://github.com/arquillian/arquillian-container-osgi
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net49
https://github.com/arquillian/arquillian-droidium
…brings Native and WebDriver based testing to
Android devices.
<container qualifier="android">
<configuration>
<property name="adapterImplClass">
org.jboss.arquillian.container.android.managed.AndroidManagedDeployableContainer
</property>
</configuration>
</container>
@ArquillianResource
AndroidDevice android;
@Test
@OperateOnDeployment("android1")
public void test01() {
assertTrue(android != null);
}
Droidium
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net50
iOS Platform
https://github.com/arquillian/arquillian-extension-ios
…brings Native and WebDriver based testing to
iOS devices.
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net51
QUnit automates the QUnit JavaScript testing on Web
Applications
@RunWith(QUnitRunner.class)
@QUnitResources("src/test/resources/assets")
public class QUnitRunnerTestCase {
@QUnitTest("tests/ticketmonster/qunit-tests-dom.html")
@InSequence(1)
public void qunitDomTest() {
// empty body - only the annotations are used
}
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net52
Cukespace … deploy and run Cucumber features using Arquillian.
@RunWith(ArquillianCucumber.class)
public class CukesInBellyTest {
@Deployment
public static Archive<?> createDeployment() {
return ShrinkWrap.create(WebArchive.class)
//…
.addAsResource("my/features/cukes.feature");
}
@EJB private CukeService service;
@Inject private CukeLocator cukeLocator;
@When("^I persist my cuke$")
public void persistCuke() {
this.service.persist(this.cukeLocator.findCuke());
}
}
https://github.com/cukespace/cukespace
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net53
© msg Applied Technology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net54
Questions?

Alien driven-development

  • 1.
  • 2.
  • 4.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net4 Testing is too hard. Testing isn’t fun. Testing is so sloow. Testing sucks!
  • 5.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net5 Unit Tests Integration Tests System Tests Complexity Functional Test Code
  • 6.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net6 You can’t fix what you can’t run.
  • 7.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net7 You can’t fix what you can’t debug.
  • 8.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net8 You can’t fix what you can’t test.
  • 9.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net9 You can’t develop what you can’t test.
  • 10.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net10 Not testing needs to be more painful And time consuming than using testing.
  • 11.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net11 What is touched by testing? Frameworks Build IDE Server Client Code
  • 12.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net12 Frameworks Build IDE Server Client EE Spring DI Maven Ant Gradle Eclipse NetBeans IntelliJ GlassFish Tomcat AS7 IE Chrome FF … … … … … Code Source Test Other …
  • 13.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net13 http://www.youtube.com/watch?v=VpZmIiIXuZ0
  • 14.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net14 An Innovative Testing Platform for the JVM
  • 15.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net15
  • 16.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net16 Guiding Principles  Tests should be portable to any supported container  Tests should be executable from IDE and build tool  Should extend or integrate existing test frameworks https://docs.jboss.org/author/display/ARQ/Reference+Guide
  • 17.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net17 SourceTest IDE Build Frameworks Tests Classes Server Deps Package ~ Client
  • 18.
    arquillian © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net18 SourceTest IDE Build Tests Classes Server Deps Package ClientPackage Client
  • 19.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net19 Lifecycle  Select Container  Start Container  Package Archive  Run Test in Container  Show Results  Undeploy / Disconnect
  • 20.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net20 Basic Setup <dependencyManagement> <dependencies> <dependency> <groupId>org.jboss.arquillian</groupId> <artifactId>arquillian-bom</artifactId> <version>1.0.4.Final</version> <scope>import</scope> <type>pom</type> </dependency> </dependencies> </dependencyManagement>
  • 21.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net21 <dependencies> <dependency> <groupId>javax</groupId> <artifactId>javaee-web-api</artifactId> <version>7.0</version> <scope>provided</scope> </dependency> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.8.1</version> <scope>test</scope> </dependency> <dependency> <groupId>org.jboss.arquillian.junit</groupId> <artifactId>arquillian-junit-container</artifactId> <scope>test</scope> </dependency> <!-- … --> </dependencies>
  • 22.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net22 Java EE Container Support Embedded Managed Remote https://docs.jboss.org/author/display/ARQ/Container+adapters
  • 23.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net23 <profiles> <profile> <id>arquillian-glassfish-managed</id> <dependencies> <dependency> <groupId>org.jboss.arquillian.container</groupId> <artifactId>arquillian-glassfish-managed-3.1</artifactId> <version>1.0.0.CR4</version> <scope>test</scope> </dependency> </dependencies> </profile> </profiles> https://docs.jboss.org/author/display/ARQ/Container+adapters
  • 24.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net24 <?xml version="1.0" encoding="UTF-8"?> <arquillian xmlns="http://jboss.org/schema/arquillian" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://jboss.org/schema/arquillian http://jboss.org/schema/arquillian/arquillian_1_0.xsd"> <container qualifier="glassfish" default="true"> <configuration> <property name="glassFishHome">D:glassfish4-b85</property> <property name="adminHost">localhost</property> <property name="adminPort">4848</property> </configuration> </container> </arquillian>
  • 25.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net25 @Stateless public class HelloBean { public String sayHello(String name) { return "Hello " + name + "!"; } }
  • 26.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net26 @RunWith(Arquillian.class) public class HelloBeanIntegrationTest { @EJB HelloBean hello; @Deployment public static WebArchive createDeployment() { return ShrinkWrap.create(WebArchive.class) .addClass(HelloBean.class) .addAsWebInfResource(EmptyAsset.INSTANCE, "beans.xml"); } @Test public void shouldSayHello() throws Exception { Assert.assertEquals("Hello Earthling!", hello.sayHello("Earthling")); } }
  • 27.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net27
  • 28.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net28 http://www.youtube.com/watch?v=VpZmIiIXuZ0
  • 29.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net29 https://docs.jboss.org/author/display/ARQ/Drone Drone …brings power of Selenium into Arquillian framework. @Drone WebDriver driver; @Test @InSequence(1) public void login() { driver.get(contextPath + "home.jsf"); driver.findElement(USERNAME_FIELD).sendKeys(USERNAME); driver.findElement(PASSWORD_FIELD).sendKeys(PASSWORD); driver.findElement(LOGIN_BUTTON).click(); Assert.isTrue("User is logged in.", driver.findElement(LOGGED_IN).isDisplayed()); }
  • 30.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net30 Graphene https://docs.jboss.org/author/display/ARQ/Graphene …brings power of Selenium and AJAX into Arquillian framework. @RunWith(Arquillian.class) public class TestLogin { @Drone WebDriver browser; @Page HomePage homePage; @Test(expects = LoginFailedException.class) public void testLoginFailed(){ homePage.login("non-existent", "user"); }
  • 31.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net31 Warp https://github.com/arquillian/arquillian-extension-warp/blob/master/README.md …client-side test which asserts server-side logic. @RunWith(Arquillian.class) @WarpTest @RunAsClient public class BasicTest { //... } Warp .initiate(Activity) .inspect(Inspection); @BeforeServlet @AfterServlet @BeforePhase @AfterPhase
  • 32.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net32 Warp .initiate(new Activity() { public void perform() { WebElement nameInput = browser.findElement(By.id("helloWorldJsf:nameInput")); nameInput.sendKeys("X"); browser.findElement(By.tagName("body")).click(); }}) .inspect(new Inspection() { private static final long serialVersionUID = 1L; @Inject CdiBean myBean; private String updatedName; @BeforePhase(UPDATE_MODEL_VALUES) public void initial_state_havent_changed_yet() { assertEquals("John", myBean.getName()); } });
  • 33.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net33 Transaction https://github.com/arquillian/arquillian-extension-transaction …enhances your tests with transaction support. @RunWith(Arquillian.class) public class TransactionTest { @Deployment public static WebArchive deployment() { //... } @Test @Transactional(TransactionMode.ROLLBACK) public void test() { //…. } }
  • 34.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net34 Persistence https://docs.jboss.org/author/display/ARQ/Persistence …helps with database wrangling. @RunWith(Arquillian.class) public class PersistenceTest { @Deployment public static WebArchive deployment() { //... .addAsResource("test-persistence.xml", "persistence.xml"); } @Test @UsingDataSet("datasets/users.yml") @ShouldMatchDataSet("datasets/expected-users.yml") public void test() { //…. } }
  • 35.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net35 https://docs.jboss.org/author/display/ARQ/Persistence @RunWith(Arquillian.class) @CreateSchema("scripts/ddl.sql") public class PersistenceTest { @Deployment public static WebArchive deployment() { //... .addAsManifestResource("test-persistence.xml", "persistence.xml"); } @Test @UsingDataSet("datasets/users.yml") @ShouldMatchDataSet("datasets/expected-users.yml") @CleanupUsingScript("drop-schema.sql") public void test() { //…. } }
  • 36.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net36 Performance https://docs.jboss.org/author/display/ARQ/Performance …keeps your tests in time. @RunWith(Arquillian.class) @PerformanceTest(resultsThreshold = 2) public class PersformanceTest { @Deployment public static WebArchive deployment() { //... } @Test @Performance(time = 575) public void test() { //…. } }
  • 37.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net37 Seam 2 https://docs.jboss.org/author/display/ARQ/Seam+2 …bringing Seam 2 Context to Arquillian. @RunWith(Arquillian.class) public class ComponentInjectionTest { @Deployment public static WebArchive deployment() { //... .addAsResource(EmptyAsset.INSTANCE, "seam.properties"); } @In SomeSeamComponent component; @Test public void test() { assertThat(component).isNotNull(); } }
  • 38.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net38 Spring https://github.com/arquillian/arquillian-extension-spring …bringing Spring 2 and 3 to Arquillian. • Injection of Spring beans into test classes • Configuration from both XML and Java-based config • Injecting beans configured in web application (e.g. DispatcherServlet) for tests annotated with @SpringWebConfiguration • Support for both Spring(@Autowired, @Qualifier, @Required) and JSR-330(@Inject, @Named) annotations • Bean initialization support (@PostConstruct) • Auto packaging the spring-context and spring-web artifacts.
  • 39.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net39 Guice https://github.com/arquillian/arquillian-extension-guice …bringing Guice DI to Arquillian. @RunWith(Arquillian.class) @GuiceConfiguration(AppointmentModule.class) public class ComponentInjectionTest { @Deployment public static WebArchive deployment() { //... } @Inject @Named("appointmentService") private AppointmentService appointmentService; @Test public void test() { assertThat(appointmentService).isNotNull(); } }
  • 40.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net40 Spock https://github.com/arquillian/arquillian-testrunner-spock …bringing Spock Testing to Arquillian. @Inject AccountService service def "transferring between accounts should result in account withdrawal and deposit"() { when: service.transfer(from, to, amount) then: from.balance == fromBalance to.balance == toBalance where: from << [new Account(100), new Account(10)] to << [new Account(50), new Account(90)] amount << [50, 10] fromBalance << [50, 0] toBalance << [100, 100] }
  • 41.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net41 Screen Recorder https://github.com/arquillian/arquillian-extension-screenrecorder …records your tests. <dependency> <groupId>org.jboss.arquillian.extension</groupId> <artifactId>arquillian-screen-recorder</artifactId> <version>1.0.0.Alpha1</version> </dependency> <extension qualifier="screenRecorder"> <property name="rootFolder">target</property> <property name="videoFolder">video</property> <property name="videoName">myTestVideo</property> <property name="video">suite</property> <property name="screenshot">test</property> </extension>
  • 42.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net42 Jacoco https://github.com/arquillian/arquillian-extension-jacoco …gives you test-coverage. <plugin> <groupId>org.jacoco</groupId> <artifactId>jacoco-maven-plugin</artifactId> <version>0.6.3.201306030806</version> </plugin> <dependency> <groupId>org.jboss.arquillian.extension</groupId> <artifactId>arquillian-jacoco</artifactId> <version>1.0.0.Alpha5</version> </dependency>
  • 43.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net43 Google Web Toolkit https://github.com/arquillian/arquillian-extension-gwt … brings Arquillian to GWT. @Test @RunAsGwtClient(moduleName = "org.myapp.MyGwtModule") public void testGreetingService() { GreetingServiceAsync greetingService = GWT.create(GreetingService.class); greetingService.greetServer("Hello!", new AsyncCallback<String>() { @Override public void onFailure(Throwable caught) { Assert.fail("Request failure: " + caught.getMessage()); } @Override public void onSuccess(String result) { assertEquals("Received invalid response from Server", "Welcome!", result); finishTest(); } }); delayTestFinish(5000); }
  • 44.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net44 Portal https://github.com/arquillian/arquillian-extension-portal …help you write tests for portlets. @RunWith(Arquillian.class) @PortalTest public class PortletTest { @Deployment public static WebArchive deployment() { //... } @ArquillianResource @PortalURL URL portalURL; @Test @RunAsClient public void renderFacesPortlet() throws Exception { browser.get(portalURL.toString()); }
  • 45.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net45 https://github.com/arquillian/arquillian-extension-byteman Byteman …gives you runtime bytecode manipulation. @RunWith(Arquillian.class) @BMRules( @BMRule( name = "Throw exception on success", targetClass = "StatelessManagerBean", targetMethod = "forcedClassLevelFailure", action = "throw new java.lang.RuntimeException()") ) public class BytemanFaultInjectionTestCase { //… @EJB(mappedName = "java:module/StatelessManagerBean") private StatelessManager bean; @Test(expected = EJBException.class) { Assert.assertNotNull("Verify bean was injected", bean); bean.forcedMethodLevelFailure(); }
  • 46.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net46 JRebel https://github.com/arquillian/arquillian-extension-jrebel … hot-deploy your integration tests. <dependency> <groupId>org.jboss.arquillian.extension</groupId> <artifactId>arquillian-jrebel-impl</artifactId> <version>1.0.0.Alpha1</version> </dependency>
  • 47.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net47 OSGi https://github.com/arquillian/arquillian-container-osgi … brings Arquillian to OSGi Frameworks. @RunWith(Arquillian.class) public class SimpleBundleTestCase { @ArquillianResource BundleContext context; @Deployment public static JavaArchive createdeployment() { final JavaArchive archive = ShrinkWrap.create(JavaArchive.class, "test.jar"); archive.setManifest(new Asset() { public InputStream openStream() { OSGiManifestBuilder builder = OSGiManifestBuilder.newInstance(); builder.addBundleSymbolicName(archive.getName()); builder.addBundleManifestVersion(2); builder.addImportPackages(Bundle.class); return builder.openStream(); } }); return archive; }
  • 48.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net48 @Test public void testBundleContextInjection() { assertNotNull("BundleContext injected", context); assertEquals("System Bundle ID", 0, context.getBundle().getBundleId()); } @Test public void testBundleInjection(@ArquillianResource Bundle bundle) { // Assert that the bundle is injected assertNotNull("Bundle injected", bundle); // Assert that the bundle is in state RESOLVED // Note when the test bundle contains the test case it // must be resolved already when this test method is called assertEquals("Bundle RESOLVED", Bundle.RESOLVED, bundle.getState()); // Start the bundle bundle.start(); assertEquals("Bundle ACTIVE", Bundle.ACTIVE, bundle.getState()); https://github.com/arquillian/arquillian-container-osgi
  • 49.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net49 https://github.com/arquillian/arquillian-droidium …brings Native and WebDriver based testing to Android devices. <container qualifier="android"> <configuration> <property name="adapterImplClass"> org.jboss.arquillian.container.android.managed.AndroidManagedDeployableContainer </property> </configuration> </container> @ArquillianResource AndroidDevice android; @Test @OperateOnDeployment("android1") public void test01() { assertTrue(android != null); } Droidium
  • 50.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net50 iOS Platform https://github.com/arquillian/arquillian-extension-ios …brings Native and WebDriver based testing to iOS devices.
  • 51.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net51 QUnit automates the QUnit JavaScript testing on Web Applications @RunWith(QUnitRunner.class) @QUnitResources("src/test/resources/assets") public class QUnitRunnerTestCase { @QUnitTest("tests/ticketmonster/qunit-tests-dom.html") @InSequence(1) public void qunitDomTest() { // empty body - only the annotations are used }
  • 52.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net52 Cukespace … deploy and run Cucumber features using Arquillian. @RunWith(ArquillianCucumber.class) public class CukesInBellyTest { @Deployment public static Archive<?> createDeployment() { return ShrinkWrap.create(WebArchive.class) //… .addAsResource("my/features/cukes.feature"); } @EJB private CukeService service; @Inject private CukeLocator cukeLocator; @When("^I persist my cuke$") public void persistCuke() { this.service.persist(this.cukeLocator.findCuke()); } } https://github.com/cukespace/cukespace
  • 53.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net53
  • 54.
    © msg AppliedTechnology Research, 01.07.2013Markus Eisele - @myfear - http://blog.eisele.net54 Questions?