Arquillian's forte is not only its ease of use, but also its extensibility. Good integration testing is not just about testing in any environment, but rather testing in the environment of your application targets. It's easy to give ourselves false assurance by validating components in a specialized testing container, or by using mocks, only to realize that small variations and assumptions cause the components fail when the application is deployed to production. To make tests count, you want to execute them in the target environment, or container.
So what is the container Arquillian uses? Is it some proprietary testing container that emulates the behavior of the technology (Java EE)? Nope! It's pluggable. It can be your target runtime, such as JBoss AS, GlassFish or Tomcat. Or it can even been an embedded container such as OpenEJB, GlassFish Embedded or Weld SE. You can even use one container for development and another for continuous integration.
This portability is made possible by a RPC-style (or local, if applicable) communication between the test runner and the container, a real container. You can run the same test case against various containers and you don't get locked into a proprietary test environment.
Arquillian recognizes three container interaction styles:
- A remote container resides in a separate JVM from the test runner. Arquillian binds to the container to deploy the test archive and invokes tests via a remote protocol (e.g., Servlet, JMX).
- A managed container is similar to a remote container, except its lifecycle (startup/shutdown) is also managed by Arquillian.
- An embedded container resides in the same JVM and is mostly likely managed by Arquillian. Tests are executed via a local protocol for containers without a web component and via a remote protocol for containers with a web component. No need to fiddle with those Maven plugins!
A container is further classified by its capabilities:
- Java EE application server (e.g., JBoss AS, GlassFish, WebLogic)
- Servlet container (e.g., Tomcat, Jetty)
- standalone bean container (e.g., OpenEJB, Weld SE)
- OSGi container
Arquillian can control a variety of containers out of the box. If the container you are using isn't supported, Arquillian provides an SPI that allows you to introduce any additional container to the default collection.