KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > caucho > ejb > protocol > EjbProtocolManager


1 /*
2  * Copyright (c) 1998-2006 Caucho Technology -- all rights reserved
3  *
4  * This file is part of Resin(R) Open Source
5  *
6  * Each copy or derived work must preserve the copyright notice and this
7  * notice unmodified.
8  *
9  * Resin Open Source is free software; you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 2 of the License, or
12  * (at your option) any later version.
13  *
14  * Resin Open Source is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or any warranty
17  * of NON-INFRINGEMENT. See the GNU General Public License for more
18  * details.
19  *
20  * You should have received a copy of the GNU General Public License
21  * along with Resin Open Source; if not, write to the
22  *
23  * Free Software Foundation, Inc.
24  * 59 Temple Place, Suite 330
25  * Boston, MA 02111-1307 USA
26  *
27  * @author Scott Ferguson
28  */

29
30 package com.caucho.ejb.protocol;
31
32 import com.caucho.config.ConfigException;
33 import com.caucho.ejb.AbstractServer;
34 import com.caucho.ejb.EnvServerManager;
35 import com.caucho.log.Log;
36 import com.caucho.naming.Jndi;
37 import com.caucho.util.L10N;
38
39 import javax.naming.NamingException JavaDoc;
40 import java.lang.ref.WeakReference JavaDoc;
41 import java.rmi.RemoteException JavaDoc;
42 import java.util.ArrayList JavaDoc;
43 import java.util.HashMap JavaDoc;
44 import java.util.Hashtable JavaDoc;
45 import java.util.Iterator JavaDoc;
46 import java.util.logging.Level JavaDoc;
47 import java.util.logging.Logger JavaDoc;
48
49
50 /**
51  * Server containing all the EJBs for a given configuration.
52  *
53  * <p>Each protocol will extend the container to override Handle creation.
54  */

55 public class EjbProtocolManager {
56   private static final L10N L = new L10N(EjbProtocolManager.class);
57   protected static final Logger JavaDoc log = Log.open(EjbProtocolManager.class);
58
59   private static ThreadLocal JavaDoc<String JavaDoc> _protocolLocal
60     = new ThreadLocal JavaDoc<String JavaDoc>();
61
62   private static Hashtable JavaDoc<String JavaDoc,WeakReference JavaDoc<AbstractServer>> _staticServerMap
63     = new Hashtable JavaDoc<String JavaDoc,WeakReference JavaDoc<AbstractServer>>();
64
65   private final EnvServerManager _ejbServer;
66   private final ClassLoader JavaDoc _loader;
67
68   private String JavaDoc _localJndiPrefix; // = "java:comp/env/cmp";
69
private String JavaDoc _remoteJndiPrefix; // = "java:comp/env/ejb";
70

71   private HashMap JavaDoc<String JavaDoc,AbstractServer> _serverMap
72     = new HashMap JavaDoc<String JavaDoc,AbstractServer>();
73
74   // handles remote stuff
75
protected ProtocolContainer _protocolContainer;
76   protected HashMap JavaDoc<String JavaDoc,ProtocolContainer> _protocolMap
77     = new HashMap JavaDoc<String JavaDoc,ProtocolContainer>();
78
79   /**
80    * Create a server with the given prefix name.
81    */

82   public EjbProtocolManager(EnvServerManager ejbServer)
83     throws ConfigException
84   {
85     _ejbServer = ejbServer;
86     _loader = _ejbServer.getClassLoader();
87
88      ProtocolContainer iiop = IiopProtocolContainer.createProtocolContainer();
89
90      if (iiop != null)
91        _protocolMap.put("iiop", iiop);
92    }
93
94    public void setLocalJndiPrefix(String JavaDoc name)
95    {
96      _localJndiPrefix = name;
97    }
98
99    public String JavaDoc getLocalJndiPrefix()
100    {
101      return _localJndiPrefix;
102    }
103
104    public void setRemoteJndiPrefix(String JavaDoc name)
105    {
106      _remoteJndiPrefix = name;
107    }
108
109    public String JavaDoc getRemoteJndiPrefix()
110    {
111      return _remoteJndiPrefix;
112    }
113
114    /**
115     * Returns the EJB server.
116     */

117   public EnvServerManager getServerManager()
118   {
119     return _ejbServer;
120   }
121
122   /**
123    * Initialize the protocol manager.
124    */

125   public void init()
126     throws NamingException JavaDoc
127   {
128   }
129
130   /**
131    * Gets the current protocol.
132    */

133   public static String JavaDoc getThreadProtocol()
134   {
135     return _protocolLocal.get();
136   }
137
138   /**
139    * Gets the current protocol.
140    */

141   public static String JavaDoc setThreadProtocol(String JavaDoc protocol)
142   {
143     String JavaDoc oldProtocol = _protocolLocal.get();
144
145     _protocolLocal.set(protocol);
146
147     return oldProtocol;
148   }
149
150   public void setProtocolContainer(ProtocolContainer protocol)
151   {
152     _protocolContainer = protocol;
153
154     synchronized (_protocolMap) {
155       _protocolMap.put(protocol.getName(), protocol);
156     }
157
158
159     addProtocolServers(protocol);
160   }
161
162   public void addProtocolContainer(ProtocolContainer protocol)
163   {
164     if (_protocolContainer == null)
165       _protocolContainer = protocol;
166
167     addProtocolContainer(protocol.getName(), protocol);
168   }
169
170   public void addProtocolContainer(String JavaDoc name, ProtocolContainer protocol)
171   {
172     synchronized (_protocolMap) {
173       if (_protocolMap.get(name) == null)
174         _protocolMap.put(name, protocol);
175     }
176
177     addProtocolServers(protocol);
178   }
179
180   public ProtocolContainer getProtocol(String JavaDoc name)
181   {
182     synchronized (_protocolMap) {
183       return _protocolMap.get(name);
184     }
185   }
186
187   private void addProtocolServers(ProtocolContainer protocol)
188   {
189     for (AbstractServer server : _serverMap.values()) {
190       protocol.addServer(server);
191     }
192   }
193
194   /**
195    * Returns the named server if it's in the same JVM.
196    */

197   public static AbstractServer getJVMServer(String JavaDoc serverId)
198   {
199     WeakReference JavaDoc<AbstractServer> serverRef = _staticServerMap.get(serverId);
200
201     return serverRef != null ? serverRef.get() : null;
202   }
203
204   /**
205    * Adds a server.
206    */

207   public void addServer(AbstractServer server)
208     throws NamingException JavaDoc
209   {
210     _serverMap.put(server.getProtocolId(), server);
211
212     for (ProtocolContainer protocol : _protocolMap.values()) {
213       protocol.addServer(server);
214     }
215
216     Thread JavaDoc thread = Thread.currentThread();
217     ClassLoader JavaDoc loader = thread.getContextClassLoader();
218
219     try {
220       Thread.currentThread().setContextClassLoader(_loader);
221       String JavaDoc ejbName = server.getEJBName();
222       String JavaDoc jndiName = server.getJndiName();
223
224       String JavaDoc localJndiName = null;
225       String JavaDoc remoteJndiName = null;
226
227       if (server.isLocal()) {
228         Object JavaDoc localObj = server.getEJBLocalHome();
229
230         // ejb/0f00
231
// EJB 3.0 does not require home interfaces, e.g
232
// for stateless session beans
233
if (localObj == null)
234           localObj = server.getClientObject();
235
236         if (localObj != null) {
237           if (jndiName != null) {
238             if (jndiName.startsWith("java:comp"))
239               localJndiName = Jndi.getFullName(jndiName);
240             else if (_localJndiPrefix != null)
241               localJndiName = Jndi.getFullName(_localJndiPrefix + "/" + jndiName);
242             else
243               throw new NamingException JavaDoc(L.l("<jndi-name> `{0}' requires a fully qualified name or a configured <jndi-local-prefix>",
244                                             jndiName));
245           }
246           else if (_localJndiPrefix != null)
247             localJndiName = Jndi.getFullName(_localJndiPrefix + "/" + ejbName);
248
249           if (localJndiName != null) {
250             if (log.isLoggable(Level.CONFIG))
251               log.config(L.l("local ejb {0} has JNDI binding {1}", localObj, localJndiName));
252
253             bindServer(localJndiName, localObj);
254           }
255           else {
256             if (log.isLoggable(Level.FINE))
257               log.fine(L.l("local ejb {0} has no JNDI binding", localObj));
258           }
259         }
260       }
261
262       if (server.isRemote()) {
263         try {
264           Object JavaDoc remoteObj = server.getEJBHome();
265
266           if (remoteObj != null) {
267
268             if (jndiName != null) {
269               if (jndiName.startsWith("java:comp"))
270                 remoteJndiName = Jndi.getFullName(jndiName);
271               else if (_remoteJndiPrefix != null)
272                 remoteJndiName = Jndi.getFullName(_remoteJndiPrefix + "/" + jndiName);
273               else
274                 throw new NamingException JavaDoc(L.l("<jndi-name> `{0}' requires a fully qualified name or a configured <jndi-remote-prefix>",
275                                               jndiName));
276             }
277             else if (_remoteJndiPrefix != null)
278               remoteJndiName = Jndi.getFullName(_remoteJndiPrefix + "/" + ejbName);
279
280             if (remoteJndiName != null && !remoteJndiName.equals(localJndiName)) {
281               if (log.isLoggable(Level.CONFIG))
282                 log.config(L.l("remote ejb {0} has JNDI binding {1}", remoteObj, remoteJndiName));
283
284               bindServer(remoteJndiName, remoteObj);
285             }
286             else {
287               if (log.isLoggable(Level.FINE))
288                 log.fine(L.l("remote ejb {0} has no JNDI binding", remoteObj));
289             }
290           }
291         }
292         catch (RemoteException JavaDoc ex) {
293           throw new RuntimeException JavaDoc(ex);
294         }
295       }
296     }
297     finally {
298       Thread.currentThread().setContextClassLoader(loader);
299     }
300   }
301
302   private void bindServer(String JavaDoc jndiName, Object JavaDoc obj)
303     throws NamingException JavaDoc
304   {
305     Thread JavaDoc thread = Thread.currentThread();
306     ClassLoader JavaDoc loader = thread.getContextClassLoader();
307
308     try {
309       Thread.currentThread().setContextClassLoader(_loader);
310
311       Jndi.bindDeep(jndiName, obj);
312
313       for (AbstractServer server : _serverMap.values()) {
314         Thread.currentThread().setContextClassLoader(server.getClassLoader());
315
316         Jndi.bindDeep(jndiName, obj);
317       }
318     }
319     finally {
320       Thread.currentThread().setContextClassLoader(loader);
321     }
322   }
323
324   /**
325    * Adds a server.
326    */

327   public void removeServer(AbstractServer server)
328     throws NamingException JavaDoc
329   {
330     for (ProtocolContainer protocol : _protocolMap.values()) {
331       protocol.removeServer(server);
332     }
333   }
334
335   /**
336    * Returns the server specified by the serverId.
337    */

338   public AbstractServer getServerByEJBName(String JavaDoc ejbName)
339   {
340     if (! ejbName.startsWith("/"))
341       ejbName = "/" + ejbName;
342
343     return _serverMap.get(ejbName);
344   }
345
346   /**
347    * Returns the server specified by the serverId.
348    */

349   public AbstractServer getServerByServerId(String JavaDoc protocolId)
350   {
351     for (AbstractServer server : _serverMap.values()) {
352       if (protocolId.equals(server.getProtocolId()))
353         return server;
354     }
355
356     return null;
357   }
358
359   public Iterator JavaDoc getLocalNames()
360   {
361     return _serverMap.keySet().iterator();
362   }
363
364   /**
365    * Returns a list of child EJB names.
366    *
367    * @param ejbName the name which might be a prefix.
368    */

369   public ArrayList JavaDoc<String JavaDoc> getLocalChildren(String JavaDoc ejbName)
370   {
371     if (! ejbName.startsWith("/"))
372       ejbName = "/" + ejbName;
373
374     if (! ejbName.endsWith("/"))
375       ejbName = ejbName + "/";
376
377     ArrayList JavaDoc<String JavaDoc> children = new ArrayList JavaDoc<String JavaDoc>();
378
379     Iterator JavaDoc<String JavaDoc> iter = _serverMap.keySet().iterator();
380     while (iter.hasNext()) {
381       String JavaDoc name = iter.next();
382
383       AbstractServer server = _serverMap.get(name);
384
385       if (server.getClientObject() == null)
386         continue;
387
388       if (name.startsWith(ejbName)) {
389         int prefixLength = ejbName.length();
390         int p = name.indexOf('/', prefixLength);
391
392         if (p > 0)
393           name = name.substring(prefixLength, p);
394         else
395           name = name.substring(prefixLength);
396
397         if (! children.contains(name))
398           children.add(name);
399       }
400     }
401
402     return children;
403   }
404
405   /**
406    * Returns a list of child EJB names.
407    *
408    * @param ejbName the name which might be a prefix.
409    */

410   public ArrayList JavaDoc<String JavaDoc> getRemoteChildren(String JavaDoc ejbName)
411   {
412     if (! ejbName.startsWith("/"))
413       ejbName = "/" + ejbName;
414
415     ArrayList JavaDoc<String JavaDoc> children = new ArrayList JavaDoc<String JavaDoc>();
416
417     Iterator JavaDoc<String JavaDoc> iter = _serverMap.keySet().iterator();
418     while (iter.hasNext()) {
419       String JavaDoc name = iter.next();
420
421       AbstractServer server = _serverMap.get(name);
422
423       if (server.getRemoteObjectClass() == null)
424         continue;
425
426       if (name.startsWith(ejbName)) {
427         int prefixLength = ejbName.length();
428         int p = name.indexOf('/', prefixLength);
429
430         if (p > 0)
431           name = name.substring(prefixLength, p);
432         else
433           name = name.substring(prefixLength);
434
435         if (! children.contains(name))
436           children.add(name);
437       }
438     }
439
440     if (children.size() == 0)
441       return null;
442     else
443       return children;
444   }
445
446   public HandleEncoder createHandleEncoder(AbstractServer server,
447                                            Class JavaDoc primaryKeyClass,
448                                            String JavaDoc protocolName)
449     throws ConfigException
450   {
451     ProtocolContainer protocol = null;
452
453     synchronized (_protocolMap) {
454       protocol = _protocolMap.get(protocolName);
455     }
456
457     if (protocol != null)
458       return protocol.createHandleEncoder(server, primaryKeyClass);
459     else if (_protocolContainer != null)
460       return _protocolContainer.createHandleEncoder(server, primaryKeyClass);
461     else
462       return new HandleEncoder(server, server.getProtocolId());
463   }
464
465   protected HandleEncoder createHandleEncoder(AbstractServer server,
466                                               Class JavaDoc primaryKeyClass)
467     throws ConfigException
468   {
469     if (_protocolContainer != null)
470       return _protocolContainer.createHandleEncoder(server, primaryKeyClass);
471     else
472       return new HandleEncoder(server, server.getProtocolId());
473   }
474
475   /**
476    * Removes an object.
477    */

478   protected void remove(AbstractHandle handle)
479   {
480   }
481
482   /**
483    * Destroys the manager.
484    */

485   public void destroy()
486   {
487   }
488 }
489
490
Popular Tags