001    // Copyright 2007 The Apache Software Foundation
002    //
003    // Licensed under the Apache License, Version 2.0 (the "License");
004    // you may not use this file except in compliance with the License.
005    // You may obtain a copy of the License at
006    //
007    //     http://www.apache.org/licenses/LICENSE-2.0
008    //
009    // Unless required by applicable law or agreed to in writing, software
010    // distributed under the License is distributed on an "AS IS" BASIS,
011    // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
012    // See the License for the specific language governing permissions and
013    // limitations under the License.
014    
015    package org.apache.hivemind.annotations.internal;
016    
017    import java.lang.reflect.Method;
018    
019    import org.apache.hivemind.ApplicationRuntimeException;
020    import org.apache.hivemind.Location;
021    import org.apache.hivemind.definition.Contribution;
022    import org.apache.hivemind.definition.ContributionContext;
023    
024    /**
025     * Contributes to a configuration point by passing the configuration container
026     * to a method defined in an annotated module by use of the {@link Contribution} annotation. 
027     * 
028     * @author Achim Huegen
029     */
030    public class MethodCallContributionConstructor implements
031            Contribution
032    {
033        private Method _templateMethod;
034    
035        private ModuleInstanceProvider _moduleInstanceProvider;
036    
037        private Location _location;
038    
039        public MethodCallContributionConstructor(Location location, Method factoryMethod,
040                ModuleInstanceProvider moduleInstanceProvider)
041        {
042            _location = location;
043            _templateMethod = factoryMethod;
044            _moduleInstanceProvider = moduleInstanceProvider;
045        }
046    
047        public Location getLocation()
048        {
049            return _location;
050        }
051    
052        public void contribute(ContributionContext context)
053        {
054            try
055            {
056                if (_templateMethod.getParameterTypes().length == 0) {
057                    Object result = _templateMethod.invoke(_moduleInstanceProvider.getModuleInstance());
058                    // a null contribution means: nothing to contribute. This happens for example
059                    // in configuration point definitions 
060                    if (result != null) {
061                        context.mergeContribution(result);
062                    }
063                } else if (_templateMethod.getParameterTypes().length == 1) {
064                    Object[] params = new Object[] {context.getConfigurationData()}; 
065                    _templateMethod.invoke(_moduleInstanceProvider.getModuleInstance(), params);
066                } else {
067                    // TODO: Throw Exception
068                }
069            }
070            catch (Exception ex)
071            {
072                throw new ApplicationRuntimeException(ex.getMessage(), getLocation(), ex);
073            }
074            
075        }
076    
077    }