Vert.x + JVx

Post to Twitter

Do you know vert.x?

It's like node.js but written in Java and without JavaScript limitations. It's very powerful and easy to use. I don't describe features of vert.x or tell you how it works. If you want to know more about it, you'll find everything you need on the official site.

How and why do we use vert.x?

We simply tried it out to find out how it works and if an integration with JVx makes sense. We started a simple Research project with some goals:

  • Create a simple http server that will run without an application server, e.g. on a Raspberry Pi
  • Create a simple net/socket server, also for Raspberry Pi
  • Deploy an existing JVx application (e.g. FirstApp) and connect to the new server
  • Integrate the EventBus in an existing JVx application
  • Create a simple JavaScript app (show data in a grid) with jQuery, jQueryUI and vert.x EventBus
  • Use EventBus in Cluster mode (Java IPC)

The documentation of vert.x is great and there are a lot of examples, not what we needed but good for a quick start.

It was easy to create a http and socket server. The only problem was that everything was asynchronous and JVx expected synchronous calls. The HttpConnection of JVx worked without modifications because the JDK solved everything. We didn't use the vert.x http client.

It was a little bit tricky to implement an IConnection for socket communication because the server has to know when a command ends. It only reads a stream and does not know the protocol! We didn't introduce a new protocol, instead we wrote a delimiter after each command. This worked like a charm.

After we had http and socket support, the usage of an existing JVx application was easy. We copied existing files and it worked out-of-the-box. That was as expected ;-)

What about the event bus?

With JVx we have a super fast and simple client/server communication and it's possible to send messages from the client to the server, but the client polls. It's not live!

The event bus offers more power and flexibility. We thought it would be a great benefit for JVx applications or applications written in technologies that are supported from vert.x e.g. JavaScript.

It's already possible to use JVx' REST interface from non Java applications but if you use vert.x it would be cool to use the event bus.

The EventBus support was soo easy because the API is very nice and simple. It's enough to register a handler (like a listener) for a specific address (= string). After the registration you'll receive events from the bus :)

We had some problems with clustering vert.x because we didn't read the (whole) documentation and the information was in a different place as expected. If you use vert.x embedded and start multiple applications with different Vertx instances, be sure to use free cluster (communication) ports (see manual):

-cluster-port If the cluster option has also been specified then this determines which port will be used for cluster communication with other vert.x instances. Default is 25500. If you are running more than one vert.x instance on the same host and want to cluster them, then you'll need to make sure each instance has its own cluster port to avoid port conflicts.

We had to create Vertx instances with a specific port, e.g. 25501, 25502 (for the second and third application):

Vertx vertx = Vertx.newVertx(25501, "10.0.0.11");

Without port and host, the instance is not clustered!

The last goal was a simple JavaScript application. Here is a screenshot:

JVx with Vert.x and JQuery

JVx with Vert.x and JQuery

The application connects with username and password and retrieves data from a database via business logic (standard JVx). We used an existing JVx application and wrote one html page for our JavaScript application. Here is the source code:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>JVx + vert.x + jQuery</title>
 
<link rel="stylesheet" type="text/css" media="screen" href="css/jquery-ui.custom.css" />
<link rel="stylesheet" type="text/css" media="screen" href="css/ui.jqgrid.css" />

<script src="js/jquery-1.7.2.min.js" type="text/javascript"></script>
<script src="js/i18n/grid.locale-en.js" type="text/javascript"></script>
<script src="js/jquery.jqGrid.min.js" type="text/javascript"></script>
<script src="http://cdn.sockjs.org/sockjs-0.2.1.min.js"></script>
<script src="js/vertxbus.js"></script>
<script type="text/javascript">
  $.jgrid.no_legacy_api = true;
  $.jgrid.useJSON = true;
</script>
<script type="text/javascript">
jQuery(document).ready(function(){
  $.jgrid.defaults = $.extend($.jgrid.defaults,{loadui:"enable"});

  jQuery("#grid").jqGrid(
  {
    datatype: "local",
    height: 400,

    colNames:['ID','PLZ-ID', 'ZIP', 'STRA-ID', 'Street', 'House #', 'Floor', 'Door #'],
    colModel:[
                {name:'ID', width:60, sorttype:"int"},
                {name:'POST_ID', hidden:true},
                {name:'POST_PLZ', width:50, align:"right", sorttype:"text"},
                {name:'STRA_ID', hidden:true},
                {name:'STRA_NAME', width:200, sorttype:"text"},        
                {name:'HAUSNUMMER', width:50, align:"right", sorttype:"int"},          
                {name:'STIEGE', width:70, align:"right", sorttype:"int"},              
                {name:'TUERNUMMER', width:60, align:"right", sorttype:"int"}
                ],
   
    multiselect: false,
    rowNum: 200,
    forceFit: true,
    loadonce: true,
    caption: "Address data"
});

eb = new vertx.EventBus("http://10.0.0.11:8080/eventbus");

eb.onopen = function()
{
    eb.send('jvx.createSession',
            {application: 'demo', username: 'rene', password: 'rene'},
            function (reply)
    {  
      eb.send('jvx.fetch',
              {sessionId: reply.sessionId, object: 'adrData'},
              function (reply2)
      {
        gdata = reply2.data;

        for(var i = 0; i <= gdata.length; i++)
       {
         jQuery("#grid").jqGrid('addRowData', i + 1, gdata[i]);
       }
     });
   });    
};

});
</script>
</head>
<body>
  <div id="GridPane">
    <table id="grid"></table>
  </div>
</body>
</html>

The authentication is hardcoded, of course. It's not a problem to show a login page, but not necessary for our project.

Summary

We have a great integration of JVx for vert.x and it's now possible to use JVx on remote hosts without application server. Simply use Vert.x as http or socket server. It's very cool to use a Raspberry Pi with JVx without Tomcat, Jetty or JBoss - it saves system resources and is cool :)

It's now possible to use JavaScript, Python, Ruby or Groovy as client technology together with vert.x and JVx. Use the power of JVx for your preferred client technology.

The EventBus is a powerful feature to enrich your rich applications :)

Our integration project is open source and free for everyone!

Leave a Reply

Spam protection by WP Captcha-Free