View Javadoc

1   /*
2    * $Id: GuiceRegistry.java 20321 2010-11-24 15:21:24Z dfeist $
3    * --------------------------------------------------------------------------------------
4    * Copyright (c) MuleSoft, Inc.  All rights reserved.  http://www.mulesoft.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  package org.mule.module.guice;
11  
12  import org.mule.api.MuleContext;
13  import org.mule.api.lifecycle.InitialisationException;
14  import org.mule.api.registry.RegistrationException;
15  import org.mule.config.i18n.MessageFactory;
16  import org.mule.registry.AbstractRegistry;
17  
18  import com.google.inject.Binding;
19  import com.google.inject.Injector;
20  import com.google.inject.Key;
21  import com.google.inject.TypeLiteral;
22  import com.google.inject.name.Named;
23  
24  import java.util.Collection;
25  import java.util.Collections;
26  import java.util.List;
27  import java.util.Map;
28  
29  import org.guiceyfruit.Injectors;
30  import org.guiceyfruit.support.CloseFailedException;
31  
32  /**
33   * The internal Mule interface for retreiving objects from a Guice injector.  This registry is read-only since all
34   * objects should be configured by {@link com.google.inject.Module} objects.  The lifecycle of objects will be
35   * managed by Mule since Guice does not provide lifecycle support.
36   * <p/>
37   * To create modules extend the {@link org.mule.module.guice.AbstractMuleGuiceModule} since it provides hooks and helpers for
38   * working with Mule configuration.  Any modules independent of Mule can just extend the Guice {@link com.google.inject.AbstractModule}
39   * as normal.
40   * <p/>
41   * Mule will discover modules on the classpath, if you need to configure a module before passing it to the Guice injector you
42   * need to implement a {@link org.mule.module.guice.GuiceModuleFactory} for your module.
43   *
44   * @see org.mule.module.guice.AbstractMuleGuiceModule
45   * @see org.mule.module.guice.GuiceModuleFactory
46   */
47  public class GuiceRegistry extends AbstractRegistry
48  {
49      private Injector injector = null;
50  
51      public GuiceRegistry(MuleContext muleContext)
52      {
53          super("guice", muleContext);
54      }
55  
56  
57      GuiceRegistry(Injector injector, MuleContext muleContext)
58      {
59          this(muleContext);
60          this.injector = injector;
61      }
62  
63      protected void doInitialise() throws InitialisationException
64      {
65          //do nothing
66      }
67  
68      protected void doDispose()
69      {
70          try
71          {
72              Injectors.close(injector);
73          }
74          catch (CloseFailedException e)
75          {
76              logger.error("Failed to close the Guice registry cleanly", e);
77          }
78      }
79  
80      public <T> T lookupObject(String key)
81      {
82          //Guice isn't really supposed to work this way but in Mule we need to look up objects by name only sometimes
83          for (Map.Entry<Key<?>, Binding<?>> entry : injector.getBindings().entrySet())
84          {
85              if (entry.getKey().getAnnotation() instanceof Named)
86              {
87                  String name = ((Named) entry.getKey().getAnnotation()).value();
88                  if (name.equals(key))
89                  {
90                      Object o = entry.getValue().getProvider().get();
91                      return (T) o;
92                  }
93              }
94          }
95          return null;
96      }
97  
98      @Override
99      public <T> T lookupObject(Class<T> type) throws RegistrationException
100     {
101         //We have to loop through all objects since Guice will act as a factory and create a binding for the given class
102         //if one is not bound in the registry.
103         List<Binding<T>> bindings = injector.findBindingsByType(TypeLiteral.get(type));
104         if(bindings.size()==0)
105         {
106             return null;
107 
108         }
109         else if (bindings.size()==1)
110         {
111             return bindings.get(0).getProvider().get();
112         }
113         else
114         {
115             throw new RegistrationException(MessageFactory.createStaticMessage("More than one object of type: " + type + ", was found"));
116         }
117     }
118 
119     public <T> Map<String, T> lookupByType(Class<T> type)
120     {
121 
122 
123         return Collections.EMPTY_MAP;
124 //        try
125 //        {
126 //            List<Binding<T>> bindings = injector.findBindingsByType(TypeLiteral.get(type));
127 //            if(bindings!=null && bindings.size()>0)
128 //            {
129 //                Map<String, T> map = new HashMap<String, T>(bindings.size());
130 //                String name;
131 //                T object;
132 //                for (Binding<T> binding : bindings)
133 //                {
134 //                    object = binding.getProvider().get();
135 //
136 //                    if(binding.getKey().getAnnotation() instanceof Named)
137 //                    {
138 //                        name = ((Named)binding.getKey().getAnnotation()).value();
139 //                    }
140 //                    else if(object instanceof NamedObject)
141 //                    {
142 //                        name = ((NamedObject)object).getName();
143 //                    }
144 //                    else
145 //                    {
146 //                        name = "_" + object.hashCode();
147 //                    }
148 //                    map.put(name, object);
149 //                }
150 //                return map;
151 //            }
152 //            return Collections.emptyMap();
153 //        }
154 //        catch (ConfigurationException e)
155 //        {
156 //            return Collections.emptyMap();
157 //        }
158     }
159 
160     public <T> Collection<T> lookupObjects(Class<T> type)
161     {
162         return Collections.emptyList();
163 
164 //        try
165 //        {
166 //            List<Binding<T>> bindings = injector.findBindingsByType(TypeLiteral.get(type));
167 //            if(bindings!=null && bindings.size()>0)
168 //            {
169 //                List<T> list = new ArrayList<T>(bindings.size());
170 //                for (Binding<T> binding : bindings)
171 //                {
172 //                    list.add(binding.getProvider().get());
173 //                }
174 //                return list;
175 //            }
176 //            return Collections.emptyList();
177 //        }
178 //        catch (ConfigurationException e)
179 //        {
180 //            return Collections.emptyList();
181 //        }
182     }
183 
184     public void registerObject(String key, Object value) throws RegistrationException
185     {
186         throw new UnsupportedOperationException("registerObject");
187     }
188 
189     public void registerObject(String key, Object value, Object metadata) throws RegistrationException
190     {
191         throw new UnsupportedOperationException("registerObject");
192     }
193 
194     public void registerObjects(Map objects) throws RegistrationException
195     {
196         throw new UnsupportedOperationException("registerObjects");
197     }
198 
199     public void unregisterObject(String key) throws RegistrationException
200     {
201         throw new UnsupportedOperationException("unregisterObject");
202     }
203 
204     public void unregisterObject(String key, Object metadata) throws RegistrationException
205     {
206         throw new UnsupportedOperationException("unregisterObject");
207     }
208 
209     public boolean isReadOnly()
210     {
211         return true;
212     }
213 
214     public boolean isRemote()
215     {
216         return false;
217     }
218 }