001/**
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *      http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.apache.camel.component.bean;
018
019import org.apache.camel.CamelContext;
020import org.apache.camel.NoSuchBeanException;
021import org.apache.camel.Processor;
022import org.apache.camel.spi.Registry;
023
024/**
025 * An implementation of a {@link BeanHolder} which will look up a bean from the registry and act as a cache of its metadata
026 *
027 * @version 
028 */
029public class RegistryBean implements BeanHolder {
030    private final CamelContext context;
031    private final String name;
032    private final Registry registry;
033    private volatile BeanInfo beanInfo;
034    private volatile Class<?> clazz;
035    private ParameterMappingStrategy parameterMappingStrategy;
036
037    public RegistryBean(CamelContext context, String name) {
038        this.context = context;
039        this.name = name;
040        this.registry = context.getRegistry();
041    }
042
043    public RegistryBean(Registry registry, CamelContext context, String name) {
044        this.registry = registry;
045        this.context = context;
046        this.name = name;
047    }
048
049    @Override
050    public String toString() {
051        return "bean: " + name;
052    }
053
054    /**
055     * Creates a cached and constant {@link org.apache.camel.component.bean.BeanHolder} from this holder.
056     *
057     * @return a new {@link org.apache.camel.component.bean.BeanHolder} that has cached the lookup of the bean.
058     */
059    public ConstantBeanHolder createCacheHolder() {
060        Object bean = getBean();
061        BeanInfo info = createBeanInfo(bean);
062        return new ConstantBeanHolder(bean, info);
063    }
064
065    public Object getBean() throws NoSuchBeanException {
066        // must always lookup bean first
067        Object value = lookupBean();
068
069        if (value != null) {
070            // could be a class then create an instance of it
071            if (value instanceof Class) {
072                // bean is a class so create an instance of it
073                value = context.getInjector().newInstance((Class<?>)value);
074            }
075            return value;
076        }
077
078        // okay bean is not in registry, so try to resolve if its a class name and create a shared instance
079        if (clazz == null) {
080            clazz = context.getClassResolver().resolveClass(name);
081        }
082
083        if (clazz == null) {
084            // no its not a class then we cannot find the bean
085            throw new NoSuchBeanException(name);
086        }
087
088        // bean is a class so create an instance of it
089        return context.getInjector().newInstance(clazz);
090    }
091
092    public Processor getProcessor() {
093        return null;
094    }
095
096    public boolean supportProcessor() {
097        return false;
098    }
099
100    public BeanInfo getBeanInfo() {
101        if (beanInfo == null) {
102            Object bean = getBean();
103            this.beanInfo = createBeanInfo(bean);
104        }
105        return beanInfo;
106    }
107
108    public BeanInfo getBeanInfo(Object bean) {
109        return createBeanInfo(bean);
110    }
111
112    public String getName() {
113        return name;
114    }
115
116    public Registry getRegistry() {
117        return registry;
118    }
119
120    public CamelContext getContext() {
121        return context;
122    }
123
124    public ParameterMappingStrategy getParameterMappingStrategy() {
125        if (parameterMappingStrategy == null) {
126            parameterMappingStrategy = createParameterMappingStrategy();
127        }
128        return parameterMappingStrategy;
129    }
130
131    public void setParameterMappingStrategy(ParameterMappingStrategy parameterMappingStrategy) {
132        this.parameterMappingStrategy = parameterMappingStrategy;
133    }
134
135    // Implementation methods
136    //-------------------------------------------------------------------------
137    protected BeanInfo createBeanInfo(Object bean) {
138        return new BeanInfo(context, bean.getClass(), getParameterMappingStrategy());
139    }
140
141    protected ParameterMappingStrategy createParameterMappingStrategy() {
142        return BeanInfo.createParameterMappingStrategy(context);
143    }
144
145    protected Object lookupBean() {
146        return registry.lookupByName(name);
147    }
148}