1 28 29 package com.caucho.jca; 30 31 import com.caucho.config.Config; 32 import com.caucho.config.ConfigException; 33 import com.caucho.config.types.InitProgram; 34 import com.caucho.jca.cfg.ObjectConfig; 35 import com.caucho.lifecycle.Lifecycle; 36 import com.caucho.loader.Environment; 37 import com.caucho.loader.EnvironmentClassLoader; 38 import com.caucho.loader.EnvironmentListener; 39 import com.caucho.log.Log; 40 import com.caucho.naming.Jndi; 41 import com.caucho.util.L10N; 42 43 import javax.annotation.PostConstruct; 44 import javax.resource.spi.ActivationSpec ; 45 import javax.resource.spi.ManagedConnectionFactory ; 46 import javax.resource.spi.ResourceAdapter ; 47 import javax.resource.spi.ResourceAdapterAssociation ; 48 import javax.resource.spi.endpoint.MessageEndpointFactory ; 49 import java.util.ArrayList ; 50 import java.util.logging.Level ; 51 import java.util.logging.Logger ; 52 53 56 public class ConnectorResource implements EnvironmentListener { 57 private static L10N L = new L10N(ConnectorResource.class); 58 private static Logger log = Log.open(ConnectorResource.class); 59 60 private static int _idGen; 61 62 private String _name; 63 private String _type; 64 65 private ResourceArchive _rar; 66 67 private ResourceAdapterConfig _resourceAdapter = new ResourceAdapterConfig(); 68 private InitProgram _resourceAdapterInit; 69 70 private ArrayList <ConnectionFactory > _outboundList = 71 new ArrayList <ConnectionFactory >(); 72 73 private ArrayList <ConnectionListener> _inboundList = 74 new ArrayList <ConnectionListener>(); 75 76 private ArrayList <ConnectionResource> _resourceList = 77 new ArrayList <ConnectionResource>(); 78 79 private ResourceAdapter _ra; 80 private boolean _isInitRA; 81 82 private final Lifecycle _lifecycle = new Lifecycle(); 83 84 87 public void setName(String name) 88 { 89 _name = name; 90 } 91 92 95 public String getName() 96 { 97 return _name; 98 } 99 100 103 public void setType(String type) 104 throws Exception 105 { 106 _type = type; 107 108 _rar = ResourceArchiveManager.findResourceArchive(_type); 109 110 ClassLoader loader = Thread.currentThread().getContextClassLoader(); 111 112 if (_rar != null) { 113 ObjectConfig raConfig = _rar.getResourceAdapter(); 114 115 if (_name == null) 116 _name = _rar.getDisplayName() + "-" + _idGen++; 117 118 if (raConfig.getType() != null) 119 _ra = (ResourceAdapter ) raConfig.instantiate(); 120 } 121 else { 122 try { 123 Class raClass = Class.forName(_type, false, loader); 124 125 _ra = (ResourceAdapter ) raClass.newInstance(); 126 } catch (Throwable e) { 127 throw new ConfigException(L.l("`{0}' is not a known connector. The type must match the resource adaptor or managed connection factory of one of the installed *.rar files or specify a ResourceAdapter implementation.", 128 _type)); 129 } 130 } 131 } 132 133 136 public String getType() 137 { 138 return _type; 139 } 140 141 144 public ResourceAdapterConfig createResourceAdapter() 145 throws ConfigException 146 { 147 if (_ra == null) 148 throw new ConfigException(L.l("`{0}' may not have a <resource-adapter> section. Old-style connectors must use <connection-factory>, but not <resource-adapter>.", 149 _type)); 150 return _resourceAdapter; 151 } 152 153 156 public void setResourceAdapter(ResourceAdapterConfig raConfig) 157 throws Throwable 158 { 159 if (raConfig.getInit() != null) 160 raConfig.getInit().configure(_ra); 161 162 165 166 initRA(); 167 168 if (raConfig.getName() != null) 169 Jndi.bindDeepShort(raConfig.getName(), _ra); 170 } 171 172 175 public ConnectionFactory createConnectionFactory() 176 throws Throwable 177 { 178 initRA(); 179 180 return new ConnectionFactory (); 181 } 182 183 186 public void addConnectionFactory(ConnectionFactory factory) 187 throws Throwable 188 { 189 ManagedConnectionFactory managedFactory = factory.getFactory(); 190 191 if (factory.getInit() != null) 192 factory.getInit().configure(managedFactory); 193 194 if (_ra != null) 195 managedFactory.setResourceAdapter(_ra); 196 197 initRA(); 198 199 ResourceManagerImpl rm = ResourceManagerImpl.createLocalManager(); 200 201 ConnectionPool cm = rm.createConnectionPool(); 202 203 if (_name != null) 204 cm.setName(_name); 205 206 if (_rar != null) { 207 String trans = _rar.getTransactionSupport(); 208 209 if (trans == null) { cm.setXATransaction(true); 211 cm.setLocalTransaction(true); 212 } 213 else if (trans.equals("XATransaction")) { 214 cm.setXATransaction(true); 215 cm.setLocalTransaction(true); 216 } 217 else if (trans.equals("NoTransaction")) { 218 cm.setXATransaction(false); 219 cm.setLocalTransaction(false); 220 } 221 else if (trans.equals("LocalTransaction")) { 222 cm.setXATransaction(false); 223 cm.setLocalTransaction(true); 224 } 225 } 226 227 cm.setLocalTransactionOptimization(factory.getLocalTransactionOptimization()); 228 cm.setShareable(factory.getShareable()); 229 Object connectionFactory = cm.init(managedFactory); 230 cm.start(); 231 232 if (factory.getName() != null) 233 Jndi.bindDeepShort(factory.getName(), connectionFactory); 234 } 235 236 239 public ConnectionListener createMessageListener() 240 throws Exception 241 { 242 initRA(); 243 244 return new ConnectionListener(); 245 } 246 247 250 public void addMessageListener(ConnectionListener listener) 251 throws Throwable 252 { 253 _inboundList.add(listener); 254 255 String listenerType = listener.getType(); 256 257 if (_ra == null) 258 throw new ConfigException(L.l("message-listener requires a resource-adapter.")); 259 260 ActivationSpec activationSpec; 261 262 if (_rar != null) { 263 ObjectConfig objectCfg = _rar.getMessageListener(listenerType); 264 265 if (objectCfg == null) 266 throw new ConfigException(L.l("`{0}' is an unknown type of <connection-listener> for `{1}'. The connector has no matching inbound connection-listener.", 267 listenerType, 268 _type)); 269 270 activationSpec = (ActivationSpec ) objectCfg.instantiate(); 271 } 272 else { 273 ClassLoader loader = Thread.currentThread().getContextClassLoader(); 274 Class listenerClass = null; 275 276 try { 277 listenerClass = Class.forName(listenerType, false, loader); 278 } catch (Throwable e) { 279 throw new ConfigException(L.l("`{0}' is not a known listener. The type must match the activation spec for an inbound connection of one of the installed *.rar files or specify an ActivationSpec implementation.", 280 listenerType), e); 281 } 282 283 activationSpec = (ActivationSpec ) listenerClass.newInstance(); 284 } 285 286 if (listener.getInit() != null) 287 listener.getInit().configure(activationSpec); 288 291 292 activationSpec.setResourceAdapter(_ra); 293 295 EndpointFactory endpointFactoryCfg = listener.getEndpointFactory(); 296 297 if (endpointFactoryCfg == null) 298 throw new ConfigException(L.l("connection-listener needs endpoint factory.")); 299 300 Class endpointClass = endpointFactoryCfg.getType(); 301 302 MessageEndpointFactory endpointFactory; 303 endpointFactory = (MessageEndpointFactory ) endpointClass.newInstance(); 304 305 if (endpointFactoryCfg.getInit() != null) 306 endpointFactoryCfg.getInit().configure(endpointFactory); 307 308 Config.init(endpointFactory); 309 310 listener.setEndpoint(endpointFactory); 311 listener.setActivation(activationSpec); 312 } 313 314 317 public ConnectionResource createResource() 318 { 319 return new ConnectionResource(); 320 } 321 322 325 public void addResource(ConnectionResource resource) 326 throws Throwable 327 { 328 Object resourceObject = resource.getObject(); 329 330 if (resource.getInit() != null) 331 resource.getInit().configure(resourceObject); 332 333 if (_ra != null && resourceObject instanceof ResourceAdapterAssociation ) 334 ((ResourceAdapterAssociation ) resourceObject).setResourceAdapter(_ra); 335 336 if (resource.getName() != null) 337 Jndi.bindDeepShort(resource.getName(), resourceObject); 338 } 339 340 343 @PostConstruct 344 public void init() 345 throws Exception 346 { 347 if (_type == null) 348 throw new ConfigException(L.l("<connector> requires a <type>.")); 349 350 354 initRA(); 355 Environment.addEnvironmentListener(this); 356 357 start(); 358 359 log.info("Connector[" + _type + "] initialized"); 360 } 361 362 365 public void start() 366 throws Exception 367 { 368 if (! _lifecycle.toActive()) 369 return; 370 371 initRA(); 372 373 for (int i = 0; i < _inboundList.size(); i++) { 374 ConnectionListener listener = _inboundList.get(i); 375 376 _ra.endpointActivation(listener.getEndpoint(), 377 listener.getActivation()); 378 } 379 } 380 381 384 public void initRA() 385 throws Exception 386 { 387 if (! _isInitRA) { 388 _isInitRA = true; 389 390 if (_ra != null) { 391 ResourceManagerImpl.addResource(_ra); 393 } 394 } 395 } 396 397 400 public void stop() 401 { 402 if (! _lifecycle.toStop()) 403 return; 404 405 for (int i = 0; i < _inboundList.size(); i++) { 406 ConnectionListener listener = _inboundList.get(i); 407 408 MessageEndpointFactory endpointFactory = listener.getEndpoint(); 409 ActivationSpec activation = listener.getActivation(); 410 411 if (_ra != null) 412 _ra.endpointDeactivation(endpointFactory, activation); 413 } 414 } 415 416 419 public void environmentStart(EnvironmentClassLoader loader) 420 { 421 try { 422 start(); 423 } catch (Exception e) { 424 log.log(Level.WARNING, e.toString(), e); 425 } 426 } 427 428 431 public void environmentStop(EnvironmentClassLoader loader) 432 { 433 stop(); 434 } 435 436 public String toString() 437 { 438 return "ConnectorResource[" + _name + "]"; 439 } 440 441 public class ResourceAdapterConfig { 442 private String _name; 443 private InitProgram _init; 444 445 public void setJndiName(String name) 446 { 447 _name = name; 448 } 449 450 public String getName() 451 { 452 return _name; 453 } 454 455 public void setInit(InitProgram init) 456 { 457 _init = init; 458 } 459 460 public InitProgram getInit() 461 { 462 return _init; 463 } 464 } 465 466 public class ConnectionFactory { 467 private String _name; 468 private String _type; 469 private ManagedConnectionFactory _factory; 470 private boolean _localTransactionOptimization = true; 471 private boolean _shareable = true; 472 private InitProgram _init; 473 474 public void setJndiName(String name) 475 { 476 _name = name; 477 } 478 479 public String getName() 480 { 481 return _name; 482 } 483 484 public void setType(String type) 485 throws Exception 486 { 487 _type = type; 488 489 if (_rar != null) { 490 ObjectConfig factoryConfig = _rar.getConnectionDefinition(type); 491 492 if (factoryConfig == null) 493 throw new ConfigException(L.l("`{0}' is an unknown type of <connection-factory> for `{1}'. The connector has no matching outbound connection-factory.", 494 type, 495 ConnectorResource.this._type)); 496 497 _factory = (ManagedConnectionFactory ) factoryConfig.instantiate(); 498 } 499 else if (type != null) { 500 ClassLoader loader = Thread.currentThread().getContextClassLoader(); 501 Class factoryClass = null; 502 503 try { 504 factoryClass = Class.forName(type, false, loader); 505 } catch (Throwable e) { 506 throw new ConfigException(L.l("`{0}' is not a known connection factory. The type must match the resource adaptor or managed connection factory of one of the installed *.rar files or specify a ManagedConnectionFactory implementation.", 507 type)); 508 } 509 510 if (! ManagedConnectionFactory .class.isAssignableFrom(factoryClass)) { 511 throw new ConfigException(L.l("`{0}' does not implement javax.resource.spi.ManagedConnectionFactory. <connection-factory> classes must implement ManagedConnectionFactory.", 512 factoryClass.getName())); 513 } 514 515 _factory = (ManagedConnectionFactory ) factoryClass.newInstance(); 516 } 517 518 } 519 520 public String getType() 521 { 522 return _type; 523 } 524 525 528 public void setLocalTransactionOptimization(boolean enable) 529 { 530 _localTransactionOptimization = enable; 531 } 532 533 536 public boolean getLocalTransactionOptimization() 537 { 538 return _localTransactionOptimization; 539 } 540 541 544 public void setShareable(boolean enable) 545 { 546 _shareable = enable; 547 } 548 549 552 public boolean getShareable() 553 { 554 return _shareable; 555 } 556 557 public ManagedConnectionFactory getFactory() 558 { 559 return _factory; 560 } 561 562 public void setInit(InitProgram init) 563 { 564 _init = init; 565 } 566 567 public InitProgram getInit() 568 { 569 return _init; 570 } 571 572 @PostConstruct 573 public void init() 574 throws Exception 575 { 576 if (_factory == null && _rar != null) { 577 ObjectConfig factoryConfig = _rar.getConnectionDefinition(null); 578 579 _factory = (ManagedConnectionFactory ) factoryConfig.instantiate(); 580 } 581 582 if (_factory == null) 583 throw new ConfigException(L.l("connection-factory requires a valid type.")); 584 } 585 } 586 587 public class ConnectionListener { 588 private String _name; 589 private String _type; 590 private InitProgram _init; 591 private EndpointFactory _endpointFactory; 592 593 private MessageEndpointFactory _endpoint; 594 private ActivationSpec _activation; 595 596 public void setJndiName(String name) 597 { 598 _name = name; 599 } 600 601 public String getName() 602 { 603 return _name; 604 } 605 606 public void setType(String type) 607 { 608 _type = type; 609 } 610 611 public String getType() 612 { 613 return _type; 614 } 615 616 public void setInit(InitProgram init) 617 { 618 _init = init; 619 } 620 621 public InitProgram getInit() 622 { 623 return _init; 624 } 625 626 public EndpointFactory getEndpointFactory() 627 { 628 return _endpointFactory; 629 } 630 631 public EndpointFactory createEndpointFactory() 632 { 633 _endpointFactory = new EndpointFactory (); 634 635 return _endpointFactory; 636 } 637 638 @PostConstruct 639 public void init() 640 throws ConfigException 641 { 642 if (_endpointFactory == null) 643 throw new ConfigException(L.l("connection-listener needs an endpoint-factory")); 644 } 645 646 public void setEndpoint(MessageEndpointFactory endpoint) 647 { 648 _endpoint = endpoint; 649 } 650 651 public MessageEndpointFactory getEndpoint() 652 { 653 return _endpoint; 654 } 655 656 public void setActivation(ActivationSpec activation) 657 { 658 _activation = activation; 659 } 660 661 public ActivationSpec getActivation() 662 { 663 return _activation; 664 } 665 } 666 667 public class EndpointFactory { 668 private String _name; 669 private Class _type; 670 private InitProgram _init; 671 672 public void setJndiName(String name) 673 { 674 _name = name; 675 } 676 677 public String getName() 678 { 679 return _name; 680 } 681 682 public void setType(Class type) 683 throws ConfigException 684 { 685 _type = type; 686 687 Config.checkCanInstantiate(type); 688 } 689 690 public Class getType() 691 { 692 return _type; 693 } 694 695 public void setInit(InitProgram init) 696 { 697 _init = init; 698 } 699 700 public InitProgram getInit() 701 { 702 return _init; 703 } 704 } 705 706 public class ConnectionResource { 707 private String _name; 708 private String _type; 709 private InitProgram _init; 710 711 private ObjectConfig _objectConfig; 712 private Object _object; 713 714 public void setJndiName(String name) 715 { 716 _name = name; 717 } 718 719 public String getName() 720 { 721 return _name; 722 } 723 724 public void setType(String type) 725 throws Exception 726 { 727 _type = type; 728 729 Object resourceObject = null; 730 731 if (_rar != null) { 732 _objectConfig = _rar.getAdminObject(type); 733 734 if (_objectConfig == null) 735 throw new ConfigException(L.l("`{0}' may not have a <resource> section. The connector has no matching <adminobject> defined.", 736 _type)); 737 738 _object = _objectConfig.instantiate(); 739 } 740 else { 741 ClassLoader loader = Thread.currentThread().getContextClassLoader(); 742 try { 743 Class resourceClass = Class.forName(type, false, loader); 744 745 _object = resourceClass.newInstance(); 746 } catch (Throwable e) { 747 throw new ConfigException(L.l("`{0}' is not a known resource. The type must match the adminobject of one of the installed *.rar files.", 748 _type), e); 749 } 750 751 } 752 } 753 754 public String getType() 755 { 756 return _type; 757 } 758 759 public void setInit(InitProgram init) 760 { 761 _init = init; 762 } 763 764 public InitProgram getInit() 765 { 766 return _init; 767 } 768 769 public Object getObject() 770 { 771 return _object; 772 } 773 774 @PostConstruct 775 public void init() 776 throws ConfigException 777 { 778 if (_object == null) 779 throw new ConfigException(L.l("<type> must be set for a resource.")); 780 } 781 } 782 } 783 784 | Popular Tags |