Containers, Microsoervices, and NoSQL provide an awesome threesome for building your modern applications. These applications need to be agile, meet constantly evolving customer demands, be pervasive, and should work across mobile, web and IoT platforms.

This blog will explain a simple microservices stack using WildFly Swarm, Docker, and Couchbase. Complete code and instructions in this blog are documented at:

Let’s understand the key components of this stack first!


WildFly Swarm allows to package and run JavaEE applications by packaging them with just enough of the server runtime to java -jar your application. With built-in service discovery, single sign-on using Keycloak, monitoring using Hawkular, and many more features, WildFly Swarm provides all the necessary components to develop your microservice.


Docker for Mac provides native support for running Docker containers on Mac OSX. It relies upon Hypervisor.framework in OSX. Docker engine runs in an Alpine Linux distribution on top of an xhyve Virtual Machine, and even the VM is managed by Docker. There is no need for Docker Machine or VirtualBox, and it integrates with OSX security sandbox model. DockerCon 2016 removed the private beta restriction from Docker for Mac, and so its available for everybody now.

Couchbase Logo

NoSQL provides the agility and flexibility of schema-less databases. This allows the application to evolve independently and rapidly without going through cumbersome database migrations. Couchbase offers true horizontal scaling with homogenous architecture, as opposed to non-scalable master/slave architecture. It also offers auto-sharding, SQL-like query language for JSON (N1QL), mobile database and synchronization with the backend server, and much more.

The complete sample application in this blog is at:

WildFly Swarm Application

Let’s look at the Java EE REST endpoint:

package com.couchbase.wildfly.swarm;

. . .

public class AirlineResource {

    @Inject Database database;
    public String getAll() {
        N1qlQuery query = N1qlQuery.simple("SELECT * FROM `travel-sample` LIMIT 10");
        N1qlQueryResult result = database.getBucket().query(query);
        return result.allRows().toString();
. . .

It uses standard JAX-RS annotation to convert a POJO into a REST endpoint. Couchbase Java API provide a fluent API and used N1QL statement to query the documents and return the results. The N1QL statement returns the first 10 elements from the query result. Learn more about N1QL syntax in this interactive tutorial.

Database abstraction is defined as:

package com.couchbase.wildfly.swarm;

. . .

public class Database {
    CouchbaseCluster cluster;
    Bucket bucket;
    public CouchbaseCluster getCluster() {
        if (null == cluster) {
            String couchbaseURI = System.getenv("COUCHBASE_URI");
            if (null == couchbaseURI) {
                System.err.println("WARING: No COUCHBASE_URI specified, defaulting to localhost");
                couchbaseURI = "localhost:8093";
            System.out.println("Couchbase endpoint: " + System.getenv("COUCHBASE_URI"));
            cluster = CouchbaseCluster.create(couchbaseURI);
        return cluster;
    public Bucket getBucket() {
        if (null == bucket) {
            bucket = getCluster().openBucket("travel-sample");
        return bucket;

This is a singleton EJB that is eagerly initialized. It uses Couchbase Java SDK to connect to Couchbase. Database endpoint can be specified using the COUCHBASE_URI environment variable.

Next up is pom.xml for configuring the WildFly Swarm and Couchbase Java Client:


It uses WildFly Swarm “bill of materials” to pull in all the dependencies. Only the specific dependencies needed for the build are specified in <dependencies>. These are then packaged in the “fat jar”.

WildFly Swarm Maven plugin is used to package and run the application:


COUCHBASE_URI is used to read the host of where Couchbase database server is running.

Run Couchbase Server

Run the Couchbase server using Docker for Mac:

docker run -d --name db -p 8091-8093:8091-8093 -p 11210:11210 arungupta/couchbase

The arungupta/couchbase is built upon the standard Couchbase image and uses Couchbase REST API to configure the server.

Wait for a couple of minutes for the sample bucket to be populated with the JSON documents.

Invoke the Couchbase CLI tool cbq create a primary index on the sample bucket:

docker run -it --link db:db arungupta/couchbase cbq -u Administrator -p password -engine http://db:8093 -s "create primary index `travel-sample-primary-index` on `travel-sample`;"

This will show the output as:

 Connected to : http://db:8093/. Type Ctrl-D or QUIT to exit.

 Path to history file for the shell : /root/.cbq_history 
    "requestID": "d0b2e4dd-b702-49e2-971c-a4c640ddb498",
    "signature": null,
    "results": [
    "status": "success",
    "metrics": {
        "elapsedTime": "3.154540272s",
        "executionTime": "3.154493281s",
        "resultCount": 0,
        "resultSize": 0

This output shows that result of creating index was successful.

One of the advantages of running Docker for Mac is that all the containers are accessible at localhost. This means Couchbase Web Console can be accessed at localhost:8091.


This screen ensures that Couchbase is configured  correctly.

Run WildFly Swarm Microservice


Package and run the self-contained microservice as:

mvn wildfly-swarm:run

If Couchbase is running on a different host, then the command will change to:

mvn -DCOUCHBASE_URI=<IP> wildfly-swarm:run

It shows the output as:

[INFO] Scanning for projects...
[INFO] ------------------------------------------------------------------------
[INFO] Building nosql-microservices 1.0-SNAPSHOT
[INFO] ------------------------------------------------------------------------

. . . 

2016-06-27 22:21:47,170 WARN  [] (MSC service thread 1-6) WFLYSRV0018: Deployment "deployment.nosql-microservices.war" is using a private module ("org.jboss.jts:main") which may be changed or removed in future versions without notice.
2016-06-27 22:21:47,203 INFO  [org.jboss.weld.deployer] (MSC service thread 1-1) WFLYWELD0003: Processing weld deployment nosql-microservices.war
2016-06-27 22:21:47,542 INFO  [org.hibernate.validator.internal.util.Version] (MSC service thread 1-1) HV000001: Hibernate Validator 5.2.3.Final
2016-06-27 22:21:47,600 INFO  [] (MSC service thread 1-1) WFLYEJB0473: JNDI bindings for session bean named 'Database' in deployment unit 'deployment "nosql-microservices.war"' are as follows:


2016-06-27 22:21:47,731 INFO  [org.jboss.weld.deployer] (MSC service thread 1-3) WFLYWELD0006: Starting Services for CDI deployment: nosql-microservices.war
2016-06-27 22:21:47,758 INFO  [org.jboss.weld.Version] (MSC service thread 1-3) WELD-000900: 2.3.2 (Final)
2016-06-27 22:21:47,780 INFO  [org.wildfly.extension.undertow] (MSC service thread 1-1) WFLYUT0018: Host default-host starting
2016-06-27 22:21:47,788 INFO  [org.jboss.weld.deployer] (MSC service thread 1-8) WFLYWELD0009: Starting weld service for deployment nosql-microservices.war
2016-06-27 22:21:48,180 INFO  [stdout] (ServerService Thread Pool -- 10) Couchbase endpoint: 
2016-06-27 22:21:48,275 INFO  [com.couchbase.client.core.CouchbaseCore] (ServerService Thread Pool -- 10) CouchbaseEnvironment: {sslEnabled=false, sslKeystoreFile='null', sslKeystorePassword='null', queryEnabled=false, queryPort=8093, bootstrapHttpEnabled=true, bootstrapCarrierEnabled=true, bootstrapHttpDirectPort=8091, bootstrapHttpSslPort=18091, bootstrapCarrierDirectPort=11210, bootstrapCarrierSslPort=11207, ioPoolSize=8, computationPoolSize=8, responseBufferSize=16384, requestBufferSize=16384, kvServiceEndpoints=1, viewServiceEndpoints=1, queryServiceEndpoints=1, searchServiceEndpoints=1, ioPool=NioEventLoopGroup, coreScheduler=CoreScheduler, eventBus=DefaultEventBus, packageNameAndVersion=couchbase-jvm-core/1.2.5 (git: 1.2.5), dcpEnabled=false, retryStrategy=BestEffort, maxRequestLifetime=75000, retryDelay=ExponentialDelay{growBy 1.0 MICROSECONDS, powers of 2; lower=100, upper=100000}, reconnectDelay=ExponentialDelay{growBy 1.0 MILLISECONDS, powers of 2; lower=32, upper=4096}, observeIntervalDelay=ExponentialDelay{growBy 1.0 MICROSECONDS, powers of 2; lower=10, upper=100000}, keepAliveInterval=30000, autoreleaseAfter=2000, bufferPoolingEnabled=true, tcpNodelayEnabled=true, mutationTokensEnabled=false, socketConnectTimeout=1000, dcpConnectionBufferSize=20971520, dcpConnectionBufferAckThreshold=0.2, queryTimeout=75000, viewTimeout=75000, kvTimeout=2500, connectTimeout=5000, disconnectTimeout=25000, dnsSrvEnabled=false}
2016-06-27 22:21:48,829 INFO  [com.couchbase.client.core.node.Node] (cb-io-1-1) Connected to Node localhost
2016-06-27 22:21:49,035 INFO  [com.couchbase.client.core.config.ConfigurationProvider] (cb-computations-1) Opened bucket travel-sample
2016-06-27 22:21:49,415 INFO  [org.jboss.resteasy.resteasy_jaxrs.i18n] (ServerService Thread Pool -- 10) RESTEASY002225: Deploying class com.couchbase.wildfly.swarm.MyApplication
2016-06-27 22:21:49,438 INFO  [org.wildfly.extension.undertow] (ServerService Thread Pool -- 10) WFLYUT0021: Registered web context: /
2016-06-27 22:21:49,457 INFO  [] (main) WFLYSRV0010: Deployed "nosql-microservices.war" (runtime-name : "nosql-microservices.war")

Now the application can be accessed as:

curl http://localhost:8080/webresources/airline

And a formatted output looks like:

    "travel-sample": {
      "country": "United States",
      "iata": "Q5",
      "callsign": "MILE-AIR",
      "name": "40-Mile Air",
      "icao": "MLA",
      "id": 10,
      "type": "airline"

  . . .

    "travel-sample": {
      "country": "France",
      "iata": "A5",
      "callsign": "AIRLINAIR",
      "name": "Airlinair",
      "icao": "RLA",
      "id": 1203,
      "type": "airline"

So you built a simple microservice using WildFly Swarm accessing a Couchbase database running as a Docker container.

Now, ideally this WildFly Swarm service should be packaged as a Docker image and then that Docker image would serve as the service. A Maven profile with the name docker is already added to pom.xml but issue #3 is making that scenario fail.

Microservices References


Microservices using WildFly Swarm, Docker and Couchbase

About The Author
- Arun Gupta is the vice president of developer advocacy at Couchbase. He has been building developer communities for 10+ years at Sun, Oracle, and Red Hat. He has deep expertise in leading cross-functional teams to develop and execute strategy, planning and execution of content, marketing campaigns, and programs. Prior to that he led engineering teams at Sun and is a founding member of the Java EE team. Gupta has authored more than 2,000 blog posts on technology. He has extensive speaking experience in more than 40 countries on myriad topics and is a JavaOne Rock Star. Gupta also founded the Devoxx4Kids chapter in the US and continues to promote technology education among children. An author of a best-selling book, an avid runner, a globe trotter, a Java Champion, and a JUG leader, he is easily accessible at @arungupta.

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>