📄 ejb笔记.txt
字号:
@PostConstruct:当bean对象完成实例化后,使用了这个注释的方法会被立即调用。这个注释同时适用于有状态和无状态的session bean。
@PreDestroy:使用这个注释的方法会在容器从它的对象池中销毁一个无用的或者过期的bean实例这前调用。同时适用于有状态和无状态的session bean.
@PrePassivate:当一个有状态的session bean实例空闲过长的时间,容器将会钝化它,并把它的状态保存下来。使用这个注释的方法会在容器钝化bean实例之前调用。适用于有状态session bean。
@PostActivate:当客户端再次使用已经被钝化的的有状态session bean时,新的实例被创建,状态被恢复。使用此注释的session bean会在bean的激活完成时调用。
@Init:这个注释指定了有状态session bean初始化的方法。它区别于@PostConstruct注释在于:多个@Init注释方法可以同时存在于有状态session bean 中,但每个bean实例只会有一个@Init注释的方法会被调用。这取决于bean是如何创建的(细节请看EJB 3.0规范)。@PostConstruct在@Init之后被调用。
另一个有用的生命周期方法注释是@Remove,特别是对于有状态session bean。当应用通过存根对象调用使用了@Remove注释的方法时,容器就知道在该方法执行完毕后,要把bean实例从对象池中移走。
一个MDB类必须实现MessageListener接口。当容器检测到bean守候的队列一条消息时,就调用onMessage()方法,将消息作为参数传入。MDB在OnMessage()中决定如何处理该消息。你可以用注释来配置MDB侦听哪一条队列。当MDB部署时,容器将会用到其中的注释信息。在下面的例子中,CalculatorBean MDB会在JMS队列queue/mdb有消息进入时调用。MDB解析消息,并根据消息内容计算投资。
@MessageDriven(activateConfig =
{
@ActivationConfigProperty(propertyName="destinationType",
propertyValue="javax.jms.Queue"),
@ActivationConfigProperty(propertyName="destination",
propertyValue="queue/mdb")
})
public class CalculatorBean implements MessageListener {
public void onMessage (Message msg) {
try {
TextMessage tmsg = (TextMessage) msg;
Timestamp sent =
new Timestamp(tmsg.getLongProperty("sent"));
StringTokenizer st =
new StringTokenizer(tmsg.getText(), ",");
int start = Integer.parseInt(st.nextToken());
int end = Integer.parseInt(st.nextToken());
double growthrate = Double.parseDouble(st.nextToken());
double saving = Double.parseDouble(st.nextToken());
double result =
calculate (start, end, growthrate, saving);
RecordManager.addRecord (sent, result);
} catch (Exception e) {
e.printStackTrace ();
}
}
// ... ...
}
除@EJB注释之外,EJB 3.0也支持@Resource注释来注入来自JNDI的任何资源。下面的例子中,我演示了如何注入服务器端默入的TimerService和SessionContext对象,也演示了如何注入来自JNDI的命名数据库和JMS资源。
@Resource
TimerService tms;
@Resource
SessionContext ctx;
@Resource (name="DefaultDS")
DataSource myDb;
@Resource (name="ConnectionFactory")
QueueConnectionFactory factory;
@Resource (name="queue/A")
Queue queue;
安全
容器也提供了安全服务来进行用户认证和根据用户规则来限制对POJO的访问。对每一个POJO来说,你可以通过使用@SecurityDomain注释为它指定一个安全域, 安全域告诉容器到哪里去找密码和用户角色列表。JBoss中的other域表明文件是classpath中的users.propertes和roles.properties。这样,对每一个方法来说,我们可以使用一个安全限制注释来指定谁可以运行这个方法。比如,下面的例子,容器对所有试图调用addFund()的用户进行认证,只允许拥有AdminUser角色的用户实际运行它。如果你没有登录或者没有以管理员的身份登录,一个安全意外将会抛出。
@Stateless
@SecurityDomain("other")
public class CalculatorBean implements Calculator {
@RolesAllowed()
public void addFund (String name, double growthrate) {
// ... ...
}
@RolesAllowed()
public void addInvestor (String name, int start, int end) {
// ... ...
}
@PermitAll
public Collection <Fund> getFunds () {
// ... ...
}
// ... ...
@RolesAllowed()
public double calculate (int fundId, int investorId,
double saving) {
// ... ...
}
}
通用拦截器
事务和安全服务都可以被看作是容器管理的运行时刻拦截器。容器拦截了对EJB存根的调用,并在其上应用事务上下文或进行安全限制。
在EJB 3.0中,你可以自己写拦截器来扩展容器服务。使用@AroundInvoke注释,你可以将任意bean方法作为拦截器方法在任意bean方法之前和之后运行。下面的例子中,log()方法是一个拦截器,它计算和记录了其它bean方法的执行时间:
@Stateful
public class CalculatorBean implements Calculator {
// Bean methods that are to be intercepted by "log()"
// bean方法将被log()方法拦截
//
// ... ...
@AroundInvoke
public Object log (InvocationContext ctx)
throws Exception {
String className = ctx.getBean().getClass().getName();
String methodName = ctx.getMethod().getName();
String target = className + "." + methodName + "()";
long start = System.currentTimeMillis();
System.out.println ("Invoking " + target);
try {
return ctx.proceed();
} catch(Exception e) {
throw e;
} finally {
System.out.println("Exiting " + target);
cal.setTrace(cal.getTrace() + "
" +
"Exiting " + target);
long time = System.currentTimeMillis() - start;
System.out.println("This method takes " +
time + "ms to execute");
}
}
2,会话 Bean 用于管理实体 Bean 和其它会话 Bean 的交互、访问资源,它们通常代表客户机执行任务。会话 Bean 对应于“模型-视图-控制器”体系结构中的控制器
3.有状态会话Bean ,每个用户有自己特有的一个实例,在用户的生存期内, Bean保持了用户的信息,即“有状态”;一旦用户灭亡(调用结束或实例结束),Bean的生命期也告结束。即每个用户最初都会得到一个初始的Bean.
4.无状态会话Bean一旦实例化就被加进会话池中,各个用户都可以共用。即使用户已经消亡,Bean 的生命期也不一定结束,它可能依然存在于会话池中,供其他用户调用。由于没有特定的用户,那么也就不能保持某一用户的状态,所以叫无状态Bean.但无状态会话Bean 并非没有状态,如果它有自己的属性(变量),那么这些变量就会受到所有调用它的用户的影响,这是在实际应用中必须注意的。
5.EJB包括Session Bean、Entity Bean、Message Driven Bean,基于JNDI、RMI、JAT等技术实现。
SessionBean在J2EE应用程序中被用来完成一些服务器端的业务操作,例如访问数据库、调用其他EJB组件。EntityBean被用来代表应用系统中用到的数据。
对于客户机,SessionBean是一种非持久性对象,它实现某些在服务器上运行的业务逻辑。
对于客户机,EntityBean是一种持久性对象,它代表一个存储在持久性存储器中的实体的对象视图,或是一个由现有企业应用程序实现的实体。
Session Bean 还可以再细分为 Stateful Session Bean 与 Stateless Session Bean
Enterprise JavaBeans 技术一般分成三种核心类型的 bean:会话 bean、消息驱动 bean 和实体 bean。bean 还可以分成充当业务对象的 bean 和充当数据对象的 bean。会话 bean 和消息驱动 bean 是业务对象;实体 bean 是数据对象。
会话虚包模式
幸运的是,有一个设计模式让您允许用户访问数据对象,同时又不会将实体 bean 暴露给 Web 层。会话虚包(Session Facade)模式在实体 bean 和应用程序客户机之间放置了一个会话 bean。当我通过这种方法使用会话 bean 时,我喜欢把它当作管理器,因为它的任务是管理对其它实体的访问。
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -