001 /* 002 Copyright (C) 2001-2003 Renaud Pawlak 003 004 This program is free software; you can redistribute it and/or modify 005 it under the terms of the GNU Lesser General Public License as 006 published by the Free Software Foundation; either version 2 of the 007 License, or (at your option) any later version. 008 009 This program is distributed in the hope that it will be useful, 010 but WITHOUT ANY WARRANTY; without even the implied warranty of 011 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 012 GNU Lesser General Public License for more details. 013 014 You should have received a copy of the GNU Lesser General Public License 015 along with this program; if not, write to the Free Software 016 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ 017 018 package org.objectweb.jac.aspects.distribution; 019 020 021 //import java.util.*; 022 import java.util.HashSet; 023 import java.util.Iterator; 024 import org.apache.log4j.Logger; 025 import org.objectweb.jac.core.*; 026 import org.objectweb.jac.core.dist.*; 027 import org.objectweb.jac.core.rtti.ClassItem; 028 import org.objectweb.jac.core.rtti.ClassRepository; 029 import org.objectweb.jac.core.rtti.FieldItem; 030 import org.objectweb.jac.core.rtti.MethodItem; 031 import org.objectweb.jac.util.*; 032 033 /** 034 * This aspect component implements a generic deployment aspect. 035 * 036 * @author <a href="http://cedric.cnam.fr/~pawlak/index-english.html">Renaud Pawlak</a> 037 * 038 * @see DeploymentConf 039 * @see DeploymentRule */ 040 041 public class DeploymentAC extends AspectComponent implements DeploymentConf { 042 static Logger logger = Logger.getLogger("deployment"); 043 static Logger loggerSerial = Logger.getLogger("serialization"); 044 045 /** the name of the metadata that tells whether the parameters of 046 * a methods are references (TRUE) or values (FALSE). */ 047 public static final String REFS= "DeploymentAC.REFS"; 048 049 /** already deployed objects */ 050 transient HashSet treated = new HashSet(); 051 052 /** 053 * Force the treatment of the objects that are being 054 * serialized. This allows the deployment aspect to be sure that 055 * an object that is passed as a parameter of a remote invocation 056 * is already deployed when arriving on the new site. If none of 057 * the deployment rule can be applied on the serialized object, 058 * then the object will not be a forwarder but a copy of the 059 * original object. 060 * 061 * @param finalObject the structure to store the serialized infos 062 */ 063 064 public Wrappee whenSerialized(Wrappee orgObject, 065 SerializedJacObject finalObject) { 066 067 NameRepository nr = (NameRepository)NameRepository.get(); 068 String name = nr.getName(orgObject); 069 loggerSerial.debug("DeploymentAC.whenSerialize " + name); 070 //if ( ! isMatchingARule( orgObject ) ) { 071 finalObject.disableForwarding(); 072 073 if (Collaboration.get().getAttribute(SerializedJacObject.STATELESS)==null) { 074 075 Object[] state = ObjectState.getState(orgObject); 076 String[] fieldsName = (String[])state[0]; 077 Object[] fieldsValue = (Object[])state[1]; 078 079 ClassItem cl = ClassRepository.get().getClass(orgObject.getClass()); 080 for (int i = 0; i < fieldsName.length; i++) { 081 loggerSerial.debug(" serializing field " + fieldsName[i] + " - " + fieldsValue[i]); 082 FieldItem fi = cl.getField(fieldsName[i]); 083 if (fi != null && fi.getAttribute("deployment.transient") == null) { 084 finalObject.addField(fieldsName[i], fieldsValue[i]); 085 } 086 } 087 088 } else { 089 loggerSerial.debug(name+" is stateless in this context"); 090 } 091 092 /*} else { 093 DeploymentRule r = getMatchingRule( orgObject ); 094 if( r != null && r.getType().equals( "dynamic client-server" ) ) { 095 finalObject.disableForwarding(); 096 finalObject.setACInfos( 097 ACManager.get().getName( this ), 098 RemoteRef.create( NameRepository.get().getName( orgObject ), orgObject ) ); 099 } 100 }*/ 101 return orgObject; 102 } 103 104 /** 105 * Fill the field values when the forwarding is disabled for this 106 * object.. 107 * 108 * @param orgObject the JAC object that is being deserialized. */ 109 110 public Wrappee whenDeserialized(SerializedJacObject orgObject, 111 Wrappee finalObject) { 112 loggerSerial.debug("DeploymentAC.whenDeserialize "+ 113 orgObject.getJacObjectClassName()); 114 if (!orgObject.isForwarder()) { 115 loggerSerial.debug("not a forwarder, deserialize..."); 116 RemoteRef server = 117 (RemoteRef)orgObject.getACInfos(ACManager.get().getName(this)); 118 if (server != null) { 119 Wrapping.wrapAll(finalObject,null, 120 new StubWrapper(this,server)); 121 } else { 122 Iterator it = orgObject.getFields().keySet().iterator(); 123 while (it.hasNext()) { 124 String fn = (String)it.next(); 125 loggerSerial.debug("setting field "+fn+" <- "+ 126 orgObject.getField(fn)); 127 ObjectState.setFieldValue( 128 finalObject,fn,orgObject.getField(fn)); 129 } 130 } 131 } else { 132 loggerSerial.debug("forwarder, do not deserialize..."); 133 } 134 return finalObject; 135 } 136 137 /* 138 * Actually deploys an object with a target host expression. 139 * 140 * @param wrappee the object to deploy 141 * @param hostExpr the host where to deploy the object 142 * @param state ??? 143 */ 144 145 /*public void deployTo(Wrappee wrappee, String hostExpr, boolean state) { 146 if (wrappee==null) 147 return; 148 if (treated.contains(wrappee)) 149 return; 150 treated.add(wrappee); 151 Log.trace("deployment", 152 "DEPLOYED UPCALLED WITH "+hostExpr+ 153 " wrappee="+wrappee+", topology="+Topology.get()); 154 Topology topology = Topology.getPartialTopology(hostExpr); 155 Deployment dep = new Deployment(this,topology); 156 if (state) { 157 dep.replicate(wrappee); 158 } else { 159 dep.replicateStruct(wrappee); 160 } 161 }*/ 162 163 public void deploy(String deploymentHost, 164 String nameRegexp, String containerName) { 165 166 pointcut(nameRegexp,".* && !org.objectweb.jac.lib.java.util.*","CONSTRUCTORS", 167 "org.objectweb.jac.aspects.distribution.DeploymentWrapper", 168 new Object[] {this,containerName,new Boolean(true)}, 169 deploymentHost,null,true); 170 171 // addDeploymentRule( new DeploymentRule( 172 // "deployment", nameRegexp, containerName, true ) ); 173 174 } 175 176 public void replicate(String deploymentHost, String nameRegexp, 177 String contRegexp) { 178 179 pointcut(nameRegexp,".* && !org.objectweb.jac.lib.java.util.*","CONSTRUCTORS", 180 "org.objectweb.jac.aspects.distribution.DeploymentWrapper", 181 new Object[] {this,contRegexp,new Boolean(true)}, 182 deploymentHost,null,true); 183 } 184 185 public void createTypedStubsFor(String name, String serverHost, 186 String hosts, 187 String stubType) { 188 pointcut(name,".* && !org.objectweb.jac.lib.java.util.*","CONSTRUCTORS", 189 "org.objectweb.jac.aspects.distribution.DeploymentWrapper", 190 new Object[] {this,hosts,new Boolean(true)}, 191 serverHost,null,true); 192 /*pointcut(name, ".*", "deployTo", 193 new Object[] { hosts, new Boolean(false) }, 194 serverHost, null);*/ 195 try { 196 pointcut(name, ".*", ".*", 197 (Wrapper)Class.forName(stubType) 198 .getConstructor(new Class[]{String.class}) 199 .newInstance(new Object[]{serverHost}), 200 hosts+" && !"+serverHost, null); 201 } catch ( Exception e ) { 202 logger.error("createTypedStubsFor: pointcut creation failed",e); 203 } 204 } 205 206 public void createStubsFor(String name, String serverHost, String hosts) { 207 createTypedStubsFor(name, serverHost, hosts, 208 "org.objectweb.jac.core.dist.StubWrapper"); 209 } 210 211 public void createAsynchronousStubsFor(String name, String serverHost, 212 String hosts) { 213 createTypedStubsFor(name, serverHost, hosts, 214 "org.objectweb.jac.core.dist.NonBlockingStubWrapper"); 215 } 216 217 public void setTransient(ClassItem classItem, String fieldName) { 218 FieldItem fi = classItem.getField(fieldName); 219 fi.setAttribute("deployment.transient","true"); 220 } 221 222 public void setParametersPassingMode(MethodItem method, Boolean[] refs) { 223 method.setAttribute(REFS, refs); 224 } 225 226 } 227 228