View Javadoc

1   /****************************************************************
2    * Licensed to the Apache Software Foundation (ASF) under one   *
3    * or more contributor license agreements.  See the NOTICE file *
4    * distributed with this work for additional information        *
5    * regarding copyright ownership.  The ASF licenses this file   *
6    * to you under the Apache License, Version 2.0 (the            *
7    * "License"); you may not use this file except in compliance   *
8    * with the License.  You may obtain a copy of the License at   *
9    *                                                              *
10   *   http://www.apache.org/licenses/LICENSE-2.0                 *
11   *                                                              *
12   * Unless required by applicable law or agreed to in writing,   *
13   * software distributed under the License is distributed on an  *
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY       *
15   * KIND, either express or implied.  See the License for the    *
16   * specific language governing permissions and limitations      *
17   * under the License.                                           *
18   ****************************************************************/
19  
20  package org.apache.james.phoenix;
21  
22  import java.lang.reflect.InvocationTargetException;
23  import java.lang.reflect.Method;
24  import java.util.HashMap;
25  import java.util.Map;
26  
27  import javax.annotation.PostConstruct;
28  import javax.annotation.Resource;
29  
30  import org.apache.avalon.framework.logger.LogEnabled;
31  import org.apache.avalon.framework.logger.Logger;
32  import org.apache.avalon.phoenix.ApplicationEvent;
33  import org.apache.avalon.phoenix.ApplicationListener;
34  import org.apache.avalon.phoenix.BlockEvent;
35  import org.apache.james.api.kernel.ServiceLocator;
36  
37  public class PhoenixLoader implements ServiceLocator, ApplicationListener, LogEnabled {
38  
39      private Logger logger;
40      
41      private final Map<String, Object> resources;
42  
43      public PhoenixLoader() {
44          resources = new HashMap<String, Object>();
45          resources.put("org.apache.james.ServiceLocator", this);
46      }
47      
48      public Object get(String name) {
49          return resources.get(name);
50      }
51  
52      public void applicationFailure(Exception exception) {
53          
54      }
55  
56      /**
57       * Indicates application has started.
58       * This hook initialises all annotated resources.
59       * This ensure that all services have been loaded 
60       * before initilisation any.
61       */
62      public void applicationStarted() {
63          for (Object resource : resources.values()) {
64              Method[] methods = resource.getClass().getMethods();
65              for (Method method : methods) {
66                  Resource resourceAnnotation = method.getAnnotation(Resource.class);
67                  if (resourceAnnotation != null) {
68                      final String name = resourceAnnotation.name();
69                      final Object service = get(name);
70                      if (resource == null) {
71                          if (logger.isWarnEnabled()) {
72                              logger.warn("Unknown service: "  + name);
73                          }
74                     } else {
75                          try {
76                              Object[] args = {service};
77                              method.invoke(resource, args);
78                          } catch (IllegalAccessException e) {
79                              throw new RuntimeException("Injection failed", e);
80                          } catch (IllegalArgumentException e) {
81                              throw new RuntimeException("Injection failed", e);
82                          } catch (InvocationTargetException e) {
83                              throw new RuntimeException("Injection failed", e);
84                          }
85                      }
86                  }
87              }
88          }
89          
90          try {
91              for (Object object : resources.values()) {
92                  Method[] methods = object.getClass().getMethods();
93                  for (Method method : methods) {
94                      PostConstruct postConstructAnnotation = method.getAnnotation(PostConstruct.class);
95                      if (postConstructAnnotation != null) {
96                          Object[] args = {};
97                          method.invoke(object, args);
98                      }
99                  }
100             }
101         } catch (Exception e) {
102             throw new RuntimeException("Initialisation failed", e);
103         }
104     }
105 
106     public void applicationStarting(ApplicationEvent event) throws Exception {
107         
108     }
109 
110     public void applicationStopped() {
111         
112     }
113 
114     public void applicationStopping() {
115         
116     }
117 
118     /**
119      * Adds service.
120      */
121     public void blockAdded(BlockEvent event) {
122         final Object resource = event.getObject();
123         final String name = event.getName();
124         resources.put(name, resource);
125     }
126 
127     /**
128      * Removes service.
129      * Existing references are maintained.
130      */
131     public void blockRemoved(BlockEvent event) {
132         final String name = event.getName();
133         resources.remove(name);
134     }
135 
136     public void enableLogging(Logger logger) {
137         this.logger = logger;
138     }
139 }