KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > naming > modules > memory > MemoryNamingContext


1 /*
2  * Copyright 1999-2004 The Apache Software Foundation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16
17 package org.apache.naming.modules.memory;
18
19 import java.util.Hashtable JavaDoc;
20
21 import javax.naming.Context JavaDoc;
22 import javax.naming.InitialContext JavaDoc;
23 import javax.naming.LinkRef JavaDoc;
24 import javax.naming.Name JavaDoc;
25 import javax.naming.NameNotFoundException JavaDoc;
26 import javax.naming.NamingEnumeration JavaDoc;
27 import javax.naming.NamingException JavaDoc;
28 import javax.naming.NotContextException JavaDoc;
29 import javax.naming.Reference JavaDoc;
30 import javax.naming.Referenceable JavaDoc;
31 import javax.naming.directory.Attributes JavaDoc;
32 import javax.naming.directory.DirContext JavaDoc;
33 import javax.naming.spi.NamingManager JavaDoc;
34
35 import org.apache.naming.core.BaseDirContext;
36 import org.apache.naming.core.NamingContextEnumeration;
37 import org.apache.naming.core.NamingEntry;
38 import org.apache.tomcat.util.res.StringManager;
39
40 /**
41  * In-memory context.
42  *
43  * IMPLEMENTATION. We use NamingEntry stored in a tree of hashtables.
44  *
45  * @author Remy Maucherat
46  * @author Costin Manolache
47  */

48 public class MemoryNamingContext extends BaseDirContext {
49
50     public MemoryNamingContext()
51         throws NamingException JavaDoc
52     {
53         super();
54     }
55
56     /**
57      * Builds a naming context using the given environment.
58      */

59     public MemoryNamingContext(Hashtable JavaDoc env)
60         throws NamingException JavaDoc
61     {
62         super( env );
63         this.bindings = new Hashtable JavaDoc();
64     }
65
66     // ----------------------------------------------------- Instance Variables
67

68     /**
69      * The string manager for this package.
70      */

71     protected static StringManager sm =
72         StringManager.getManager("org.apache.naming.res");
73
74     /**
75      * Bindings in this Context.
76      */

77     protected Hashtable JavaDoc bindings;
78
79     public void setBindings( Hashtable JavaDoc bindings ) {
80         this.bindings = bindings;
81     }
82
83     // -------------------------------------------------------- Context Methods
84

85     /**
86      * Unbinds the named object. Removes the terminal atomic name in name
87      * from the target context--that named by all but the terminal atomic
88      * part of name.
89      * <p>
90      * This method is idempotent. It succeeds even if the terminal atomic
91      * name is not bound in the target context, but throws
92      * NameNotFoundException if any of the intermediate contexts do not exist.
93      *
94      * @param name the name to bind; may not be empty
95      * @exception NameNotFoundException if an intermediate context does not
96      * exist
97      * @exception NamingException if a naming exception is encountered
98      */

99     public void unbind(Name JavaDoc name, boolean isContext)
100         throws NamingException JavaDoc
101     {
102         checkWritable(name);
103         
104     while ((!name.isEmpty()) && (name.get(0).length() == 0))
105         name = name.getSuffix(1);
106         
107         if (name.isEmpty())
108             throw new NamingException JavaDoc
109                 (sm.getString("namingContext.invalidName"));
110         
111         NamingEntry entry = (NamingEntry) bindings.get(name.get(0));
112         
113         if (entry == null) {
114             throw new NameNotFoundException JavaDoc
115                 (sm.getString("namingContext.nameNotBound", name.get(0)));
116         }
117         
118         if (name.size() > 1) {
119             if (entry.type == NamingEntry.CONTEXT) {
120                 ((Context JavaDoc) entry.value).unbind(name.getSuffix(1));
121             } else {
122                 throw new NamingException JavaDoc
123                     (sm.getString("namingContext.contextExpected"));
124             }
125         } else {
126             if (entry.type == NamingEntry.CONTEXT) {
127                 ((Context JavaDoc) entry.value).close();
128                 bindings.remove(name.get(0));
129             } else {
130                 if( isContext ) {
131                     throw new NotContextException JavaDoc
132                         (sm.getString("namingContext.contextExpected"));
133                 } else {
134                     bindings.remove(name.get(0));
135                 }
136             }
137         }
138     }
139
140     /**
141      * Enumerates the names bound in the named context, along with the class
142      * names of objects bound to them. The contents of any subcontexts are
143      * not included.
144      * <p>
145      * If a binding is added to or removed from this context, its effect on
146      * an enumeration previously returned is undefined.
147      *
148      * @param name the name of the context to list
149      * @return an enumeration of the names and class names of the bindings in
150      * this context. Each element of the enumeration is of type NameClassPair.
151      * @exception NamingException if a naming exception is encountered
152      */

153     public NamingEnumeration JavaDoc list(Name JavaDoc name)
154         throws NamingException JavaDoc {
155         // Removing empty parts
156
while ((!name.isEmpty()) && (name.get(0).length() == 0))
157             name = name.getSuffix(1);
158
159         if (name.isEmpty()) {
160             return new NamingContextEnumeration(bindings.elements(), this, false);
161         }
162         
163         NamingEntry entry = (NamingEntry) bindings.get(name.get(0));
164         
165         if (entry == null) {
166             throw new NameNotFoundException JavaDoc
167                 (sm.getString("namingContext.nameNotBound", name.get(0)));
168         }
169         
170         if (entry.type != NamingEntry.CONTEXT) {
171             throw new NamingException JavaDoc
172                 (sm.getString("namingContext.contextExpected"));
173         }
174         return ((Context JavaDoc) entry.value).list(name.getSuffix(1));
175     }
176
177     private Name JavaDoc removeEmptyPrefix(Name JavaDoc name ) {
178         while ((!name.isEmpty()) && (name.get(0).length() == 0))
179             name = name.getSuffix(1);
180         return name;
181     }
182     
183     /**
184      * Enumerates the names bound in the named context, along with the
185      * objects bound to them. The contents of any subcontexts are not
186      * included.
187      * <p>
188      * If a binding is added to or removed from this context, its effect on
189      * an enumeration previously returned is undefined.
190      *
191      * @param name the name of the context to list
192      * @return an enumeration of the bindings in this context.
193      * Each element of the enumeration is of type Binding.
194      * @exception NamingException if a naming exception is encountered
195      */

196     public NamingEnumeration JavaDoc listBindings(Name JavaDoc name)
197         throws NamingException JavaDoc {
198         // Removing empty parts
199
while ((!name.isEmpty()) && (name.get(0).length() == 0))
200             name = name.getSuffix(1);
201         
202         if (name.isEmpty()) {
203             return new NamingContextEnumeration(bindings.elements(), this, true);
204         }
205         
206         NamingEntry entry = (NamingEntry) bindings.get(name.get(0));
207         
208         if (entry == null) {
209             throw new NameNotFoundException JavaDoc
210                 (sm.getString("namingContext.nameNotBound", name.get(0)));
211         }
212         
213         if (entry.type != NamingEntry.CONTEXT) {
214             throw new NamingException JavaDoc
215                 (sm.getString("namingContext.contextExpected"));
216         }
217         return ((Context JavaDoc) entry.value).listBindings(name.getSuffix(1));
218     }
219
220     /**
221      * Creates and binds a new context. Creates a new context with the given
222      * name and binds it in the target context (that named by all but
223      * terminal atomic component of the name). All intermediate contexts and
224      * the target context must already exist.
225      *
226      * @param name the name of the context to create; may not be empty
227      * @return the newly created context
228      * @exception NameAlreadyBoundException if name is already bound
229      * @exception InvalidAttributesException if creation of the subcontext
230      * requires specification of mandatory attributes
231      * @exception NamingException if a naming exception is encountered
232      */

233     public DirContext JavaDoc createSubcontext(Name JavaDoc name, Attributes JavaDoc attrs)
234         throws NamingException JavaDoc
235     {
236         checkWritable(name);
237         
238         DirContext JavaDoc newContext = new MemoryNamingContext(env);
239         bind(name, newContext);
240         return newContext;
241     }
242
243     // XXX Make it iterative, less objects
244
private NamingEntry findNamingEntry(Name JavaDoc name, boolean resolveLinks)
245         throws NamingException JavaDoc
246     {
247          if (name.isEmpty()) {
248 // // If name is empty, a newly allocated naming context is returned
249
// MemoryNamingContext mmc= new MemoryNamingContext(env);
250
// mmc.setBindings( bindings );
251
// return mmc;
252
return null;
253          }
254         
255         NamingEntry entry = (NamingEntry) bindings.get(name.get(0));
256         
257         if (entry == null) {
258             throw new NameNotFoundException JavaDoc
259                 (sm.getString("namingContext.nameNotBound", name.get(0)));
260         }
261         
262         if (name.size() > 1) {
263             // If the size of the name is greater that 1, then we go through a
264
// number of subcontexts.
265
if (entry.type != NamingEntry.CONTEXT) {
266                 throw new NamingException JavaDoc
267                     (sm.getString("namingContext.contextExpected"));
268             }
269             return entry;
270         } else {
271             return entry;
272         }
273     }
274
275     public Object JavaDoc lookup(Name JavaDoc name, boolean resolveLinks)
276         throws NamingException JavaDoc
277     {
278         // Removing empty parts
279
while ((!name.isEmpty()) && (name.get(0).length() == 0))
280             name = name.getSuffix(1);
281         
282         NamingEntry entry=findNamingEntry( name, resolveLinks );
283
284         if( entry.type == NamingEntry.CONTEXT ) {
285             return ((BaseDirContext) entry.value).lookup(name.getSuffix(1), resolveLinks);
286         }
287         
288         if ((resolveLinks) && (entry.type == NamingEntry.LINK_REF)) {
289             String JavaDoc link = ((LinkRef JavaDoc) entry.value).getLinkName();
290             if (link.startsWith(".")) {
291                 // Link relative to this context
292
return lookup(link.substring(1));
293             } else {
294                 return (new InitialContext JavaDoc(env)).lookup(link);
295             }
296         } else if (entry.type == NamingEntry.REFERENCE) {
297             try {
298                 Object JavaDoc obj = NamingManager.getObjectInstance
299                     (entry.value, name, this, env);
300                 if (obj != null) {
301                     entry.value = obj;
302                     entry.type = NamingEntry.ENTRY;
303                 }
304                 return obj;
305             } catch (NamingException JavaDoc e) {
306                 throw e;
307             } catch (Exception JavaDoc e) {
308                 throw new NamingException JavaDoc(e.getMessage());
309             }
310         } else {
311             return entry.value;
312         }
313     }
314
315     /**
316      * Binds a name to an object. All intermediate contexts and the target
317      * context (that named by all but terminal atomic component of the name)
318      * must already exist.
319      *
320      * @param name the name to bind; may not be empty
321      * @param object the object to bind; possibly null
322      * @param rebind if true, then perform a rebind (ie, overwrite)
323      * @exception NameAlreadyBoundException if name is already bound
324      * @exception InvalidAttributesException if object did not supply all
325      * mandatory attributes
326      * @exception NamingException if a naming exception is encountered
327      */

328     public void bind(Name JavaDoc name, Object JavaDoc obj, Attributes JavaDoc attrs,
329                      boolean rebind)
330         throws NamingException JavaDoc
331     {
332         checkWritable(name);
333         
334     while ((!name.isEmpty()) && (name.get(0).length() == 0))
335         name = name.getSuffix(1);
336
337         if (name.isEmpty())
338             throw new NamingException JavaDoc
339                 (sm.getString("namingContext.invalidName"));
340         
341         NamingEntry entry = (NamingEntry) bindings.get(name.get(0));
342         
343         if (name.size() > 1) {
344             if (entry == null) {
345                 throw new NameNotFoundException JavaDoc
346                     (sm.getString("namingContext.nameNotBound", name.get(0)));
347             }
348             if (entry.type == NamingEntry.CONTEXT) {
349                 if (rebind) {
350                     ((Context JavaDoc) entry.value).rebind(name.getSuffix(1), obj);
351                 } else {
352                     ((Context JavaDoc) entry.value).bind(name.getSuffix(1), obj);
353                 }
354             } else {
355                 throw new NamingException JavaDoc
356                     (sm.getString("namingContext.contextExpected"));
357             }
358         } else {
359             if ((!rebind) && (entry != null)) {
360                 throw new NamingException JavaDoc
361                     (sm.getString("namingContext.alreadyBound", name.get(0)));
362             } else {
363                 // Getting the type of the object and wrapping it within a new
364
// NamingEntry
365
Object JavaDoc toBind =
366                     NamingManager.getStateToBind(obj, name, this, env);
367                 if (toBind instanceof Context JavaDoc) {
368                     entry = new NamingEntry(name.get(0), toBind, attrs,
369                                             NamingEntry.CONTEXT);
370                 } else if (toBind instanceof LinkRef JavaDoc) {
371                     entry = new NamingEntry(name.get(0), toBind, attrs,
372                                             NamingEntry.LINK_REF);
373                 } else if (toBind instanceof Reference JavaDoc) {
374                     entry = new NamingEntry(name.get(0), toBind, attrs,
375                                             NamingEntry.REFERENCE);
376                 } else if (toBind instanceof Referenceable JavaDoc) {
377                     toBind = ((Referenceable JavaDoc) toBind).getReference();
378                     entry = new NamingEntry(name.get(0), toBind, attrs,
379                                             NamingEntry.REFERENCE);
380                 } else {
381                     entry = new NamingEntry(name.get(0), toBind, attrs,
382                                             NamingEntry.ENTRY);
383                 }
384                 bindings.put(name.get(0), entry);
385             }
386         }
387     }
388 }
389
390
Popular Tags