MongoDb on HP Cloud, using Cumulogic

27 Mar 2013    

On Cumulogic’s website it is stated that Cumulogic is an enabler for rapidly building Amazon-style cloud services securely on a private cloud and virtualized environment. Cumulogic is a platform that offers a PaaS (supporting Spring), a DBaaS (supporting MongoDb) and other offerings for application development. The Cumulogic platform sits on top of an IaaS environment such as HP Cloud Services (HPCS). Currently Cumulogic and HPCS offer a free 90 day trial.

cumulogic

Although that’s a lot of buzzwords, I was curious about MongoDB and Cumulogic seemed to offer a quick way of learning something about it.

Cumulogic

After registering, a dashboard was greeting me. On the dashboard, I could create a MongoDB instance through a simple user interface. Since I wanted to use the MongoDB instance from Java, the Access Details tab was particularly interesting. It contained the connection details, I needed later.

cumulogic

Next up was the application container .. Cumulogic links the application container/server (Tomcat, JBoss, GlassFish, ..) with the preferred framework (Java EE, Spring, ..). While this makes sense (sort of), I don’t see this link as a necessity. I choose Spring and ended up with Tomcat.

cumulogic

Both are using HPCS as Target Cloud. The configuration of both the database and the framework/application container really only took a couple of clicks. So far their statement regarding “enabling AWS-style cloud services” was correct.

The Framework instance has an Action(s) column that allows you to deploy/undeploy/redeploy/delete/… applications. Unfortunately there is no way to find logfiles when the deploy failed. I contacted Cumulogic and they stated logfiles would become available soon. Accessing logfiles really is essential for application development. I wasn’t able to SSH into my instances either. The Access Groups displayed port 22 as available, but I couldn’t find an account anywhere. They also didn’t provide me with one, when I asked about it. Another issue I encountered was missing information in their user interface, eg. there is no way to check the JDK version on the instance, let alone change it. As it turned out, my Tomcat instance was using JDK 6, while I was trying to deploy a JDK 7 application.

MongoDB and Spring

I wanted to make an application that had CRUD functionality using Spring. I used Maven for building the application. In my Maven POM, I started with these dependencies:

        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-core</artifactId>
            <version>3.2.2.RELEASE</version>
        </dependency>

        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>3.2.2.RELEASE</version>
        </dependency>

        <dependency>
            <groupId>org.mongodb</groupId>
            <artifactId>mongo-java-driver</artifactId>
            <version>2.10.1</version>
        </dependency>

        <dependency>
            <groupId>org.springframework.data</groupId>
            <artifactId>spring-data-mongodb</artifactId>
            <version>1.1.1.RELEASE</version>
        </dependency>

        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>servlet-api</artifactId>
            <version>2.5</version>
            <scope>provided</scope>
        </dependency>

The servlet-api dependency is not necessary for using Spring and MongoDB, but I want to deploy the application on the Cumulogic Tomcat container and will use a simple servlet for that.

Spring Data has a lot of support for MongoDB. I went with AbstractMongoConfiguration for configuring MongoDB in Spring:

public class SpringMongoConfig extends AbstractMongoConfiguration {

    @Override
    protected String getDatabaseName() {
        return "mdb_test";
    }

    @Override
    @Bean
    public Mongo mongo() throws Exception {
        return new Mongo("15.185.160.1", 27017);
    }

I needed something to persist and cars are always a good idea. I created this simple POJO:

    public Car(String brand, String model, Integer horsePower) {
        this.brand = brand;
        this.model = model;
        this.horsePower = horsePower;
    }

I’m pretty sure anyone can imagine what the rest of the class looks like, but I’ll add the source of the application at the end. After a database configuration and an object to persist, I added a service class to interact with the database. The interesting part of this service is the MongoOperations class. The API documentation holds all the necessary information for different operations such as insert, remove, update, … CarService uses MongoTemplate. Some might remember this from HibernateTemplate or JdbcTemplate.

public class CarService {
    ApplicationContext ctx = new AnnotationConfigApplicationContext(
            SpringMongoConfig.class);

    MongoOperations mongoOperation = (MongoOperations) ctx
            .getBean("mongoTemplate");

    public List<Car> findCars() {
        return mongoOperation.findAll(Car.class, "cars");
    }

    public void save(Car car) {
        mongoOperation.save(car, "cars");
    }
}

All that’s still needed now, is a Servlet to use the CarService class:

/**
 * This Servlet was quickly hacked for demonstrating MongoDb.<br />
 * Do not use it for real work. Ever.
 */
public class MongoServlet extends HttpServlet {

    private static final long serialVersionUID = -3353123142320733735L;

    public void doGet(HttpServletRequest req, HttpServletResponse res)
            throws ServletException, IOException {
        PrintWriter out = res.getWriter();

        CarService carService = new CarService();

        Car newCar = makeCar(req);
        if (newCar != null) {
            carService.save(newCar);
        }

        for (Car car : carService.findCars()) {
            out.println(car.getBrand() + " - " + car.getModel() + " - " + car.getHorsePower());
        }

        out.close();
    }

    private Car makeCar(HttpServletRequest req) {
        String[] brand = req.getParameterValues("brand");

        if (brand != null &amp;&amp; brand.length == 1) {
            String[] model = req.getParameterValues("model");
            String[] horsePower = req.getParameterValues("horsepower");

            return new Car(brand[0], model[0], Integer.parseInt(horsePower[0]));
        } else {
            return null;
        }
    }

Please read the Javadoc on the class. Never use a servlet like this for a “real” project. It can go wrong in so many ways .. I consider it a quick and dirty hack to use my CarService. For it to work, a simple web.xml is needed:

    <servlet>
        <servlet-name>MongDb</servlet-name>
        <servlet-class>com.hp.afterhours.mongo.web.MongoServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>MongDb</servlet-name>
        <url-pattern>/mongo/*</url-pattern>
    </servlet-mapping>

And we’re done.

Deploying the application shouldn’t pose any problems. After the deployment, the content of the database can be queried using the servlet: (where localhost is replaced with the IP of your Tomcat instance)

http://localhost:1234/mongo

  Adding a new car to the MongoDB, can be done via

http://localhost:1234/mongo?brand=Mercedes&model=SLS&horsepower=583

  I implemented a couple methods of MongoOperations more in the CarService, in the attached source.

This simple example only scratches the surface of what’s possible in MongoDB. Parleys hosts an interesting talk on “Building Web Applications with MongoDB” (it has 2 parts) that is worth checking if you want to learn more about MongoDB.

Source:

https://github.com/bart-blommaerts/cumulogic-mongo.git