KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > jfox > ejb > MDBBucket


1 /* JFox, the OpenSource J2EE Application Server
2  *
3  * Distributable under GNU LGPL license by gun.org
4  * more details please visit http://www.huihoo.org/jfox
5  */

6
7 package org.jfox.ejb;
8
9 import java.lang.reflect.Proxy JavaDoc;
10 import java.rmi.RemoteException JavaDoc;
11 import javax.ejb.EJBContext JavaDoc;
12 import javax.ejb.EJBException JavaDoc;
13 import javax.ejb.EnterpriseBean JavaDoc;
14 import javax.ejb.Handle JavaDoc;
15 import javax.ejb.MessageDrivenBean JavaDoc;
16 import javax.ejb.MessageDrivenContext JavaDoc;
17 import javax.ejb.RemoveException JavaDoc;
18 import javax.jms.Destination JavaDoc;
19 import javax.jms.JMSException JavaDoc;
20 import javax.jms.Session JavaDoc;
21
22 import org.jfox.ejb.connector.EJBInvocation;
23 import org.jfox.ejb.meta.MDBDescriptor;
24 import org.jfox.ejb.timer.EJBTimerService;
25 import org.jfox.ioc.ComponentName;
26 import org.jfox.ioc.connector.ConnectorHelper;
27 import org.jfox.ioc.connector.ConnectorRemote;
28 import org.jfox.ioc.connector.ObjectId;
29 import org.jfox.ioc.depend.DependencyPack;
30 import org.jfox.ioc.depend.ObjectDependency;
31 import org.jfox.ioc.util.ObjectUUID;
32 import org.jfox.jms.JMSConnectionRemote;
33 import org.jfox.jms.JMSConsumer;
34 import org.jfox.jms.connector.JMSConnectorInvoker;
35 import org.jfox.jms.connector.JMSContainer;
36 import org.jfox.jms.message.JMSMessage;
37 import org.jfox.jndi.InitialContextHelper;
38 import org.jfox.jndi.JNDIProperties;
39
40 /**
41  * 一个Message Driven Bean 的小容器,接收到消息之后,把消息交给Bean执行
42  *
43  * @author <a HREF="mailto:young_yy@hotmail.com">Young Yang</a>
44  */

45
46 public class MDBBucket extends BucketSupport {
47     /*
48     * 静态变量,所有MDBBucket共用一个 conn
49     */

50     private static MDBConnection conn = null;
51
52     private MDBSession session = null;
53
54     private MDBObjectPool instancePool = null;
55
56     private MessageDrivenContext JavaDoc ejbConext = null;
57
58     private String JavaDoc user = null;
59     private String JavaDoc password = null;
60
61     public MDBBucket() {
62         super();
63     }
64
65     //########### EJBObject 定义的方法
66
public Object JavaDoc getPrimaryKey(EnterpriseBean JavaDoc obj) throws RemoteException JavaDoc {
67         throw new EJBException JavaDoc("NOT SUPPORT!");
68     }
69
70     public Handle JavaDoc getHandle(EnterpriseBean JavaDoc obj) throws RemoteException JavaDoc {
71         throw new EJBException JavaDoc("NOT SUPPORT!");
72     }
73
74     public boolean isIdentical(EJBObjectId thisObjectId, EJBObjectId thatObjectId) throws RemoteException JavaDoc {
75         throw new EJBException JavaDoc("NOT SUPPORT!");
76     }
77
78     public void remove(EnterpriseBean JavaDoc bean) throws RemoteException JavaDoc, RemoveException JavaDoc {
79         ejbRemove(bean);
80     }
81
82     public void remove(Handle JavaDoc handle) throws RemoteException JavaDoc, RemoveException JavaDoc {
83         throw new EJBException JavaDoc("NOT SUPPORT!");
84     }
85
86     public void remove(Object JavaDoc primaryKey) throws RemoteException JavaDoc, RemoveException JavaDoc {
87         throw new EJBException JavaDoc("NOT SUPPORT!");
88     }
89
90     /**
91      * MDB No EJBHome
92      * @param invocation
93      * @return
94      * @throws Exception
95      */

96     public Object JavaDoc invokeHome(EJBInvocation invocation) throws Exception JavaDoc {
97         throw new EJBException JavaDoc("MessageDrivenBean has no EJBHome.");
98     }
99
100     public Object JavaDoc invokeBean(EJBInvocation invocation) throws Exception JavaDoc {
101         return super.invokeBean(invocation);
102     }
103
104     public void ejbActivate(EnterpriseBean JavaDoc bean) throws EJBException JavaDoc, RemoteException JavaDoc {
105         throw new EJBException JavaDoc("NOT SUPPORT!");
106     }
107
108     public void ejbPassivate(EnterpriseBean JavaDoc bean) throws EJBException JavaDoc, RemoteException JavaDoc {
109         throw new EJBException JavaDoc("NOT SUPPORT!");
110     }
111
112     public void ejbRemove(EnterpriseBean JavaDoc bean) throws EJBException JavaDoc, RemoteException JavaDoc {
113         logger.debug(bean + " remove");
114         ((MessageDrivenBean JavaDoc)bean).ejbRemove();
115     }
116
117     public void setContext(EnterpriseBean JavaDoc bean, EJBContext JavaDoc ctx) throws EJBException JavaDoc, RemoteException JavaDoc {
118         logger.debug(bean + " setMessageDrivenContext");
119         ((MessageDrivenBean JavaDoc)bean).setMessageDrivenContext((MessageDrivenContext JavaDoc)ctx);
120     }
121
122     public EJBPoolableObject retrieveBean(Object JavaDoc key) throws Exception JavaDoc {
123         MDBPoolableObject pobj = (MDBPoolableObject) instancePool.retrieveObject();
124         if(!pobj.isEjbCreated()) { // 新生的对象,要调用 setSessionContext, ejbCreate
125
MessageDrivenBean JavaDoc bean = (MessageDrivenBean JavaDoc) pobj.getBeanInstance();
126             setContext(bean, ejbConext);
127             ejbCreate(bean, "create", null);
128             pobj.ejbCreated();
129         }
130         return pobj;
131     }
132
133     public void restoreBean(Object JavaDoc key, EJBPoolableObject pobj) {
134         instancePool.restoreObject(pobj);
135     }
136
137     public EJBObjectId createBean(EJBInvocation invocation) throws Exception JavaDoc {
138         throw new EJBException JavaDoc("NOT Support in MDB!");
139     }
140
141     public void syncBean(EJBInvocation invocation) {
142         throw new EJBException JavaDoc("NOT Support in MDB!");
143     }
144
145     /**
146      * 要做 ConnectionFactory.createConnection 的事情
147      * 多个MDBBucket 共用一个 Connection
148      * @throws Exception
149      */

150     protected void doInit() throws Exception JavaDoc {
151         idgen = EJBObjectIDGenerator.newInstance(bucketMeta.getEJBDescriptor().getEjbName(),
152                                                  bucketMeta.getBeanClass().getName(),
153                                                  bucketMeta.getBeanClass().getName());
154
155         beanMethods = introspectorBeanMethods(MDBConnection.class,JMSConnectionRemote.class);
156
157         timerService = new EJBTimerService(bucketMeta.getEJBDescriptor().getEjbName());
158
159         // bind refrence to EnterpriseContext
160
bindReference();
161
162         // create connection if needed
163
if(conn == null) {
164             conn = createConnection(user,password,false);
165             conn.start();
166         }
167
168         // craete Consumer
169
instancePool = (MDBObjectPool) context.getRegistry().getComponentInstance(
170                                                                 ComponentName.newInstance(MDBObjectPool.class),
171                                                                 new DependencyPack[]{
172                                                                     new DependencyPack("EJBObjectFactory",
173                                                                                       new ObjectDependency(new MDBObjectFactory(MDBPoolableObject.class, this)))});
174         // create session
175
session = (MDBSession) conn.createSession(false, Session.AUTO_ACKNOWLEDGE);
176         String JavaDoc destinationJndiName = ((MDBDescriptor) bucketMeta.getEJBDescriptor()).getDestination();
177         Destination JavaDoc dest = (Destination JavaDoc)InitialContextHelper.getInitialContext().lookup(destinationJndiName);
178         // 生成一个Consumer,这样才能接收到该地址的消息,但是MDBSession接收到消息之后,将从 pool 中取得MDB实例来响应请求
179
JMSConsumer consumer = (JMSConsumer)session.createConsumer(dest);
180         // 激活异步接收
181
session.setConsumerAsync(consumer,true);
182
183     }
184
185     protected void doDestroy() throws Exception JavaDoc {
186         // MDB 不需要从JNDI中卸载
187
// super.doDestroy();
188
instancePool.destroy();
189     }
190
191     public void onMessage(String JavaDoc sessionId, MessageDrivenBean JavaDoc bean, JMSMessage msg) throws RemoteException JavaDoc, JMSException JavaDoc {
192         conn.onMessage(sessionId,bean,msg);
193     }
194
195     protected synchronized MDBConnection createConnection(String JavaDoc userName, String JavaDoc password, boolean isXA) throws JMSException JavaDoc {
196
197         ObjectId clientId = new ObjectId(ObjectUUID.randomUUID());
198         // lookup ConnectorService from jndi, 然后使用动态代理封装成 JMSContainer 对象
199
ConnectorRemote remote = ConnectorHelper.lookupConnector(JNDIProperties.getProviderURL());
200
201         JMSContainer container = null;
202
203         if(container == null) {
204             container = (JMSContainer) Proxy.newProxyInstance(this.getClass().getClassLoader(),
205                                                               new Class JavaDoc[]{JMSContainer.class},
206                                                               new JMSConnectorInvoker(clientId, remote));
207         }
208
209         container.auth(userName, password);
210
211         MDBConnection conn = new MDBConnection(clientId.toString(), container, isXA);
212         try {
213             // 生成 MDBConnection 的代理并注册到 JMSContainer
214
// 主要用来改变 onMessage 方法的策略,使用 ConnectorRemote
215
Object JavaDoc proxy = Proxy.newProxyInstance(this.getClass().getClassLoader(),
216                                                   new Class JavaDoc[]{JMSConnectionRemote.class},
217                                                   new MDBConnectorInvoker(nextObjectId(),remote));
218             container.registerConnection(clientId.toString(), proxy);
219         }
220         catch(Exception JavaDoc e) {
221             e.printStackTrace();
222         }
223         return conn;
224     }
225
226     public static void main(String JavaDoc[] args) {
227
228     }
229
230 }
231
Popular Tags