Java Service Wrapper is a library that provides a set of binaries and scripts for different architectures and operating systems that allow us to run a Java application as a service daemon. There are some integration methods to run a Java app. The used in this post is WrapperJarApp to run a jar package, you can see the different methods in the official documentation:
http://wrapper.tanukisoftware.com/doc/english/integrate.html
There are more alternatives to run a Java daemon, for example JSVC library http://commons.apache.org/proper/commons-daemon/jsvc.html, in my opinion more clear and you have more control to manage the different signals sent to your applications, but with Java Service Wrapper it may be easier deploy the daemon, it’s multiplatform and no needs to change the code for our software.
For this post I used a Fedora 18 Core 64 bits as server with the package rabbitmq-server and openjdk-7 installed. The example code used basically the Consumer running on the server will fetch the messages from the rabbitmq queues and the Producer running on the client, it will send a message to the server. You can download the jar examples to test it.
The source code of both programs are:
– Consumer.java (Download rabbitmqConsumer jar):
package rabbitmqconsumer; import com.rabbitmq.client.ConnectionFactory; import com.rabbitmq.client.Connection; import com.rabbitmq.client.Channel; import com.rabbitmq.client.QueueingConsumer; public class Consumer { private final static String QUEUE_NAME = "myQueue"; public static void main(String[] argv) throws java.io.IOException, java.lang.InterruptedException { ConnectionFactory factory = new ConnectionFactory(); factory.setHost("localhost"); Connection connection = factory.newConnection(); Channel channel = connection.createChannel(); channel.queueDeclare(QUEUE_NAME, false, false, false, null); System.out.println(" [*] Waiting for clients!!"); QueueingConsumer consumer = new QueueingConsumer(channel); channel.basicConsume(QUEUE_NAME, true, consumer); while (true) { QueueingConsumer.Delivery delivery = consumer.nextDelivery(); String message = new String(delivery.getBody()); System.out.println(" [x] Received '" + message + "'"); } } }
– Producer.java (Download rabbitmqProducer jar):
package rabbitmqproducer; import com.rabbitmq.client.ConnectionFactory; import com.rabbitmq.client.Connection; import com.rabbitmq.client.Channel; public class Producer { private final static String QUEUE_NAME = "myQueue"; private static String RABBITMQ_SERVER=""; public static void main(String[] argv) throws java.io.IOException { if(argv.length >0){ RABBITMQ_SERVER=argv[0]; ConnectionFactory factory = new ConnectionFactory(); factory.setHost(RABBITMQ_SERVER); Connection connection = factory.newConnection(); Channel channel = connection.createChannel(); channel.queueDeclare(QUEUE_NAME, false, false, false, null); String message = "Hi Server!"; channel.basicPublish("", QUEUE_NAME, null, message.getBytes()); System.out.println(" [x] Hello, Sent! '" + message + "'"); channel.close(); connection.close(); } else{ System.out.println("Usage: java -jar rabbitmqProducer.jar <ip address>"); } } }
– Preparing the environment:
# mkdir -p /usr/local/queuesApp/bin/ # mkdir /usr/local/queuesApp/conf # mkdir /usr/local/queuesApp/logs # cp -r rabbitmqConsumer.jar lib/ /usr/local/queuesApp/bin/
– Download and install java service wrapper for Linux:
– 32 bits systems:
# wget http://heanet.dl.sourceforge.net/project/wrapper/wrapper/Wrapper_3.5.17_20121127/wrapper-linux-x86-32-3.5.17.tar.gz
– 64 bits systems:
# wget http://heanet.dl.sourceforge.net/project/wrapper/wrapper/Wrapper_3.5.17_20121127/wrapper-linux-x86-64-3.5.17.tar.gz
– Extract the package and copy the files needed:
# tar -xzvf wrapper-linux-x86-*-3.5.17.tar.gz # cd wrapper-linux-x86-*-3.5.17/ # cp bin/wrapper /usr/local/queuesApp/bin/ # cp src/bin/sh.script.in /usr/local/queuesApp/bin/ # cp lib/* /usr/local/queuesApp/bin/ # cp conf/wrapper.conf /usr/local/queuesApp/conf/
– Rename the service script and set correct permissions:
# cd /usr/local/queuesApp/bin/ # mv sh.script.in consumer-daemon # chmod +x consumer-daemon
– Changing some directive from the config file for our application:
# cd /usr/local/queuesApp/conf/ # vi wrapper.conf #******************************************************************** # Wrapper Java Properties #******************************************************************** # Java Application # Locate the java binary on the system PATH: wrapper.java.command=java # Java Main class. This class must implement the WrapperListener interface # or guarantee that the WrapperManager class is initialized. Helper # classes are provided to do this for you. See the Integration section # of the documentation for details. wrapper.java.mainclass=org.tanukisoftware.wrapper.WrapperJarApp # Java Classpath (include wrapper.jar) Add class path elements as # needed starting from 1 wrapper.java.classpath.1=../bin/wrapper.jar # Java Library Path (location of Wrapper.DLL or libwrapper.so) wrapper.java.library.path.1=../bin # Application parameters. Add parameters as needed starting from 1 wrapper.app.parameter.1=../bin/rabbitmqConsumer.jar
- wrapper.java.command : It’s the path for the java binary, by default in Linux it’s found in the PATH.
- wrapper.java.mainclass: The main class to load our program, it may be different depending of the integration method used.
- wrapper.java.classpath.1 : the location for the wrapper jar.
- wrapper.java.library.path.1 : The path for the wrapper binary.
- wrapper.app.parameter.1 : The jar package for our program.
– Edit init script:
# vi /usr/local/queuesApp/bin/consumer-daemon APP_NAME="consumer-daemon" APP_LONG_NAME="Consumer Java Daemon for RabbitMQ"
– Run the aplication at boot time:
# ln -s /usr/local/queuesApp/bin/consumer-daemon /etc/init.d/consumer-daemon # chkconfig --levels 235 consumer-daemon on
You can start or stop the new daemon like other Unix daemon. If you would like to monitor the start of the daemon, you can init it with the console parameter:
– Source:
http://wrapper.tanukisoftware.com/doc/english/introduction.html