001    /**
002     * Copyright (c) 2000-2010 Liferay, Inc. All rights reserved.
003     *
004     * The contents of this file are subject to the terms of the Liferay Enterprise
005     * Subscription License ("License"). You may not use this file except in
006     * compliance with the License. You can obtain a copy of the License by
007     * contacting Liferay, Inc. See the License for the specific language governing
008     * permissions and limitations under the License, including but not limited to
009     * distribution rights of the Software.
010     *
011     *
012     *
013     */
014    
015    package com.liferay.portal.bean;
016    
017    import com.liferay.portal.kernel.bean.BeanLocator;
018    import com.liferay.portal.kernel.bean.BeanLocatorException;
019    import com.liferay.portal.kernel.log.Log;
020    import com.liferay.portal.kernel.log.LogFactoryUtil;
021    import com.liferay.portal.kernel.util.ListUtil;
022    
023    import java.lang.reflect.Proxy;
024    
025    import java.util.Iterator;
026    import java.util.List;
027    import java.util.Map;
028    import java.util.concurrent.ConcurrentHashMap;
029    
030    import org.springframework.context.ApplicationContext;
031    
032    /**
033     * @author Brian Wing Shun Chan
034     */
035    public class BeanLocatorImpl implements BeanLocator {
036    
037            public static final String VELOCITY_SUFFIX = ".velocity";
038    
039            public BeanLocatorImpl(
040                    ClassLoader classLoader, ApplicationContext applicationContext) {
041    
042                    _classLoader = classLoader;
043                    _applicationContext = applicationContext;
044            }
045    
046            public ApplicationContext getApplicationContext() {
047                    return _applicationContext;
048            }
049    
050            public ClassLoader getClassLoader() {
051                    return _classLoader;
052            }
053    
054            public Object locate(String name) throws BeanLocatorException {
055                    try {
056                            return doLocate(name);
057                    }
058                    catch (Exception e) {
059                            throw new BeanLocatorException(e);
060                    }
061            }
062    
063            protected Object doLocate(String name) throws Exception {
064                    if (_log.isDebugEnabled()) {
065                            _log.debug("Locating " + name);
066                    }
067    
068                    if (name.endsWith(VELOCITY_SUFFIX)) {
069                            Object bean = _velocityBeans.get(name);
070    
071                            if (bean == null) {
072                                    String originalName = name.substring(
073                                            0, name.length() - VELOCITY_SUFFIX.length());
074    
075                                    bean = _applicationContext.getBean(originalName);
076    
077                                    Class<?>[] interfaces = bean.getClass().getInterfaces();
078    
079                                    List<Class<?>> interfacesList = ListUtil.fromArray(interfaces);
080    
081                                    Iterator<Class<?>> itr = interfacesList.iterator();
082    
083                                    while (itr.hasNext()) {
084                                            Class<?> classObj = itr.next();
085    
086                                            try {
087                                                    _classLoader.loadClass(classObj.getName());
088                                            }
089                                            catch (Exception e) {
090                                                    itr.remove();
091                                            }
092                                    }
093    
094                                    bean = Proxy.newProxyInstance(
095                                            _classLoader,
096                                            interfacesList.toArray(new Class<?>[interfacesList.size()]),
097                                            new VelocityBeanHandler(bean, _classLoader));
098    
099                                    _velocityBeans.put(name, bean);
100                            }
101    
102                            return bean;
103                    }
104                    else {
105                            return _applicationContext.getBean(name);
106                    }
107            }
108    
109            private static Log _log = LogFactoryUtil.getLog(BeanLocatorImpl.class);
110    
111            private ClassLoader _classLoader;
112            private ApplicationContext _applicationContext;
113            private Map<String, Object> _velocityBeans =
114                    new ConcurrentHashMap<String, Object>();
115    
116    }