001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one
003: * or more contributor license agreements. See the NOTICE file
004: * distributed with this work for additional information
005: * regarding copyright ownership. The ASF licenses this file
006: * to you under the Apache License, Version 2.0 (the
007: * "License"); you may not use this file except in compliance
008: * with the License. You may obtain a copy of the License at
009: *
010: * http://www.apache.org/licenses/LICENSE-2.0
011: *
012: * Unless required by applicable law or agreed to in writing,
013: * software distributed under the License is distributed on an
014: * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015: * KIND, either express or implied. See the License for the
016: * specific language governing permissions and limitations
017: * under the License.
018: */
019:
020: package org.apache.geronimo.naming.deployment;
021:
022: import java.lang.reflect.Method;
023: import java.util.HashMap;
024: import java.util.List;
025: import java.util.Map;
026:
027: import javax.annotation.PostConstruct;
028: import javax.annotation.PreDestroy;
029:
030: import org.apache.geronimo.common.DeploymentException;
031: import org.apache.geronimo.gbean.GBeanInfo;
032: import org.apache.geronimo.gbean.GBeanInfoBuilder;
033: import org.apache.geronimo.j2ee.annotation.Holder;
034: import org.apache.geronimo.j2ee.annotation.LifecycleMethod;
035: import org.apache.geronimo.j2ee.deployment.Module;
036: import org.apache.geronimo.j2ee.deployment.NamingBuilder;
037: import org.apache.geronimo.j2ee.deployment.annotation.AnnotatedApp;
038: import org.apache.geronimo.j2ee.j2eeobjectnames.NameFactory;
039: import org.apache.geronimo.kernel.config.ConfigurationModuleType;
040: import org.apache.geronimo.xbeans.javaee.FullyQualifiedClassType;
041: import org.apache.geronimo.xbeans.javaee.JavaIdentifierType;
042: import org.apache.geronimo.xbeans.javaee.LifecycleCallbackType;
043: import org.apache.xbean.finder.ClassFinder;
044: import org.apache.xmlbeans.QNameSet;
045: import org.apache.xmlbeans.XmlObject;
046:
047: /**
048: * @version $Rev: 541492 $ $Date: 2007-05-24 17:09:32 -0700 (Thu, 24 May 2007) $
049: */
050: public class LifecycleMethodBuilder extends AbstractNamingBuilder {
051: public void buildNaming(XmlObject specDD, XmlObject plan,
052: Module module, Map componentContext)
053: throws DeploymentException {
054: // skip ejb modules... they have alreayd been processed
055: if (module.getType() == ConfigurationModuleType.EJB) {
056: return;
057: }
058:
059: ClassFinder classFinder = module.getClassFinder();
060: AnnotatedApp annotatedApp = module.getAnnotatedApp();
061: if (annotatedApp == null) {
062: throw new NullPointerException("No AnnotatedApp supplied");
063: }
064: Map<String, LifecycleCallbackType> postConstructMap = mapLifecycleCallbacks(
065: annotatedApp.getPostConstructArray(), annotatedApp
066: .getComponentType());
067: Map<String, LifecycleCallbackType> preDestroyMap = mapLifecycleCallbacks(
068: annotatedApp.getPreDestroyArray(), annotatedApp
069: .getComponentType());
070: if (module.getClassFinder() != null) {
071: List<Method> postConstructs = classFinder
072: .findAnnotatedMethods(PostConstruct.class);
073: for (Method m : postConstructs) {
074: String methodName = m.getName();
075: String className = m.getDeclaringClass().getName();
076: if (!postConstructMap.containsKey(className)) {
077: LifecycleCallbackType callback = annotatedApp
078: .addPostConstruct();
079: FullyQualifiedClassType classType = callback
080: .addNewLifecycleCallbackClass();
081: classType.setStringValue(className);
082: JavaIdentifierType method = callback
083: .addNewLifecycleCallbackMethod();
084: method.setStringValue(methodName);
085: postConstructMap.put(className, callback);
086: }
087: }
088: List<Method> preDestroys = classFinder
089: .findAnnotatedMethods(PreDestroy.class);
090: for (Method m : preDestroys) {
091: String methodName = m.getName();
092: String className = m.getDeclaringClass().getName();
093: if (!preDestroyMap.containsKey(className)) {
094: LifecycleCallbackType callback = annotatedApp
095: .addPreDestroy();
096: FullyQualifiedClassType classType = callback
097: .addNewLifecycleCallbackClass();
098: classType.setStringValue(className);
099: JavaIdentifierType method = callback
100: .addNewLifecycleCallbackMethod();
101: method.setStringValue(methodName);
102: preDestroyMap.put(className, callback);
103: }
104: }
105: }
106: Map<String, LifecycleMethod> postConstructs = map(postConstructMap);
107: Map<String, LifecycleMethod> preDestroys = map(preDestroyMap);
108: Holder holder = NamingBuilder.INJECTION_KEY
109: .get(componentContext);
110: holder.addPostConstructs(postConstructs);
111: holder.addPreDestroys(preDestroys);
112: }
113:
114: private Map<String, LifecycleMethod> map(
115: Map<String, LifecycleCallbackType> lifecycleCallbackTypes) {
116: if (lifecycleCallbackTypes.isEmpty()) {
117: return null;
118: }
119: Map<String, LifecycleMethod> map = new HashMap<String, LifecycleMethod>();
120: for (Map.Entry<String, LifecycleCallbackType> entry : lifecycleCallbackTypes
121: .entrySet()) {
122: String className = entry.getKey();
123: LifecycleCallbackType callback = entry.getValue();
124: LifecycleMethod method = new LifecycleMethod(className,
125: callback.getLifecycleCallbackMethod()
126: .getStringValue().trim());
127: map.put(className, method);
128: }
129: return map;
130: }
131:
132: private Map<String, LifecycleCallbackType> mapLifecycleCallbacks(
133: LifecycleCallbackType[] callbackArray, String componentType)
134: throws DeploymentException {
135: Map<String, LifecycleCallbackType> map = new HashMap<String, LifecycleCallbackType>();
136: for (LifecycleCallbackType callback : callbackArray) {
137: String className;
138: if (callback.isSetLifecycleCallbackClass()) {
139: className = callback.getLifecycleCallbackClass()
140: .getStringValue().trim();
141: } else {
142: if (componentType == null) {
143: throw new DeploymentException(
144: "No component type available and none in lifecycle callback");
145: }
146: className = componentType;
147: }
148: map.put(className, callback);
149: }
150: return map;
151: }
152:
153: public QNameSet getSpecQNameSet() {
154: return QNameSet.EMPTY;
155: }
156:
157: public QNameSet getPlanQNameSet() {
158: return QNameSet.EMPTY;
159: }
160:
161: public static final GBeanInfo GBEAN_INFO;
162:
163: static {
164: GBeanInfoBuilder infoBuilder = GBeanInfoBuilder.createStatic(
165: LifecycleMethodBuilder.class,
166: NameFactory.MODULE_BUILDER);
167:
168: GBEAN_INFO = infoBuilder.getBeanInfo();
169: }
170:
171: public static GBeanInfo getGBeanInfo() {
172: return GBEAN_INFO;
173: }
174: }
|