ejb3

Executing EJB3 Using Glassfish 3 AppClient

On my last EJB3 tutorial, im still using the old fashioned way of EJB3. Still importing lots of jars, which is very dangerous due to the fact that sometimes i forgot which jar i need to include.

That’s why now im trying to use one of Glassfish’s feature application, appclient. It can bundle all the libraries and dependencies your EJB client needed, so it save your time from including various Glassfish’s jars to your project.

Lets start with a very simple ejb interface class,

package com.edw.facade;

public interface ConnectionFacadeRemote {
    String sayHello(String string);
    int sayAge(int age);
}

And a simple main class,

package com.edw.main;

import com.edw.facade.ConnectionFacadeRemote;
import java.util.Properties;
import javax.naming.Context;
import javax.naming.InitialContext;
import org.apache.log4j.Logger;

public class Main {

    private Logger logger = Logger.getLogger(Main.class);
    
    private void connect() {
        try{
            Properties props = new Properties();
            props.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.enterprise.naming.SerialInitContextFactory");
            props.setProperty("org.omg.CORBA.ORBInitialHost", "localhost");
            props.setProperty("org.omg.CORBA.ORBInitialPort", "3700");
            
            InitialContext ctx = new InitialContext();
            ConnectionFacadeRemote connectionFacadeRemote = (ConnectionFacadeRemote) ctx.lookup("com.edw.facade.ConnectionFacadeRemote");
            logger.debug(connectionFacadeRemote.sayHello("edwin ")); 
            logger.debug("my age is " + connectionFacadeRemote.sayAge(12) + " years");
        }catch(Exception ex){
            logger.error(ex,ex);
        }
    }

    public static void main(String[] args) {
        Main tejbc = new Main();
        tejbc.connect();
    }
}

After you create all classes needed, you have to build your application into .jar.
Next is to pull all the jar needed for this EJB client application to run smoothly. First go to your Server glassfish’s bin folder located in your Server glassfish installation folder, in my PC it would be (C:\Program Files\glassfish-3.0.1\glassfish\bin). And execute the package-appclient command.

C:\Program Files\glassfish-3.0.1\glassfish\bin>package-appclient
Creating C:\Program Files\glassfish-3.0.1\glassfish\lib\appclient.jar

It would create a jar file, appclient.jar, which located in your glassfish lib installation folder.

Next is copy your appclient.jar into your client computers. Extract it, and execute appclient command. The appclient format would be, appclient -jar .

C:\Users\edw\Documents\appclient\appclient\glassfish\bin>appclient -jar "C:\Users\edw\Documents\NetBeansProjects\TestEJBClient\dist\TestEJBClient.jar"
Apr 19, 2012 6:28:03 PM com.sun.enterprise.transaction.JavaEETransactionManagerSimplified initDelegates
INFO: Using com.sun.enterprise.transaction.jts.JavaEETransactionManagerJTSDelegate as the delegate
2012-04-19 18:28:10,067 [Main] DEBUG com.edw.main.Main:22 - hello edwin
2012-04-19 18:28:10,072 [Main] DEBUG com.edw.main.Main:23 - my age is 24 years

You can see the server side’s source code here. And here is my netbeans project structure

Not too hard right 😉

A Simple Java RMI Tutorial

Java Remote Method Invocation (Java RMI) enables the programmer to create distributed Java technology-based to Java technology-based applications, in which the methods of remote Java objects can be invoked from other Java virtual machines, possibly on different hosts. RMI uses object serialization to marshal and unmarshal parameters and does not truncate types, supporting true object-oriented polymorphism.

Let’s just say RMI is the “older version” of ejb remote. Because in EJB, enterprise beans are made available for remote clients using RMI.

In this example, im trying to create 2 different project, one is the RMI Server and another one is RMI Client.

First is a simple interface, i will use this interface to create invocation methods and implementations. This interface will be on both Server’s and Client’s side.

package com.edw.rmi;

import java.rmi.Remote;
import java.rmi.RemoteException;

public interface Message extends Remote {
    void sayHello(String name) throws RemoteException;
}

and next is the implementation for my interface, it is exist only on the server’s side. It has to implements my interface and extends to UnicastRemoteObject class.

package com.edw.rmi;

import java.rmi.RemoteException;
import java.rmi.server.UnicastRemoteObject;

public class MessageImpl extends UnicastRemoteObject implements Message {

    public MessageImpl() throws RemoteException {        
    }
    
    @Override
    public void sayHello(String name) throws RemoteException {
        System.out.println("hello "+name);
    }
    
}

And next is creating my server side application. Im running on port 1099 for RMI port.

package com.edw.main;

import com.edw.rmi.MessageImpl;
import java.rmi.registry.LocateRegistry;
import java.rmi.registry.Registry;

public class Main {
    
    private void startServer(){
        try {
            // create on port 1099
            Registry registry = LocateRegistry.createRegistry(1099);
            
            // create a new service named myMessage
            registry.rebind("myMessage", new MessageImpl());
        } catch (Exception e) {
            e.printStackTrace();
        }      
        System.out.println("system is ready");
    }
    
    public static void main(String[] args) {
        Main main = new Main();
        main.startServer();
    }
}

And this is my client’s side application

package com.edw.main;

import java.rmi.registry.LocateRegistry;
import java.rmi.registry.Registry;
import com.edw.rmi.Message;

public class Main {
    
    private void doTest(){
        try {
			// fire to localhost port 1099
            Registry myRegistry = LocateRegistry.getRegistry("127.0.0.1", 1099);
			
			// search for myMessage service
            Message impl = (Message) myRegistry.lookup("myMessage");
			
			// call server's method			
            impl.sayHello("edwin");
			
            System.out.println("Message Sent");
        } catch (Exception e) {
            e.printStackTrace();
        }        
    }
    
    public static void main(String[] args) {
        Main main = new Main();
        main.doTest();
    }
}

This is the screenshot of what happen on my netbeans’ console, for my RMI client’s side

and RMI’s server side

and this is my netbeans’ project

While this is what RMI messages looks like

Have fun with RMI 🙂

A Simple Java Client Server Application using EJB3 and Glassfish3

Well, in this tutorial i want to show you how to create a simple client server application using java. Actually java has dozens of different network protocols, from a simple socket, hessian, burlap, SpringHttpInvoker, SOAP, XML and so on. But in this example, i will try to create a very simple client server application with EJB 3, using Glassfish 3 as JavaEE Container. As usual, i use Netbeans 6.9 with its default Glassfish3 installation.

First, i create a new JavaEE, EJB Module project, named CompressedEJBServer, and create a simple Stateless Session Bean in it

package com.edw.facade;

import javax.ejb.Remote;

/**
 *
 * @author edw
 */
@Remote
public interface ConnectionFacadeRemote {
    String sayHello(String string);
    int sayAge(int age);  
}

and its implementation

package com.edw.facade;

import javax.ejb.Stateless;

/**
 *
 * @author edw
 */
@Stateless
public class ConnectionFacade implements ConnectionFacadeRemote {

    public String sayHello(String string) {
        System.out.println("im at " + this.getClass().getName() + " method sayHello()");
        return "hello " + string;
    }

    public int sayAge(int age) {
        System.out.println("im at " + this.getClass().getName() + " method sayAge()");
        return age * 2;
    }
}

and that’s my EJB3 Server side files. Simple isn’t it?

Next step is creating a Standard Java Application project, for my EJB3 client application. It consist only 1 java file, for testing connection to the server.

package com.edw.main;

import com.edw.facade.ConnectionFacadeRemote;
import java.util.Properties;

import javax.naming.Context;
import javax.naming.InitialContext;
import org.apache.log4j.Logger;

/**
 *
 * @author edw
 */
public class Main {

    private Logger logger = Logger.getLogger(Main.class);

    private void connect() {
        try {
            Properties props = new Properties();
            props.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.enterprise.naming.SerialInitContextFactory");
            props.setProperty("org.omg.CORBA.ORBInitialHost", "localhost");
            
            // glassfish default port value will be 3700, 
            // but im using tcpviewer to redirect my 50005 port to 3700
            props.setProperty("org.omg.CORBA.ORBInitialPort", "50005");

            InitialContext ctx = new InitialContext(props);
            ConnectionFacadeRemote connectionFacadeRemote = (ConnectionFacadeRemote) ctx.lookup("com.edw.facade.ConnectionFacadeRemote");
            logger.debug(connectionFacadeRemote.sayHello("edwin "));
            logger.debug("my age is " + connectionFacadeRemote.sayAge(12) + " years");
        } catch (Exception ex) {
            logger.error(ex.getMessage(), ex);
        }
    }

    public static void main(String[] args) {
        Main x = new Main();
        x.connect();
    }
}

include these jars to your client side’s application,

auto-depends.jar
common-util.jar
config.jar
config-api.jar
config-types.jar
connectors-internal-api.jar
container-common.jar
deployment-common.jar
dol.jar
ejb.security.jar
ejb-container.jar
glassfish-api.jar
glassfish-corba-asm.jar
glassfish-corba-codegen.jar
glassfish-corba-csiv2-idl.jar
glassfish-corba-newtimer.jar
glassfish-corba-omgapi.jar
glassfish-corba-orb.jar
glassfish-corba-orbgeneric.jar
glassfish-naming.jar
gmbal.jar
hk2-core.jar
internal-api.jar
javax.ejb.jar
javax.jms.jar
javax.resource.jar
javax.servlet.jar
javax.transaction.jar
jta.jar
kernel.jar
management-api.jar
orb-connector.jar
orb-iiop.jar
security.jar
tiger-types-osgi.jar
transaction-internal-api.jar 

and dont forget to add CompressedEJBServer project into CompressEJBClient’s project

this is what happen if i run my client side’s application

[Main] DEBUG com.edw.main.Main:30 - hello edwin 
[Main] DEBUG com.edw.main.Main:31 - my age is 24 years

this is my Server side’s project structures

and this is my Client side’s project structures
My Client Side's Project Structure

and this is my TCP Viewer logs, i try to redirect my localhost’s port 50005 into my localhost’s port 3700 (Glassfish’s port), so i can see what is passing through my 50005 port via TCP Viewer’s console.

Hope this can help, have fun and good luck. May the Source be with You.
(*)

Connecting Remote EJB3 from a Servlet with WebLogic 10.3

Right now i’m trying to connect 2 different applications that located in a different server. Im using remote EJB3 to connecting them, with Apache Tomcat as server 1 and WebLogic 10.3 as server 2. Im using Netbeans 6.8 as primary IDE for this test.

create an EJB Module Project from Netbeans IDE, and create these files

first is the remote interface

package com.edw.ejb3;

import javax.ejb.Remote;

@Remote
public interface HelloEJBRemote {
    String sayHello(final String name);    
}

and the ejb implementation

package com.edw.ejb3;

import javax.ejb.Stateless;

@Stateless(mappedName="HelloEJB")
public class HelloEJB implements HelloEJBRemote {
    public String sayHello(final String name) {
        return "Hello "+name+" how do you do?";
    }
}

Package it as JAR or EAR, start Weblogic then use Admin Console (default: http://localhost:7001/ ) to deploy the EJB.
deployment

and to make sure, you can check EJB’s JNDI
ejb's jndi

next is creating a Web Project, dont forget to include your EJB project to your Web Project’s library.

create a servlet file to perform a connection to Remote EJBs.

package ejb;

import com.edw.ejb3.HelloEJBRemote;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.Hashtable;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class EJBServlet extends HttpServlet {

    @Override
   protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        response.setContentType("text/html;charset=UTF-8");
        PrintWriter out = response.getWriter();
        try {

            Hashtable<String, String> env = new Hashtable<String, String>();
            env.put(Context.INITIAL_CONTEXT_FACTORY, "weblogic.jndi.WLInitialContextFactory");
            env.put(Context.PROVIDER_URL, "t3://localhost:7001");

            Context ic = new InitialContext(env);

            HelloEJBRemote remote = (HelloEJBRemote) ic.lookup("HelloEJB#com.edw.ejb3.HelloEJBRemote");

            out.println(remote.sayHello("Edwin"));

        } catch (Exception ex) {
            out.print(ex);
            ex.printStackTrace();
        } finally {
            out.close();
        }
    } 
}

and this is my web.xml configuration file

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
    <servlet>
        <servlet-name>EJBServlet</servlet-name>
        <servlet-class>ejb.EJBServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>EJBServlet</servlet-name>
        <url-pattern>/ejb</url-pattern>
    </servlet-mapping>
    <session-config>
        <session-timeout>
            30
        </session-timeout>
    </session-config>
    <welcome-file-list>
        <welcome-file>index.jsp</welcome-file>
    </welcome-file-list>
</web-app>

if you find this error,

javax.naming.NoInitialContextException: Cannot instantiate class: weblogic.jndi.WLInitialContextFactory [Root exception is java.lang.ClassNotFoundException: weblogic.jndi.WLInitialContextFactory]

it happen because you havent put wlfullclient.jar (WebLogic library) into your Apache Tomcat’s library folder. You can find it in your Weblogic installation folder ({weblogic}\server\lib) or you can create it your self, by executing wljarbuilder.jar.

java -jar wljarbuilder.jar

tomcat libs

you can test your app by running your web project from your IDE.
web content

this is my netbeans project structure
Netbeans Project Structure