View Javadoc

1   /*
2    * $Id: ObjectGetOrCreateRule.java 7976 2007-08-21 14:26:13Z dirk.olmes $
3    * --------------------------------------------------------------------------------------
4    * Copyright (c) MuleSource, Inc.  All rights reserved.  http://www.mulesource.com
5    *
6    * The software in this package is published under the terms of the CPAL v1.0
7    * license, a copy of which has been included with this distribution in the
8    * LICENSE.txt file.
9    */
10  
11  package org.mule.config.builders;
12  
13  import org.mule.config.ConfigurationException;
14  import org.mule.config.builders.i18n.BuildersMessages;
15  import org.mule.config.i18n.CoreMessages;
16  import org.mule.impl.container.ContainerKeyPair;
17  import org.mule.umo.manager.UMOContainerContext;
18  
19  import java.lang.reflect.InvocationTargetException;
20  
21  import org.apache.commons.beanutils.MethodUtils;
22  import org.apache.commons.digester.ObjectCreateRule;
23  import org.xml.sax.Attributes;
24  
25  /**
26   * A digester rule that will either create an object of look it up from a container.
27   */
28  public class ObjectGetOrCreateRule extends ObjectCreateRule
29  {
30      public static final String DEFAULT_REF_ATTRIBUTE = "ref";
31      public static final String DEFAULT_CLASSNAME_ATTRIBUTE = "className";
32      protected String refAttrib = DEFAULT_REF_ATTRIBUTE;
33      protected String classAttrib = DEFAULT_CLASSNAME_ATTRIBUTE;
34      protected boolean classRefRequired = false;
35      protected String containerMethodName;
36      protected UMOContainerContext context;
37      protected String containerAttrib;
38  
39      public ObjectGetOrCreateRule(String defaultImpl, String className, String containerMethodName)
40      {
41          this(defaultImpl, className, DEFAULT_REF_ATTRIBUTE, false, containerMethodName);
42      }
43  
44      public ObjectGetOrCreateRule(String defaultImpl,
45                                   String className,
46                                   boolean classRefRequired,
47                                   String containerMethodName)
48      {
49          this(defaultImpl, className, DEFAULT_REF_ATTRIBUTE, classRefRequired, containerMethodName);
50      }
51  
52      public ObjectGetOrCreateRule(String defaultImpl,
53                                   String className,
54                                   String refAttrib,
55                                   boolean classRefRequired,
56                                   String containerMethodName)
57      {
58          super(defaultImpl, className);
59          this.refAttrib = refAttrib;
60          this.classRefRequired = classRefRequired;
61          this.containerMethodName = containerMethodName;
62      }
63  
64      public ObjectGetOrCreateRule(String defaultImpl,
65                                   String className,
66                                   String refAttrib,
67                                   String classAttrib,
68                                   boolean classRefRequired,
69                                   String containerMethodName)
70      {
71          super(defaultImpl, className);
72          this.refAttrib = refAttrib;
73          this.classRefRequired = classRefRequired;
74          this.containerMethodName = containerMethodName;
75          this.classAttrib = classAttrib;
76      }
77  
78      public ObjectGetOrCreateRule(String defaultImpl,
79                                   String className,
80                                   String refAttrib,
81                                   String containerAttrib,
82                                   String classAttrib,
83                                   boolean classRefRequired,
84                                   String containerMethodName)
85      {
86          super(defaultImpl, className);
87          this.refAttrib = refAttrib;
88          this.containerAttrib = containerAttrib;
89          this.classRefRequired = classRefRequired;
90          this.containerMethodName = containerMethodName;
91          this.classAttrib = classAttrib;
92      }
93  
94      /**
95       * This method is deprecated in the Digester API however the API still uses it
96       * and we must overload it in order to customse the ObjectCreateRuleBehaviour
97       * 
98       * @param attributes
99       * @throws Exception
100      */
101     public void begin(Attributes attributes) throws Exception
102     {
103 
104         String ref = attributes.getValue(refAttrib);
105         String container = null;
106         if (containerAttrib != null)
107         {
108             container = attributes.getValue(containerAttrib);
109         }
110         if (ref != null)
111         {
112             Object cRef = ref;
113             if (container != null)
114             {
115                 cRef = new ContainerKeyPair(container, ref);
116             }
117             Object obj = getContainer().getComponent(cRef);
118             digester.push(obj);
119         }
120         else
121         {
122             String classRef = attributes.getValue(classAttrib);
123             if (classRef == null && classRefRequired)
124             {
125                 throw new ConfigurationException(
126                     BuildersMessages.mustSpecifyContainerRefOrClassAttribute(refAttrib, classAttrib,
127                         this.digester.getCurrentElementName()));
128             }
129             else
130             {
131                 super.begin(attributes);
132             }
133         }
134     }
135 
136     protected UMOContainerContext getContainer()
137         throws NoSuchMethodException, IllegalAccessException, InvocationTargetException
138     {
139         if (context == null)
140         {
141             Object root = digester.getRoot();
142             context = (UMOContainerContext)MethodUtils.invokeMethod(root, containerMethodName, null);
143             if (context == null)
144             {
145                 throw new IllegalArgumentException(CoreMessages.objectIsNull("Container context").toString());
146             }
147         }
148         return context;
149     }
150 }