/* * Copyright (C) 2006-2013 Bitronix Software (http://www.bitronix.be) * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package bitronix.tm.resource; import bitronix.tm.mock.resource.jdbc.MockitoXADataSource; import bitronix.tm.mock.resource.jms.MockXAConnectionFactory; import bitronix.tm.resource.jdbc.PoolingDataSource; import bitronix.tm.resource.jms.PoolingConnectionFactory; import bitronix.tm.utils.PropertyUtils; import junit.framework.TestCase; import javax.sql.XADataSource; import java.lang.reflect.Field; import java.util.Map; import java.util.Properties; /** * * @author Ludovic Orban */ public class ResourceLoaderTest extends TestCase { public void testBindOneJdbc() throws Exception { ResourceLoader loader = new ResourceLoader(); Properties p = new Properties(); p.setProperty("resource.ds1.className", MockitoXADataSource.class.getName()); p.setProperty("resource.ds1.uniqueName", "dataSource1"); p.setProperty("resource.ds1.maxPoolSize", "123"); p.setProperty("resource.ds1.automaticEnlistingEnabled", "true"); p.setProperty("resource.ds1.useTmJoin", "false"); p.setProperty("resource.ds1.deferConnectionRelease", "true"); p.setProperty("resource.ds1.driverProperties.userName", "java"); p.setProperty("resource.ds1.driverProperties.password", "java"); p.setProperty("resource.ds1.driverProperties.database", "users1"); p.setProperty("resource.ds1.driverProperties.clonedProperties.a.key", "1000"); p.setProperty("resource.ds1.driverProperties.clonedProperties.b.key", "2000"); loader.initXAResourceProducers(p); Map dataSources = loader.getResources(); assertEquals(1, dataSources.size()); String uniqueName = (String) dataSources.keySet().iterator().next(); assertEquals("dataSource1", uniqueName); PoolingDataSource pds = (PoolingDataSource) dataSources.get(uniqueName); assertEquals("bitronix.tm.mock.resource.jdbc.MockitoXADataSource", pds.getClassName()); assertEquals("dataSource1", pds.getUniqueName()); assertEquals(123, pds.getMaxPoolSize()); assertEquals(5, pds.getDriverProperties().size()); MockitoXADataSource mockXA = pds.unwrap(MockitoXADataSource.class); assertNotNull(mockXA); Properties clonedProperties = mockXA.getClonedProperties(); assertNotNull(clonedProperties); assertEquals(2, clonedProperties.size()); assertEquals("1000", clonedProperties.getProperty("a.key")); assertEquals("2000", clonedProperties.getProperty("b.key")); } public void testDecryptPassword() throws Exception { ResourceLoader loader = new ResourceLoader(); Properties p = new Properties(); p.setProperty("resource.ds1.className", MockitoXADataSource.class.getName()); p.setProperty("resource.ds1.uniqueName", "dataSource10"); p.setProperty("resource.ds1.maxPoolSize", "123"); p.setProperty("resource.ds1.automaticEnlistingEnabled", "true"); p.setProperty("resource.ds1.useTmJoin", "false"); p.setProperty("resource.ds1.deferConnectionRelease", "true"); p.setProperty("resource.ds1.driverProperties.userName", "java"); p.setProperty("resource.ds1.driverProperties.password", "{DES}UcXKog312decCrwu51xGmw=="); p.setProperty("resource.ds1.driverProperties.database", "users1"); loader.initXAResourceProducers(p); Map dataSources = loader.getResources(); assertEquals(1, dataSources.size()); String uniqueName = (String) dataSources.keySet().iterator().next(); assertEquals("dataSource10", uniqueName); PoolingDataSource pds = (PoolingDataSource) dataSources.get(uniqueName); assertEquals("bitronix.tm.mock.resource.jdbc.MockitoXADataSource", pds.getClassName()); assertEquals("dataSource10", pds.getUniqueName()); assertEquals(123, pds.getMaxPoolSize()); assertEquals(3, pds.getDriverProperties().size()); String decryptedPassword = (String) PropertyUtils.getProperty(getXADataSource(pds), "password"); assertEquals("java", decryptedPassword); } protected XADataSource getXADataSource(PoolingDataSource poolingDataSource) throws NoSuchFieldException, IllegalAccessException { Field field = PoolingDataSource.class.getDeclaredField("xaDataSource"); field.setAccessible(true); return (XADataSource) field.get(poolingDataSource); } public void testBindOneJms() throws Exception { ResourceLoader loader = new ResourceLoader(); Properties p = new Properties(); p.setProperty("resource.ds1.className", MockXAConnectionFactory.class.getName()); p.setProperty("resource.ds1.uniqueName", "mq1"); p.setProperty("resource.ds1.maxPoolSize", "123"); p.setProperty("resource.ds1.automaticEnlistingEnabled", "true"); p.setProperty("resource.ds1.useTmJoin", "false"); p.setProperty("resource.ds1.deferConnectionRelease", "true"); p.setProperty("resource.ds1.driverProperties.endpoint", "tcp://somewhere"); loader.initXAResourceProducers(p); Map dataSources = loader.getResources(); assertEquals(1, dataSources.size()); String uniqueName = (String) dataSources.keySet().iterator().next(); assertEquals("mq1", uniqueName); PoolingConnectionFactory pcf = (PoolingConnectionFactory) dataSources.get(uniqueName); assertEquals("bitronix.tm.mock.resource.jms.MockXAConnectionFactory", pcf.getClassName()); assertEquals("mq1", pcf.getUniqueName()); assertEquals(123, pcf.getMaxPoolSize()); assertEquals(1, pcf.getDriverProperties().size()); } public void testBind2WithSomeDefaults() throws Exception { ResourceLoader loader = new ResourceLoader(); Properties p = new Properties(); p.setProperty("resource.ds1.className", MockitoXADataSource.class.getName()); p.setProperty("resource.ds1.uniqueName", "dataSource2"); p.setProperty("resource.ds1.maxPoolSize", "123"); p.setProperty("resource.ds1.automaticEnlistingEnabled", "true"); p.setProperty("resource.ds1.useTmJoin", "false"); p.setProperty("resource.ds1.deferConnectionRelease", "true"); p.setProperty("resource.ds1.driverProperties.userName", "java"); p.setProperty("resource.ds1.driverProperties.password", "java"); p.setProperty("resource.ds1.driverProperties.database", "users1"); p.setProperty("resource.ds2.className", MockitoXADataSource.class.getName()); p.setProperty("resource.ds2.uniqueName", "some.unique.Name"); p.setProperty("resource.ds2.maxPoolSize", "123"); loader.initXAResourceProducers(p); Map dataSources = loader.getResources(); assertEquals(2, dataSources.size()); PoolingDataSource pds = (PoolingDataSource) dataSources.get("dataSource2"); assertEquals("bitronix.tm.mock.resource.jdbc.MockitoXADataSource", pds.getClassName()); assertEquals("dataSource2", pds.getUniqueName()); assertEquals(123, pds.getMaxPoolSize()); assertEquals(3, pds.getDriverProperties().size()); pds = (PoolingDataSource) dataSources.get("some.unique.Name"); assertEquals("bitronix.tm.mock.resource.jdbc.MockitoXADataSource", pds.getClassName()); assertEquals("some.unique.Name", pds.getUniqueName()); assertEquals(123, pds.getMaxPoolSize()); assertEquals(true, pds.getDeferConnectionRelease()); assertEquals(true, pds.getAutomaticEnlistingEnabled()); assertEquals(true, pds.getUseTmJoin()); assertEquals(0, pds.getDriverProperties().size()); } public void testConfigErrors() throws Exception { ResourceLoader loader = new ResourceLoader(); try { Properties p = new Properties(); p.setProperty("resource.ds2.className", "some.class.Name"); loader.initXAResourceProducers(p); fail("should have thrown ResourceConfigurationException"); } catch (ResourceConfigurationException ex) { assertEquals("cannot configure resource for configuration entries with name [ds2] - failing property is [className]", ex.getMessage()); assertEquals(ClassNotFoundException.class, ex.getCause().getClass()); assertEquals("some.class.Name", ex.getCause().getMessage()); } try { Properties p = new Properties(); p.setProperty("resource.ds2.className", MockitoXADataSource.class.getName()); loader.initXAResourceProducers(p); fail("should have thrown ResourceConfigurationException"); } catch (ResourceConfigurationException ex) { assertEquals("missing mandatory property [uniqueName] of resource [ds2] in resources configuration file", ex.getMessage()); } try { Properties p = new Properties(); p.setProperty("resource.ds2.jndiName", "some.jndi.Name"); loader.initXAResourceProducers(p); fail("should have thrown ResourceConfigurationException"); } catch (ResourceConfigurationException ex) { assertEquals("missing mandatory property [className] for resource [ds2] in resources configuration file", ex.getMessage()); } Properties p = new Properties(); p.setProperty("resource.ds2.className", MockitoXADataSource.class.getName()); p.setProperty("resource.ds2.uniqueName", "some.other.unique.Name"); p.setProperty("resource.ds2.maxPoolSize", "123"); loader.initXAResourceProducers(p); } public void testFormatErrors() throws Exception { ResourceLoader loader = new ResourceLoader(); Properties p = new Properties(); p.setProperty("resource.ds2.className", MockitoXADataSource.class.getName()); p.setProperty("resource.ds2.uniqueName", "some.more.unique.Name"); p.setProperty("resource.ds2.maxPoolSize", "abc"); // incorrect format try { loader.initXAResourceProducers(p); fail("expected ResourceConfigurationException"); } catch (ResourceConfigurationException ex) { assertEquals("cannot configure resource for configuration entries with name [ds2] - failing property is [maxPoolSize]", ex.getMessage()); } p.setProperty("resource.ds2.className", MockitoXADataSource.class.getName()); p.setProperty("resource.ds2.uniqueName", "some.also.other.unique.Name"); p.setProperty("resource.ds2.maxPoolSize", "123"); p.setProperty("resource.ds2.useTmJoin", "unknown"); // incorrect format, will default to false loader.initXAResourceProducers(p); PoolingDataSource pds = (PoolingDataSource) loader.getResources().get("some.also.other.unique.Name"); assertFalse(pds.getUseTmJoin()); } }