1 22 package org.jboss.ejb3.iiop; 23 24 import java.lang.annotation.Annotation ; 25 import java.net.URL ; 26 27 import javax.ejb.EJBHome ; 28 import javax.ejb.EJBObject ; 29 import javax.management.MalformedObjectNameException ; 30 import javax.management.ObjectName ; 31 import javax.naming.Context ; 32 import javax.naming.InitialContext ; 33 import javax.naming.NamingException ; 34 import javax.rmi.PortableRemoteObject ; 35 36 import org.jboss.annotation.ejb.IIOP; 37 import org.jboss.annotation.ejb.RemoteBinding; 38 import org.jboss.aop.Advisor; 39 import org.jboss.ejb3.Container; 40 import org.jboss.ejb3.NonSerializableFactory; 41 import org.jboss.ejb3.ProxyFactoryHelper; 42 import org.jboss.ejb3.SessionContainer; 43 import org.jboss.ejb3.remoting.RemoteProxyFactory; 44 import org.jboss.iiop.CorbaORBService; 45 import org.jboss.iiop.codebase.CodebasePolicy; 46 import org.jboss.iiop.csiv2.CSIv2Policy; 47 import org.jboss.iiop.rmi.InterfaceAnalysis; 48 import org.jboss.iiop.rmi.ir.InterfaceRepository; 49 import org.jboss.invocation.iiop.ReferenceFactory; 50 import org.jboss.invocation.iiop.ServantRegistries; 51 import org.jboss.invocation.iiop.ServantRegistry; 52 import org.jboss.invocation.iiop.ServantRegistryKind; 53 import org.jboss.logging.Logger; 54 import org.jboss.metadata.IorSecurityConfigMetaData; 55 import org.jboss.mx.loading.RepositoryClassLoader; 56 import org.jboss.mx.util.MBeanProxyExt; 57 import org.jboss.proxy.ejb.handle.HandleDelegateImpl; 58 import org.jboss.system.Registry; 59 import org.jboss.web.WebClassLoader; 60 import org.jboss.web.WebServiceMBean; 61 import org.omg.CORBA.Any ; 62 import org.omg.CORBA.InterfaceDef ; 63 import org.omg.CORBA.InterfaceDefHelper; 64 import org.omg.CORBA.ORB ; 65 import org.omg.CORBA.Policy ; 66 import org.omg.CORBA.Repository ; 67 import org.omg.CORBA.UserException ; 68 import org.omg.CosNaming.NameComponent ; 69 import org.omg.CosNaming.NamingContext ; 70 import org.omg.CosNaming.NamingContextExt ; 71 import org.omg.CosNaming.NamingContextExtHelper ; 72 import org.omg.CosNaming.NamingContextHelper ; 73 import org.omg.CosNaming.NamingContextPackage.AlreadyBound ; 74 import org.omg.CosNaming.NamingContextPackage.CannotProceed ; 75 import org.omg.CosNaming.NamingContextPackage.InvalidName ; 76 import org.omg.CosNaming.NamingContextPackage.NotFound ; 77 import org.omg.PortableServer.Current ; 78 import org.omg.PortableServer.CurrentHelper ; 79 import org.omg.PortableServer.POA ; 80 import org.omg.PortableServer.Servant ; 81 82 88 public class IORFactory 89 implements RemoteProxyFactory 90 { 91 private static final Logger log = Logger.getLogger(IORFactory.class); 92 93 private Container container; 94 private Advisor advisor; 95 private RemoteBinding binding; 96 private String webServiceName = "jboss:service=WebService"; 98 private String beanRepositoryIds[]; 100 private String homeRepositoryIds[]; 101 private ORB orb; 103 private POA irPoa; 105 private InterfaceRepository iri; 106 private ServantRegistry servantRegistry; 107 private ServantRegistry homeServantRegistry; 108 private WebClassLoader wcl; 109 private ReferenceFactory referenceFactory; 110 private ReferenceFactory homeReferenceFactory; 111 112 private static final IIOP defaultIIOP = new IIOP() 114 { 115 public boolean interfaceRepositorySupported() 116 { 117 return false; 118 } 119 120 public String poa() 121 { 122 return POA_PER_SERVANT; 123 } 124 125 public Class <? extends Annotation > annotationType() 126 { 127 return IIOP.class; 128 } 129 }; 130 131 public Object createHomeProxy() 133 { 134 try 135 { 136 org.omg.CORBA.Object corbaRef = homeReferenceFactory.createReference(homeRepositoryIds[0]); 137 138 EJBHome corbaObj = (EJBHome ) PortableRemoteObject.narrow(corbaRef, EJBHome .class); 139 140 return corbaObj; 141 } 142 catch(Exception e) 143 { 144 throw new RuntimeException (e); 145 } 146 } 147 148 public Object createProxy() 149 { 150 try 151 { 152 org.omg.CORBA.Object corbaRef = referenceFactory.createReference(beanRepositoryIds[0]); 153 154 EJBObject corbaObj = (EJBObject ) PortableRemoteObject.narrow(corbaRef, EJBObject .class); 155 156 return corbaObj; 157 } 158 catch(Exception e) 159 { 160 throw new RuntimeException (e); 161 } 162 } 163 164 public Object createProxy(Object id) 165 { 166 try 167 { 168 org.omg.CORBA.Object corbaRef = referenceFactory.createReferenceWithId(id, beanRepositoryIds[0]); 169 170 EJBObject corbaObj = (EJBObject ) PortableRemoteObject.narrow(corbaRef, EJBObject .class); 171 172 return corbaObj; 173 } 174 catch(Exception e) 175 { 176 throw new RuntimeException (e); 177 } 178 } 179 180 private IIOP getIIOP() 181 { 182 IIOP iiop = (IIOP) advisor.resolveAnnotation(IIOP.class); 183 if(iiop != null) 184 return iiop; 185 186 return defaultIIOP; 187 } 188 189 private String getJndiName() 190 { 191 return ProxyFactoryHelper.getDefaultRemoteJndiName(container); 192 } 193 194 private String getServantName() 195 { 196 return "Servant/" + getJndiName(); 198 } 199 200 private WebServiceMBean getWebServer() throws MalformedObjectNameException 201 { 202 if(webServiceName == null) 203 throw new IllegalStateException ("iiop is not going to work without a web service"); 204 205 return (WebServiceMBean) MBeanProxyExt.create(WebServiceMBean.class, webServiceName); 206 } 207 208 211 private void rebind(NamingContextExt ctx, String strName, org.omg.CORBA.Object obj) throws Exception 212 { 213 NameComponent [] name = ctx.to_name(strName); 214 NamingContext intermediateCtx = ctx; 215 216 for (int i = 0; i < name.length - 1; i++ ) { 217 NameComponent [] relativeName = new NameComponent [] { name[i] }; 218 try { 219 intermediateCtx = NamingContextHelper.narrow( 220 intermediateCtx.resolve(relativeName)); 221 } 222 catch (NotFound e) { 223 intermediateCtx = intermediateCtx.bind_new_context(relativeName); 224 } 225 } 226 intermediateCtx.rebind(new NameComponent [] { name[name.length - 1] }, obj); 227 } 228 229 private void removeWebClassLoader() throws MalformedObjectNameException 230 { 231 getWebServer().removeClassLoader(wcl); 232 } 233 234 public void setContainer(Container container) 235 { 236 this.container = container; 237 this.advisor = (Advisor) container; } 239 240 public void setRemoteBinding(RemoteBinding binding) 241 { 242 this.binding = binding; 243 } 244 245 public void setWebServiceName(String name) 246 { 247 this.webServiceName = name; 248 } 249 250 public void start() throws Exception 251 { 252 Class remoteInterfaces[] = ProxyFactoryHelper.getRemoteInterfaces(container); 254 if(remoteInterfaces.length > 1) 255 log.warn("IIOP binding only works on 1 interface, using: " + remoteInterfaces[0].getName()); 256 InterfaceAnalysis interfaceAnalysis = InterfaceAnalysis.getInterfaceAnalysis(remoteInterfaces[0]); 257 this.beanRepositoryIds = interfaceAnalysis.getAllTypeIds(); 258 259 InterfaceAnalysis homeInterfaceAnalysis = null; 260 Class homeInterface = ProxyFactoryHelper.getRemoteHomeInterface(container); 261 if(homeInterface != null) 262 { 263 if(!EJBHome .class.isAssignableFrom(homeInterface)) 264 throw new IllegalArgumentException ("home interface " + homeInterface.getName() + " must extend javax.ejb.EJBHome (EJB3 4.6.8)"); 265 homeInterfaceAnalysis = InterfaceAnalysis.getInterfaceAnalysis(homeInterface); 266 this.homeRepositoryIds = homeInterfaceAnalysis.getAllTypeIds(); 267 } 268 270 try { 272 orb = (ORB )new InitialContext ().lookup("java:/" + CorbaORBService.ORB_NAME); 273 } 274 catch (NamingException e) { 275 throw new Exception ("Cannot lookup java:/" + CorbaORBService.ORB_NAME + ": " + e); 276 } 277 try { 278 irPoa = (POA )new InitialContext ().lookup("java:/" + CorbaORBService.IR_POA_NAME); 279 } 280 catch (NamingException e) { 281 throw new Exception ("Cannot lookup java:/" + CorbaORBService.IR_POA_NAME + ": " + e); 282 } 283 284 IIOP iiop = getIIOP(); 285 if(iiop.interfaceRepositorySupported()) 286 { 287 this.iri = new InterfaceRepository(orb, irPoa, getJndiName()); 288 iri.mapClass(remoteInterfaces[0]); 289 if(homeInterface != null) 290 iri.mapClass(homeInterface); 291 iri.finishBuild(); 292 } 293 294 ObjectName invokerName = new ObjectName ("jboss:service=invoker,type=iiop"); 296 ServantRegistries servantRegistries = (ServantRegistries) Registry.lookup(invokerName); 297 if(servantRegistries == null) 298 throw new Exception ("can't find iiop invoker"); 299 ServantRegistryKind registryWithTransientPOA; 300 ServantRegistryKind registryWithPersistentPOA; 301 if(iiop.poa().equals(IIOP.POA_PER_SERVANT)) 302 { 303 registryWithTransientPOA = ServantRegistryKind.TRANSIENT_POA_PER_SERVANT; 304 registryWithPersistentPOA = ServantRegistryKind.PERSISTENT_POA_PER_SERVANT; 305 } 306 else if(iiop.poa().equals(IIOP.POA_SHARED)) 307 { 308 registryWithTransientPOA = ServantRegistryKind.SHARED_TRANSIENT_POA; 309 registryWithPersistentPOA = ServantRegistryKind.SHARED_PERSISTENT_POA; 310 } 311 else 312 throw new IllegalArgumentException ("@IIOP.poa can only be 'per-servant' or 'shared'"); 313 this.servantRegistry = servantRegistries.getServantRegistry(registryWithTransientPOA); 315 this.homeServantRegistry = servantRegistries.getServantRegistry(registryWithPersistentPOA); 317 ObjectName on = container.getObjectName(); 320 this.wcl = new EJB3IIOPWebClassLoader(on, (RepositoryClassLoader) ((SessionContainer) container).getClassloader(), getJndiName()); 321 WebServiceMBean webServer = getWebServer(); 322 URL [] codebaseURLs = {webServer.addClassLoader(wcl)}; 323 wcl.setWebURLs(codebaseURLs); 324 325 String codebaseString = wcl.getCodebaseString(); 327 log.debug("codebase = " + codebaseString); 328 Any codebase = orb.create_any(); 329 codebase.insert_string(codebaseString); 330 Policy codebasePolicy; 331 codebasePolicy = orb.create_policy(CodebasePolicy.TYPE, codebase); 332 333 Any secPolicy = orb.create_any(); 336 IorSecurityConfigMetaData iorSecurityConfigMetaData = new IorSecurityConfigMetaData(); secPolicy.insert_Value(iorSecurityConfigMetaData); 340 Policy csiv2Policy = orb.create_policy(CSIv2Policy.TYPE, secPolicy); 341 342 Policy policies[] = { codebasePolicy, csiv2Policy }; 343 344 InterfaceDef interfaceDef = null; 345 if(iri != null) 346 { 347 Repository ir = iri.getReference(); 348 interfaceDef = InterfaceDefHelper.narrow(ir.lookup_id(beanRepositoryIds[0])); 349 } 350 351 Current poaCurrent = CurrentHelper.narrow(orb.resolve_initial_references("POACurrent")); 352 353 NamingContextExt ctx = getNamingContextExt(); 354 355 log.debug("binding servant name " + getServantName()); 356 357 Servant servant = new BeanCorbaServant(this, poaCurrent, container, interfaceDef, interfaceAnalysis); 358 this.referenceFactory = servantRegistry.bind(getServantName(), servant, policies); 359 360 EJBObject corbaObj = (EJBObject ) createProxy(); 361 362 rebind(ctx, getJndiName(), (org.omg.CORBA.Object ) corbaObj); 363 364 if(homeInterfaceAnalysis != null) 366 { 367 servant = new BeanCorbaServant(this, poaCurrent, container, null, homeInterfaceAnalysis); 368 this.homeReferenceFactory = homeServantRegistry.bind(getServantName() + "Home", servant, policies); 369 370 Object homeObject = createHomeProxy(); 371 372 rebind(ctx, getJndiName() + "Home", (org.omg.CORBA.Object ) homeObject); 373 } 374 375 Context compCtx = (Context ) new InitialContext ().lookup("java:comp"); 377 NonSerializableFactory.rebind(compCtx, "ORB", orb); 378 NonSerializableFactory.rebind(compCtx, "HandleDelegate", new HandleDelegateImpl()); 379 } 380 381 public void stop() throws Exception 382 { 383 if(homeReferenceFactory != null) 384 { 385 unbind(getJndiName() + "Home"); 386 unbindHomeServant(); 387 } 388 unbind(getJndiName()); 389 390 unbindServant(); 391 392 removeWebClassLoader(); 393 } 394 395 398 private void unbind(String strName) 399 { 400 try 401 { 402 NamingContextExt corbaContext = getNamingContextExt(); 403 NameComponent n[] = corbaContext.to_name(strName); 404 getNamingContextExt().unbind(n); 405 } 406 catch(Exception e) 407 { 408 log.warn("unable to unbind '" + strName + "'", e); 409 } 410 } 411 412 private void unbindHomeServant() 413 { 414 try 415 { 416 homeServantRegistry.unbind(getServantName() + "Home"); 417 } 418 catch(Exception e) 419 { 420 log.warn("unable to unbind home servant", e); 421 } 422 } 423 424 private void unbindServant() 425 { 426 try 427 { 428 servantRegistry.unbind(getServantName()); 429 } 430 catch(Exception e) 431 { 432 log.warn("unable to unbind servant", e); 433 } 434 } 435 436 private NamingContextExt getNamingContextExt() throws NamingException 437 { 438 Context initialContext = new InitialContext (); 439 440 return NamingContextExtHelper.narrow((org.omg.CORBA.Object ) initialContext.lookup("java:/" + org.jboss.iiop.CorbaNamingService.NAMING_NAME)); 443 } 444 } | Popular Tags |