Coverage Report - org.mule.config.spring.jndi.DefaultSpringJndiContext
 
Classes in this File Line Coverage Branch Coverage Complexity
DefaultSpringJndiContext
0%
0/185
0%
0/66
2.078
DefaultSpringJndiContext$1
N/A
N/A
2.078
DefaultSpringJndiContext$AbstractLocalNamingEnumeration
0%
0/6
N/A
2.078
DefaultSpringJndiContext$ListBindingEnumeration
0%
0/4
N/A
2.078
DefaultSpringJndiContext$ListEnumeration
0%
0/4
N/A
2.078
 
 1  
 /*
 2  
  * Copyright (c) MuleSoft, Inc.  All rights reserved.  http://www.mulesoft.com
 3  
  * The software in this package is published under the terms of the CPAL v1.0
 4  
  * license, a copy of which has been included with this distribution in the
 5  
  * LICENSE.txt file.
 6  
  */
 7  
 package org.mule.config.spring.jndi;
 8  
 
 9  
 import java.io.Serializable;
 10  
 import java.util.HashMap;
 11  
 import java.util.Hashtable;
 12  
 import java.util.Iterator;
 13  
 import java.util.Map;
 14  
 
 15  
 import javax.naming.Binding;
 16  
 import javax.naming.CompositeName;
 17  
 import javax.naming.Context;
 18  
 import javax.naming.LinkRef;
 19  
 import javax.naming.Name;
 20  
 import javax.naming.NameClassPair;
 21  
 import javax.naming.NameNotFoundException;
 22  
 import javax.naming.NameParser;
 23  
 import javax.naming.NamingEnumeration;
 24  
 import javax.naming.NamingException;
 25  
 import javax.naming.NotContextException;
 26  
 import javax.naming.OperationNotSupportedException;
 27  
 import javax.naming.Reference;
 28  
 import javax.naming.spi.NamingManager;
 29  
 /**
 30  
  * TODO
 31  
  */
 32  
 
 33  
 /**
 34  
  * A simple spring based JNDI context which is mutable
 35  
  * <p/>
 36  
  * Borrowed from the XBean (xbean.codehaus.org) project. Thanks guys!
 37  
  */
 38  
 public class DefaultSpringJndiContext implements Context, Serializable
 39  
 {
 40  
 
 41  
     private static final long serialVersionUID = -5754338187296859149L;
 42  0
     protected static final NameParser nameParser = new DefaultNameParser();
 43  
 
 44  0
     private boolean freeze = false;
 45  
 
 46  
     protected final Hashtable environment;        // environment for this context
 47  
     protected final Map bindings;         // bindings at my level
 48  
     protected final Map treeBindings;     // all bindings under me
 49  
 
 50  0
     private boolean frozen = false;
 51  0
     private String nameInNamespace = "";
 52  
     public static final String SEPARATOR = "/";
 53  
 
 54  
     public DefaultSpringJndiContext()
 55  0
     {
 56  0
         environment = new Hashtable();
 57  0
         bindings = new HashMap();
 58  0
         treeBindings = new HashMap();
 59  0
     }
 60  
 
 61  
     public DefaultSpringJndiContext(Hashtable env)
 62  0
     {
 63  0
         if (env == null)
 64  
         {
 65  0
             this.environment = new Hashtable();
 66  
         }
 67  
         else
 68  
         {
 69  0
             this.environment = new Hashtable(env);
 70  
         }
 71  0
         this.bindings = new HashMap();
 72  0
         this.treeBindings = new HashMap();
 73  0
     }
 74  
 
 75  
     public DefaultSpringJndiContext(Hashtable environment, Map bindings)
 76  0
     {
 77  0
         if (environment == null)
 78  
         {
 79  0
             this.environment = new Hashtable();
 80  
         }
 81  
         else
 82  
         {
 83  0
             this.environment = new Hashtable(environment);
 84  
         }
 85  0
         this.bindings = bindings;
 86  0
         treeBindings = new HashMap();
 87  0
         frozen = true;
 88  0
     }
 89  
 
 90  
     public DefaultSpringJndiContext(Hashtable environment, Map bindings, String nameInNamespace)
 91  
     {
 92  0
         this(environment, bindings);
 93  0
         this.nameInNamespace = nameInNamespace;
 94  0
     }
 95  
 
 96  
     protected DefaultSpringJndiContext(DefaultSpringJndiContext clone, Hashtable env)
 97  0
     {
 98  0
         this.bindings = clone.bindings;
 99  0
         this.treeBindings = clone.treeBindings;
 100  0
         this.environment = new Hashtable(env);
 101  0
     }
 102  
 
 103  
     protected DefaultSpringJndiContext(DefaultSpringJndiContext clone, Hashtable env, String nameInNamespace)
 104  
     {
 105  0
         this(clone, env);
 106  0
         this.nameInNamespace = nameInNamespace;
 107  0
     }
 108  
 
 109  
     public Object addToEnvironment(String propName, Object propVal) throws NamingException
 110  
     {
 111  0
         return environment.put(propName, propVal);
 112  
     }
 113  
 
 114  
     public Hashtable getEnvironment() throws NamingException
 115  
     {
 116  0
         return (Hashtable) environment.clone();
 117  
     }
 118  
 
 119  
     public Object removeFromEnvironment(String propName) throws NamingException
 120  
     {
 121  0
         return environment.remove(propName);
 122  
     }
 123  
 
 124  
     public Object lookup(String name) throws NamingException
 125  
     {
 126  0
         if (name.length() == 0)
 127  
         {
 128  0
             return this;
 129  
         }
 130  0
         Object result = treeBindings.get(name);
 131  0
         if (result == null)
 132  
         {
 133  0
             result = bindings.get(name);
 134  
         }
 135  0
         if (result == null)
 136  
         {
 137  0
             int pos = name.indexOf(':');
 138  0
             if (pos > 0)
 139  
             {
 140  0
                 String scheme = name.substring(0, pos);
 141  0
                 Context ctx = NamingManager.getURLContext(scheme, environment);
 142  0
                 if (ctx == null)
 143  
                 {
 144  0
                     throw new NamingException("scheme " + scheme + " not recognized");
 145  
                 }
 146  0
                 return ctx.lookup(name);
 147  
             }
 148  
             else
 149  
             {
 150  
                 // Split out the first name of the path
 151  
                 // and look for it in the bindings map.
 152  0
                 CompositeName path = new CompositeName(name);
 153  
 
 154  0
                 if (path.size() == 0)
 155  
                 {
 156  0
                     return this;
 157  
                 }
 158  
                 else
 159  
                 {
 160  0
                     String first = path.get(0);
 161  0
                     Object obj = bindings.get(first);
 162  0
                     if (obj == null)
 163  
                     {
 164  0
                         throw new NameNotFoundException(name);
 165  
                     }
 166  0
                     else if (obj instanceof Context && path.size() > 1)
 167  
                     {
 168  0
                         Context subContext = (Context) obj;
 169  0
                         obj = subContext.lookup(path.getSuffix(1));
 170  
                     }
 171  0
                     return obj;
 172  
                 }
 173  
             }
 174  
         }
 175  0
         if (result instanceof LinkRef)
 176  
         {
 177  0
             LinkRef ref = (LinkRef) result;
 178  0
             result = lookup(ref.getLinkName());
 179  
         }
 180  0
         if (result instanceof Reference)
 181  
         {
 182  
             try
 183  
             {
 184  0
                 result = NamingManager.getObjectInstance(result, null, null, this.environment);
 185  
             }
 186  0
             catch (NamingException e)
 187  
             {
 188  0
                 throw e;
 189  
             }
 190  0
             catch (Exception e)
 191  
             {
 192  0
                 throw (NamingException) new NamingException("could not look up : " + name).initCause(e);
 193  0
             }
 194  
         }
 195  0
         if (result instanceof DefaultSpringJndiContext)
 196  
         {
 197  0
             String prefix = getNameInNamespace();
 198  0
             if (prefix.length() > 0)
 199  
             {
 200  0
                 prefix = prefix + SEPARATOR;
 201  
             }
 202  0
             result = new DefaultSpringJndiContext((DefaultSpringJndiContext) result, environment, prefix + name);
 203  
         }
 204  0
         return result;
 205  
     }
 206  
 
 207  
     public Object lookup(Name name) throws NamingException
 208  
     {
 209  0
         return lookup(name.toString());
 210  
     }
 211  
 
 212  
     public Object lookupLink(String name) throws NamingException
 213  
     {
 214  0
         return lookup(name);
 215  
     }
 216  
 
 217  
     public Name composeName(Name name, Name prefix) throws NamingException
 218  
     {
 219  0
         Name result = (Name) prefix.clone();
 220  0
         result.addAll(name);
 221  0
         return result;
 222  
     }
 223  
 
 224  
     public String composeName(String name, String prefix) throws NamingException
 225  
     {
 226  0
         CompositeName result = new CompositeName(prefix);
 227  0
         result.addAll(new CompositeName(name));
 228  0
         return result.toString();
 229  
     }
 230  
 
 231  
     public NamingEnumeration list(String name) throws NamingException
 232  
     {
 233  0
         Object o = lookup(name);
 234  0
         if (o == this)
 235  
         {
 236  0
             return new DefaultSpringJndiContext.ListEnumeration();
 237  
         }
 238  0
         else if (o instanceof Context)
 239  
         {
 240  0
             return ((Context) o).list("");
 241  
         }
 242  
         else
 243  
         {
 244  0
             throw new NotContextException();
 245  
         }
 246  
     }
 247  
 
 248  
     public NamingEnumeration listBindings(String name) throws NamingException
 249  
     {
 250  0
         Object o = lookup(name);
 251  0
         if (o == this)
 252  
         {
 253  0
             return new DefaultSpringJndiContext.ListBindingEnumeration();
 254  
         }
 255  0
         else if (o instanceof Context)
 256  
         {
 257  0
             return ((Context) o).listBindings("");
 258  
         }
 259  
         else
 260  
         {
 261  0
             throw new NotContextException();
 262  
         }
 263  
     }
 264  
 
 265  
     public Object lookupLink(Name name) throws NamingException
 266  
     {
 267  0
         return lookupLink(name.toString());
 268  
     }
 269  
 
 270  
     public NamingEnumeration list(Name name) throws NamingException
 271  
     {
 272  0
         return list(name.toString());
 273  
     }
 274  
 
 275  
     public NamingEnumeration listBindings(Name name) throws NamingException
 276  
     {
 277  0
         return listBindings(name.toString());
 278  
     }
 279  
 
 280  
     public void bind(Name name, Object value) throws NamingException
 281  
     {
 282  0
         bind(name.toString(), value);
 283  0
     }
 284  
 
 285  
     public void bind(String name, Object value) throws NamingException
 286  
     {
 287  0
         checkFrozen();
 288  0
         internalBind(name, value);
 289  0
     }
 290  
 
 291  
     public void close() throws NamingException
 292  
     {
 293  
         // ignore
 294  0
     }
 295  
 
 296  
     public Context createSubcontext(Name name) throws NamingException
 297  
     {
 298  0
         throw new OperationNotSupportedException();
 299  
     }
 300  
 
 301  
     public Context createSubcontext(String name) throws NamingException
 302  
     {
 303  0
         throw new OperationNotSupportedException();
 304  
     }
 305  
 
 306  
     public void destroySubcontext(Name name) throws NamingException
 307  
     {
 308  0
         throw new OperationNotSupportedException();
 309  
     }
 310  
 
 311  
     public void destroySubcontext(String name) throws NamingException
 312  
     {
 313  0
         throw new OperationNotSupportedException();
 314  
     }
 315  
 
 316  
     public String getNameInNamespace() throws NamingException
 317  
     {
 318  0
         return nameInNamespace;
 319  
     }
 320  
 
 321  
     public NameParser getNameParser(Name name) throws NamingException
 322  
     {
 323  0
         return nameParser;
 324  
     }
 325  
 
 326  
     public NameParser getNameParser(String name) throws NamingException
 327  
     {
 328  0
         return nameParser;
 329  
     }
 330  
 
 331  
     public void rebind(Name name, Object value) throws NamingException
 332  
     {
 333  0
         rebind(name.toString(), value);
 334  0
     }
 335  
 
 336  
     public void rebind(String name, Object value) throws NamingException
 337  
     {
 338  0
         checkFrozen();
 339  0
         internalBind(name, value, true);
 340  0
     }
 341  
 
 342  
     public void rename(Name oldName, Name newName) throws NamingException
 343  
     {
 344  0
         checkFrozen();
 345  0
         Object value = lookup(oldName);
 346  0
         unbind(oldName);
 347  0
         bind(newName, value);
 348  0
     }
 349  
 
 350  
     public void rename(String oldName, String newName) throws NamingException
 351  
     {
 352  0
         Object value = lookup(oldName);
 353  0
         unbind(oldName);
 354  0
         bind(newName, value);
 355  0
     }
 356  
 
 357  
     public void unbind(Name name) throws NamingException
 358  
     {
 359  0
         unbind(name.toString());
 360  0
     }
 361  
 
 362  
     public void unbind(String name) throws NamingException
 363  
     {
 364  0
         checkFrozen();
 365  0
         internalBind(name, null, true);
 366  0
     }
 367  
 
 368  0
     private abstract class AbstractLocalNamingEnumeration implements NamingEnumeration
 369  
     {
 370  
 
 371  0
         private Iterator i = bindings.entrySet().iterator();
 372  
 
 373  
         public boolean hasMore() throws NamingException
 374  
         {
 375  0
             return i.hasNext();
 376  
         }
 377  
 
 378  
         public boolean hasMoreElements()
 379  
         {
 380  0
             return i.hasNext();
 381  
         }
 382  
 
 383  
         protected Map.Entry getNext()
 384  
         {
 385  0
             return (Map.Entry) i.next();
 386  
         }
 387  
 
 388  
         public void close() throws NamingException
 389  
         {
 390  0
         }
 391  
     }
 392  
 
 393  0
     private class ListEnumeration extends AbstractLocalNamingEnumeration
 394  
     {
 395  
 
 396  
         public Object next() throws NamingException
 397  
         {
 398  0
             return nextElement();
 399  
         }
 400  
 
 401  
         public Object nextElement()
 402  
         {
 403  0
             Map.Entry entry = getNext();
 404  0
             return new NameClassPair((String) entry.getKey(), entry.getValue().getClass().getName());
 405  
         }
 406  
     }
 407  
 
 408  0
     private class ListBindingEnumeration extends AbstractLocalNamingEnumeration
 409  
     {
 410  
 
 411  
         public Object next() throws NamingException
 412  
         {
 413  0
             return nextElement();
 414  
         }
 415  
 
 416  
         public Object nextElement()
 417  
         {
 418  0
             Map.Entry entry = getNext();
 419  0
             return new Binding((String) entry.getKey(), entry.getValue());
 420  
         }
 421  
     }
 422  
 
 423  
     public Map getEntries()
 424  
     {
 425  0
         return new HashMap(bindings);
 426  
     }
 427  
 
 428  
     public void setEntries(Map entries) throws NamingException
 429  
     {
 430  0
         if (entries != null)
 431  
         {
 432  0
             for (Iterator iter = entries.entrySet().iterator(); iter.hasNext();)
 433  
             {
 434  0
                 Map.Entry entry = (Map.Entry) iter.next();
 435  0
                 String name = (String) entry.getKey();
 436  0
                 Object value = entry.getValue();
 437  0
                 internalBind(name, value);
 438  0
             }
 439  
         }
 440  0
     }
 441  
 
 442  
     public boolean isFreeze()
 443  
     {
 444  0
         return freeze;
 445  
     }
 446  
 
 447  
     public void setFreeze(boolean freeze)
 448  
     {
 449  0
         this.freeze = freeze;
 450  0
     }
 451  
 
 452  
     /**
 453  
      * internalBind is intended for use only during setup or possibly by suitably synchronized superclasses.
 454  
      * It binds every possible lookup into a map in each context.  To do this, each context
 455  
      * strips off one name segment and if necessary creates a new context for it. Then it asks that context
 456  
      * to bind the remaining name.  It returns a map containing all the bindings from the next context, plus
 457  
      * the context it just created (if it in fact created it). (the names are suitably extended by the segment
 458  
      * originally lopped off).
 459  
      *
 460  
      * @param name
 461  
      * @param value
 462  
      * @throws javax.naming.NamingException
 463  
      */
 464  
     protected Map internalBind(String name, Object value) throws NamingException
 465  
     {
 466  0
         return internalBind(name, value, false);
 467  
 
 468  
     }
 469  
 
 470  
     protected Map internalBind(String name, Object value, boolean allowRebind) throws NamingException
 471  
     {
 472  0
         if (name == null || name.length() == 0)
 473  
         {
 474  0
             throw new NamingException("Invalid Name " + name);
 475  
         }
 476  0
         if (frozen)
 477  
         {
 478  0
             throw new NamingException("Read only");
 479  
         }
 480  
 
 481  0
         Map newBindings = new HashMap();
 482  0
         int pos = name.indexOf('/');
 483  0
         if (pos == -1)
 484  
         {
 485  0
             Object oldValue = treeBindings.put(name, value);
 486  0
             if (!allowRebind && oldValue != null)
 487  
             {
 488  0
                 throw new NamingException("Something already bound at " + name);
 489  
             }
 490  0
             bindings.put(name, value);
 491  0
             newBindings.put(name, value);
 492  0
         }
 493  
         else
 494  
         {
 495  0
             String segment = name.substring(0, pos);
 496  
 
 497  0
             if (segment == null || segment.length() == 0)
 498  
             {
 499  0
                 throw new NamingException("Invalid segment " + segment);
 500  
             }
 501  0
             Object o = treeBindings.get(segment);
 502  0
             if (o == null)
 503  
             {
 504  0
                 o = newContext();
 505  0
                 treeBindings.put(segment, o);
 506  0
                 bindings.put(segment, o);
 507  0
                 newBindings.put(segment, o);
 508  
             }
 509  0
             else if (!(o instanceof DefaultSpringJndiContext))
 510  
             {
 511  0
                 throw new NamingException("Something already bound where a subcontext should go");
 512  
             }
 513  0
             DefaultSpringJndiContext defaultContext = (DefaultSpringJndiContext) o;
 514  0
             String remainder = name.substring(pos + 1);
 515  0
             Map subBindings = defaultContext.internalBind(remainder, value, allowRebind);
 516  0
             for (Iterator iterator = subBindings.entrySet().iterator(); iterator.hasNext();)
 517  
             {
 518  0
                 Map.Entry entry = (Map.Entry) iterator.next();
 519  0
                 String subName = segment + "/" + (String) entry.getKey();
 520  0
                 Object bound = entry.getValue();
 521  0
                 treeBindings.put(subName, bound);
 522  0
                 newBindings.put(subName, bound);
 523  0
             }
 524  
         }
 525  0
         return newBindings;
 526  
     }
 527  
 
 528  
     protected void checkFrozen() throws OperationNotSupportedException
 529  
     {
 530  0
         if (isFreeze())
 531  
         {
 532  0
             throw new OperationNotSupportedException("JNDI context is frozen!");
 533  
         }
 534  0
     }
 535  
 
 536  
     protected DefaultSpringJndiContext newContext()
 537  
     {
 538  0
         return new DefaultSpringJndiContext();
 539  
     }
 540  
 
 541  
 }
 542