001: /*
002: * CoadunationLib: The coaduntion implementation library.
003: * Copyright (C) 2006 Rift IT Contracting
004: *
005: * This library is free software; you can redistribute it and/or
006: * modify it under the terms of the GNU Lesser General Public
007: * License as published by the Free Software Foundation; either
008: * version 2.1 of the License, or (at your option) any later version.
009: *
010: * This library is distributed in the hope that it will be useful,
011: * but WITHOUT ANY WARRANTY; without even the implied warranty of
012: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
013: * Lesser General Public License for more details.
014: *
015: * You should have received a copy of the GNU Lesser General Public
016: * License along with this library; if not, write to the Free Software
017: * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
018: *
019: * BeanWrapper.java
020: *
021: * This object is responsible for wrapping a bean and loading it into memory.
022: */
023:
024: // package definition
025: package com.rift.coad.lib.bean;
026:
027: // java imports
028: import java.lang.reflect.Proxy;
029: import java.lang.reflect.Constructor;
030:
031: // logging import
032: import org.apache.log4j.Logger;
033:
034: // coadunation imports
035: import com.rift.coad.lib.deployment.DeploymentLoader;
036: import com.rift.coad.lib.deployment.BeanInfo;
037: import com.rift.coad.lib.security.ThreadsPermissionContainer;
038:
039: /**
040: * This object is responsible for wrapping a bean and loading it into memory.
041: *
042: * @author Brett Chaldecott
043: */
044: public class BeanWrapper {
045:
046: // the class log variable
047: protected Logger log = Logger
048: .getLogger(BeanWrapper.class.getName());
049:
050: // The classes member variables
051: private DeploymentLoader loader = null;
052: private ThreadsPermissionContainer permissions = null;
053: private String bindName = null;
054: private BeanHandler handler = null;
055: private Object proxy = null;
056: private java.rmi.Remote tie = null;
057: private Object subObject = null;
058: private Class interfaceRef = null;
059:
060: /**
061: * Creates a new instance of BeanWrapper
062: *
063: * @param deploymentLoader The reference to the deployment loader.
064: * @param beanInfo The reference to the bean information object.
065: * @exception BeanException
066: */
067: public BeanWrapper(DeploymentLoader deploymentLoader,
068: BeanInfo beanInfo, ThreadsPermissionContainer permissions)
069: throws BeanException {
070: try {
071: this .loader = deploymentLoader;
072: this .permissions = permissions;
073: bindName = beanInfo.getBindName();
074: subObject = deploymentLoader.getClassLoader().loadClass(
075: beanInfo.getClassName()).newInstance();
076: interfaceRef = deploymentLoader.getClassLoader().loadClass(
077: beanInfo.getInterfaceName());
078: handler = new BeanHandler(beanInfo, subObject, beanInfo
079: .getRole(), permissions, deploymentLoader
080: .getClassLoader());
081: proxy = (Object) Proxy.newProxyInstance(deploymentLoader
082: .getClassLoader(), new Class[] { deploymentLoader
083: .getClass(beanInfo.getInterfaceName()) }, handler);
084: tie = loadTie(beanInfo, subObject);
085: } catch (Exception ex) {
086: log.error("Failed to instanciate the bean wrapper : "
087: + ex.getMessage(), ex);
088: throw new BeanException(
089: "Failed to instanciate the bean wrapper : "
090: + ex.getMessage(), ex);
091: }
092: }
093:
094: /**
095: * The bind name that will be used to search for this proxy object or
096: * container object.
097: *
098: * @return The string containing the bind information.
099: */
100: public String getBindName() {
101: return bindName;
102: }
103:
104: /**
105: * This method returns the reference to the proxy object.
106: *
107: * @return The reference to the proxy object
108: */
109: public Object getProxy() {
110: return proxy;
111: }
112:
113: /**
114: * This method returns the reference to the tie class.
115: *
116: * @return The reference to the tie object.
117: */
118: public java.rmi.Remote getTie() {
119: return tie;
120: }
121:
122: /**
123: * This method returns the reference to the sub object.
124: *
125: * @return The reference to the sub object.
126: */
127: public Object getSubObject() {
128: return subObject;
129: }
130:
131: /**
132: * The interface this class must run as.
133: *
134: * @return The class this object must run as.
135: */
136: public Class getInterface() {
137: return interfaceRef;
138: }
139:
140: /**
141: * This method loads the tie class.
142: *
143: * @return The reference to the loaded tie or null if it does not inherit
144: * from remote.
145: * @param beanInfo The information
146: * @param subObject The sub object uppon which all the call will be made.
147: */
148: private java.rmi.Remote loadTie(BeanInfo beanInfo, Object subObject)
149: throws BeanException {
150: if (!(subObject instanceof java.rmi.Remote)) {
151: return null;
152: }
153: String className = subObject.getClass().getName()
154: + BeanPattern.TIE_SUFFIX;
155: try {
156: Class classRef = loader.getClassLoader().loadClass(
157: className);
158: // note: Must be exact matching class when doing the constructor
159: // look up. It does not take inheritance into account.
160: Class[] parameterTypes = new Class[] { ClassLoader.class,
161: subObject.getClass(), String.class,
162: ThreadsPermissionContainer.class, BeanInfo.class };
163: Constructor constructor = classRef
164: .getConstructor(parameterTypes);
165: return (java.rmi.Remote) constructor.newInstance(loader
166: .getClassLoader(), subObject, beanInfo.getRole(),
167: permissions, beanInfo);
168: } catch (Exception ex) {
169: throw new BeanException("Failed to load the class ["
170: + className + "] because : " + ex.getMessage(), ex);
171: }
172: }
173: }
|