1:本地调用
前提:
(1)被调用者实现了LOCAL接口
(2)调用者和被调用者应该在同一EJB模块打包文件(ear)內,由于是本地调用,也就是说调用者和被调用者应运行于同一个ejb容器内,所以,想用类似main函数调用的企图都是不能成功的(因为main函数不可能运行于ejb容器)。
(3)调用者的部署描述(ejb-jar.xml)中有关于被调用者的Local ref的描述。
示例如下:
比如我有一个无状态sessionBean(被访问者):MapSessionBean,一个访问用的sessionBean:AccessBean
其中AccessBean的ejb-jar.xml应有被调用者的Local ref描述,否则,不能进行本地调用:
<?
xmlversion="1.0"encoding="UTF-8"
?>
<!
DOCTYPEejb-jarPUBLIC"-//SunMicrosystems,Inc.//DTDEnterpriseJavaBeans2.0//EN""http://java.sun.com/dtd/ejb-jar_2_0.dtd"
>
<
ejb-jar
id
="ejb-jar_ID"
>
<
display-name
>
TestEJB
</
display-name
>
<
enterprise-beans
>
<
session
id
="MapSession"
>
<
ejb-name
>
MapSession
</
ejb-name
>
<
home
>
co.test.bean.MapSessionHome
</
home
>
<
remote
>
co.test.bean.MapSession
</
remote
>
<
local-home
>
co.test.bean.MapSessionLocalHome
</
local-home
>
<
local
>
co.test.bean.MapSessionLocal
</
local
>
<
ejb-class
>
co.test.bean.MapSessionBean
</
ejb-class
>
<
session-type
>
Stateless
</
session-type
>
<
transaction-type
>
Container
</
transaction-type
>
<
ejb-local-ref
id
="EJBLocalRef_1165387097531"
>
<
ejb-ref-name
>
ejb/MapSession
</
ejb-ref-name
>
<
ejb-ref-type
>
Session
</
ejb-ref-type
>
<
local-home
>
co.test.bean.MapSessionLocalHome
</
local-home
>
<
local
>
co.test.bean.MapSessionLocal
</
local
>
<
ejb-link
>
MapSession
</
ejb-link
>
</
ejb-local-ref
>
</
session
>
<
session
id
="AccessBean"
>
<
ejb-name
>
AccessBean
</
ejb-name
>
<
home
>
co.test.bean.AccessBeanHome
</
home
>
<
remote
>
co.test.bean.AccessBean
</
remote
>
<
local-home
>
co.test.bean.AccessBeanLocalHome
</
local-home
>
<
local
>
co.test.bean.AccessBeanLocal
</
local
>
<
ejb-class
>
co.test.bean.AccessBeanBean
</
ejb-class
>
<
session-type
>
Stateless
</
session-type
>
<
transaction-type
>
Container
</
transaction-type
>
<
ejb-local-ref
id
="EJBLocalRef_1165393609046"
>
<
ejb-ref-name
>
ejb/MapSession
</
ejb-ref-name
>
<
ejb-ref-type
>
Session
</
ejb-ref-type
>
<
local-home
>
co.test.bean.MapSessionLocalHome
</
local-home
>
<
local
>
co.test.bean.MapSessionLocal
</
local
>
<
ejb-link
>
MapSession
</
ejb-link
>
</
ejb-local-ref
>
</
session
>
</
enterprise-beans
>
</
ejb-jar
>
本地调用代码如下:
public
void
invoke()

...
{
MapSessionLocalHomemapSessionLocalHome=null;
MapSessionLocalmapSessionLocal=null;
InitialContextinitContext=null;
finalStringJNDIName="java:comp/env/ejb/MapSession";

try...{
System.out.println("ininvoke()!!!!!!!");
initContext=newInitialContext();
Objectobj=initContext.lookup(JNDIName);
mapSessionLocalHome=(MapSessionLocalHome)obj;
mapSessionLocal=mapSessionLocalHome.create();
Personperson=newPerson("lcl",555);
mapSessionLocal.setMapValue("key1",person);

PersontempPerson=(Person)mapSessionLocal.getMapValue("key1");
tempPerson.setName("wangwu");
tempPerson.setAge(88);
PersonchangedPerson=(Person)mapSessionLocal.getMapValue("key1");
System.out.println("afterchanged:"+changedPerson.getName()+"---"+changedPerson.getAge());

}
catch(Exceptione)

...{
e.printStackTrace();
}

}
值得一提的是,在本地调用中,对一个object的操作,是在同一内存块中进行的。具体到上面的代码,tempPerson的改变,已经影响到了changedPerson的值。
2:远程方法调用:
前提:被调用者实现了REMOTE接口,适用于不在同一模块中的ejb,servlet.
public
static
void
main(String[]args)

...
{

MapSessionHomemapSessionHome=null;
MapSessionmapSession=null;
InitialContextinitContext=null;

finalStringJNDIName="ejb/co/test/bean/MapSessionHome";

try...{
System.out.println("inMapSessionClient!!!!!!!");
initContext=newInitialContext();
Objectobj=initContext.lookup(JNDIName);

mapSessionHome=
(MapSessionHome)PortableRemoteObject.narrow(
obj,
MapSessionHome.class);
mapSession=mapSessionHome.create();
Personperson1=newPerson("zhangsan",100);

mapSession.setMapValue("key1",person1);
PersontempPerson=(Person)mapSession.getMapValue("key1");

tempPerson.setName("lisi");
tempPerson.setAge(500);
System.out.println("beforechanged:"+tempPerson.getName()+"---"+tempPerson.getAge());

PersonchangedPerson=(Person)mapSession.getMapValue("key1");
System.out.println("afterchanged:"+changedPerson.getName()+"---"+changedPerson.getAge());


}catch(Exceptione)...{
e.printStackTrace();
System.exit(0);
}
}
值得一提的是,在远程调用中,对一个object的操作,经过了corba处理,是不在同一内存块中进行的。具体到上面的代码,tempPerson的改变,不影响changedPerson的值(其实理所当然,一个是远程的对象,你个是本地内存对象)。
3:远程调用:适用于不在同一机器的远程调用:
对于websphere:
InitialFactory:(INITIAL_CONTEXT_FACTORY):com.ibm.websphere.naming.WsnInitialContextFactory
ProviderURL:(PROVIDER_URL):iiop://serverip:
2809
/
其中:server ip为ejb容器ip地址.必须注意:在websphere服务器的配置中,有一项orb bootstrap setting的配置,它的默认配置如下:
Port:2809
hostname:localhost
其中,hostname必须改为server的ip地址,
hostname:192.168.0.81
否则,远程调用不能成功.
调用代码如下:
public
static
void
main(String[]args)

...
{
System.out.println("inMapSessionRemoteTest");
MapSessionHomemapSessionHome=null;
MapSessionmapSession=null;
StringJNDIName="ejb/co/test/bean/MapSessionHome";
Propertiesp=newProperties();
p.put(Context.INITIAL_CONTEXT_FACTORY,"com.ibm.websphere.naming.WsnInitialContextFactory");
p.put(Context.PROVIDER_URL,"iiop://192.168.0.81:2809/");
InitialContextinitContext;
try

...{
initContext=newInitialContext(p);
Objectobj=initContext.lookup(JNDIName);
mapSessionHome=(MapSessionHome)PortableRemoteObject.narrow(
obj,
MapSessionHome.class);
mapSession=mapSessionHome.create();
Personperson1=newPerson("zhangsan",100);
mapSession.setMapValue("key1",person1);
PersontempPerson=(Person)mapSession.getMapValue("key1");
tempPerson.setName("lisi");
tempPerson.setAge(500);
System.out.println("beforechanged:"+tempPerson.getName()+"---"+tempPerson.getAge());
PersonchangedPerson=(Person)mapSession.getMapValue("key1");
System.out.println("afterchanged:"+changedPerson.getName()+"---"+changedPerson.getAge());
}
catch(Exceptione)

...{
//TODOAuto-generatedcatchblock
e.printStackTrace();
}

}