EJB的远程调用与本地调用http://fay19860916.blog.163.com/blog/static/1186491192009819220664/

时间:2022-04-29 12:27:59

核心:远程调用传值 本地调用传址

远程调用是指运行在两个JVM中,通过通信建立的调用,本地调用是指运行在同一个JVM中,调用时传递的是一个引用,即一个内存地址

编写EJB:

package com.ighost.ejb;

import java.io.Serializable;
import java.util.Date;

public class User implements Serializable{

 private int id;
 
 private String name;
 
 public int getId() {
  return id;
 }

 public void setId(int id) {
  this.id = id;
 }

 public String getName() {
  return name;
 }

 public void setName(String name) {
  this.name = name;
 }
}

本地接口:

package com.ighost.ejb;


public interface UserManagerL {
 
 public void addUser(User user);
 
}

远程访问接口

package com.ighost.ejb;


public interface UserManagerR {

 public void addUser(User user);
 
}

实现Bean

package com.ighost.ejb;

import javax.ejb.Local;
import javax.ejb.Remote;
import javax.ejb.Stateless;

@Stateless
@Remote({UserManagerR.class})
@Local({UserManagerL.class})
public class UserManagerBean implements UserManagerR,UserManagerL {

 public void addUser(User user){
  System.out.println("用户" + user.getName() + "以保存成功");  
  user.setId(10); 
 }
  
}
调用过程:

远程调用

package ejbclient;

import java.io.FileInputStream;
import java.io.InputStream;
import java.util.Properties;

import javax.naming.InitialContext;

import com.ighost.ejb.User;
import com.ighost.ejb.UserManagerR;

public class UserManagerClient {

 /**
  * 远程调用
  * @param args
  */
 public static void main(String[] args) throws Exception {
  // TODO Auto-generated method stub
  Properties prop = new Properties();
  InputStream in = new FileInputStream("src/jndi.properties");
  prop.load(in);
  
  //初始化
  InitialContext ctx = new InitialContext(prop);
  //查找EJBBean
  UserManagerR userManager = (UserManagerR)ctx.lookup("UserManagerBean/remote");
  User user = new User();
  user.setName("zhangsan");
  //user.setBirth(new Date());
  userManager.addUser(user);
  
  System.out.println("用户已经被保存 id为:" + user.getId());  
  
 }

}

输出结果

用户已经被保存 id为:0
远程调用需要把需要的接口和类打包放到buildpath下 把jboss的client也要引入

本地调用测试:

建立一个web工程,将web工程与EJB部署到同一个服务器jboss下,即可使运行在同一个jvm下

<%@ page language="java" import="java.util.*,javax.naming.*,com.ighost.ejb.*,java.io.*" contentType="text/html; charset=GB18030"
    pageEncoding="GB18030"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=GB18030">
<title>Insert title here</title>
</head>
<body>

<%
  //本地调用EJB_03 调用与EJB_03中的同一个JVM进程里 所以为本地调用 传递的是一个地址
  
  //初始化
  InitialContext ctx = new InitialContext();
  //查找EJBBean
  UserManagerL userManager = (UserManagerL)ctx.lookup("UserManagerBean/local");
  User user = new User();
  user.setName("zhangsan");
  //user.setBirth(new Date());
  userManager.addUser(user);
  
  out.println("用户已经被保存 id为:" + user.getId());  
 
%>

</body>
</html>

输出结果:

用户已经被保存 id为:10

注意:使用JSP本地调用时,不需要把接口和相关的类再加入环境变量 初始化可以使用默认的 另外jboss的client端也不需要 部署时jboss会把这些jar包部署进去 如果出现如下错误 则去掉相关的lib引用即可

java.lang.IllegalArgumentException: Wrong target. class com.persia.ejb.UserManagerBean for public void com.persia.ejb.UserManagerBean.addUser(com.persia.ejb.User)

at org.jboss.aop.joinpoint.MethodInvocation.handleErrors(MethodInvocation.java:141)

at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:116)

at org.jboss.ejb3.interceptor.InvocationContextImpl.proceed(InvocationContextImpl.java:166)

at org.jboss.ejb3.interceptor.EJB3InterceptorsInterceptor.invoke(EJB3InterceptorsInterceptor.java:63)

at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)

at org.jboss.ejb3.entity.TransactionScopedEntityManagerInterceptor.invoke(TransactionScopedEntityManagerInterceptor.java:54)

at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)

at org.jboss.ejb3.AllowedOperationsInterceptor.invoke(AllowedOperationsInterceptor.java:47)

at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)

at org.jboss.aspects.tx.TxPolicy.invokeInOurTx(TxPolicy.java:79)