/** * The contents of this file are subject to the OpenMRS Public License * Version 1.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://license.openmrs.org * * Software distributed under the License is distributed on an "AS IS" * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the * License for the specific language governing rights and limitations * under the License. * * Copyright (C) OpenMRS, LLC. All Rights Reserved. */ package org.openmrs.api; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; import static org.junit.Assert.fail; import java.util.ArrayList; import java.util.List; import org.junit.Assert; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; import org.openmrs.GlobalProperty; import org.openmrs.ImplementationId; import org.openmrs.api.context.Context; import org.openmrs.test.BaseContextSensitiveTest; import org.openmrs.test.Verifies; import org.openmrs.util.OpenmrsConstants; /** * TODO clean up and finish this test class. Should test all methods in the * {@link AdministrationService} */ public class AdministrationServiceTest extends BaseContextSensitiveTest { private AdministrationService adminService = null; protected static final String ADMIN_INITIAL_DATA_XML = "org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"; /** * Run this before each unit test in this class. It simply assigns the services used in this * class to private variables The "@Before" method in {@link BaseContextSensitiveTest} is run * right before this method and sets up the initial data set and authenticates to the Context * * @throws Exception */ @Before public void runBeforeEachTest() throws Exception { if (adminService == null) adminService = Context.getAdministrationService(); } /** * Tests the AdministrationService.executeSql method with a sql statement containing a valid * group by clause * * @see {@link AdministrationService#executeSQL(String,null)} */ @Test @Verifies(value = "should execute sql containing group by", method = "executeSQL(String,null)") public void executeSQL_shouldExecuteSqlContainingGroupBy() throws Exception { String sql = "select encounter1_.location_id, encounter1_.creator, encounter1_.encounter_type, encounter1_.form_id, location2_.location_id, count(obs0_.obs_id) from obs obs0_ right outer join encounter encounter1_ on obs0_.encounter_id=encounter1_.encounter_id inner join location location2_ on encounter1_.location_id=location2_.location_id inner join users user3_ on encounter1_.creator=user3_.user_id inner join person user3_1_ on user3_.user_id=user3_1_.person_id inner join encounter_type encountert4_ on encounter1_.encounter_type=encountert4_.encounter_type_id inner join form form5_ on encounter1_.form_id=form5_.form_id where encounter1_.date_created>='2007-05-05' and encounter1_.date_created<= '2008-05-05' group by encounter1_.location_id, encounter1_.creator , encounter1_.encounter_type , encounter1_.form_id"; adminService.executeSQL(sql, true); String sql2 = "select encounter_id, count(*) from encounter encounter_id group by encounter_id"; adminService.executeSQL(sql2, true); } /** * @see AdministrationService#setImplementationId(ImplementationId) */ @Test @Verifies(value = "should not fail if given implementationId is null", method = "setImplementationId(ImplementationId)") public void setImplementationId_shouldNotFailIfGivenImplementationIdIsNull() throws Exception { // save a null impl id. no exception thrown adminService.setImplementationId(null); ImplementationId afterNull = adminService.getImplementationId(); assertNull("There shouldn't be an impl id defined after setting a null impl id", afterNull); } /** * This uses a try/catch so that we can make sure no blank id is saved to the database. * * @see AdministrationService#setImplementationId(ImplementationId) */ @Test() @Verifies(value = "should throw APIException if given empty implementationId object", method = "setImplementationId(ImplementationId)") public void setImplementationId_shouldThrowAPIExceptionIfGivenEmptyImplementationIdObject() throws Exception { // save a blank impl id. exception thrown try { adminService.setImplementationId(new ImplementationId()); fail("An exception should be thrown on a blank impl id save"); } catch (APIException e) { // expected exception } ImplementationId afterBlank = adminService.getImplementationId(); assertNull("There shouldn't be an impl id defined after setting a blank impl id", afterBlank); } /** * This uses a try/catch so that we can make sure no blank id is saved to the database. * * @see {@link AdministrationService#setImplementationId(ImplementationId)} */ @Test @Verifies(value = "should throw APIException if given a caret in the implementationId code", method = "setImplementationId(ImplementationId)") public void setImplementationId_shouldThrowAPIExceptionIfGivenACaretInTheImplementationIdCode() throws Exception { // save an impl id with an invalid hl7 code ImplementationId invalidId = new ImplementationId(); invalidId.setImplementationId("caret^caret"); invalidId.setName("an invalid impl id for a unit test"); invalidId.setPassphrase("some valid passphrase"); invalidId.setDescription("Some valid description"); try { adminService.setImplementationId(invalidId); fail("An exception should be thrown on an invalid impl id save"); } catch (APIException e) { // expected exception } ImplementationId afterInvalid = adminService.getImplementationId(); assertNull("There shouldn't be an impl id defined after setting an invalid impl id", afterInvalid); } /** * @see {@link AdministrationService#setImplementationId(ImplementationId)} */ @Test @Verifies(value = "should throw APIException if given a pipe in the implementationId code", method = "setImplementationId(ImplementationId)") public void setImplementationId_shouldThrowAPIExceptionIfGivenAPipeInTheImplementationIdCode() throws Exception { // save an impl id with an invalid hl7 code ImplementationId invalidId2 = new ImplementationId(); invalidId2.setImplementationId("pipe|pipe"); invalidId2.setName("an invalid impl id for a unit test"); invalidId2.setPassphrase("some valid passphrase"); invalidId2.setDescription("Some valid description"); try { adminService.setImplementationId(invalidId2); fail("An exception should be thrown on an invalid impl id save"); } catch (APIException e) { // expected exception } ImplementationId afterInvalid2 = adminService.getImplementationId(); assertNull("There shouldn't be an impl id defined after setting an invalid impl id", afterInvalid2); } /** * @see AdministrationService#setImplementationId(ImplementationId) */ @Test @Verifies(value = "should create implementation id in database", method = "setImplementationId(ImplementationId)") public void setImplementationId_shouldCreateImplementationIdInDatabase() throws Exception { // save a valid impl id ImplementationId validId = new ImplementationId(); validId.setImplementationId("JUNIT-TEST"); validId.setName("JUNIT-TEST implementation id"); validId.setPassphrase("This is the junit test passphrase"); validId.setDescription("This is the junit impl id used for testing of the openmrs API only."); adminService.setImplementationId(validId); assertEquals(validId, adminService.getImplementationId()); } /** * @see AdministrationService#setImplementationId(ImplementationId) */ @Test @Verifies(value = "should overwrite implementation id in database if exists", method = "setImplementationId(ImplementationId)") public void setImplementationId_shouldOverwriteImplementationIdInDatabaseIfExists() throws Exception { executeDataSet("org/openmrs/api/include/AdministrationServiceTest-general.xml"); // sanity check to make sure we have an implementation id Assert.assertNotNull(adminService.getImplementationId()); Context.clearSession(); // so a NonUniqueObjectException doesn't occur on the global property later // save a second valid id ImplementationId validId2 = new ImplementationId(); validId2.setImplementationId("JUNIT-TEST 2"); validId2.setName("JUNIT-TEST (#2) implementation id"); validId2.setPassphrase("This is the junit test passphrase 2"); validId2.setDescription("This is the junit impl id (2) used for testing of the openmrs API only."); adminService.setImplementationId(validId2); assertEquals(validId2, adminService.getImplementationId()); } /** * @see AdministrationService#setImplementationId(ImplementationId) */ @Test @Verifies(value = "should set uuid on implementation id global property", method = "setImplementationId(ImplementationId)") public void setImplementationId_shouldSetUuidOnImplementationIdGlobalProperty() throws Exception { ImplementationId validId = new ImplementationId(); validId.setImplementationId("JUNIT-TEST"); validId.setName("JUNIT-TEST implementation id"); validId.setPassphrase("This is the junit test passphrase"); validId.setDescription("This is the junit impl id used for testing of the openmrs API only."); adminService.setImplementationId(validId); GlobalProperty gp = adminService.getGlobalPropertyObject(OpenmrsConstants.GLOBAL_PROPERTY_IMPLEMENTATION_ID); Assert.assertNotNull(gp.getUuid()); } /** * @see {@link AdministrationService#getGlobalProperty(String)} */ @Test @Verifies(value = "should not fail with null propertyName", method = "getGlobalProperty(String)") public void getGlobalProperty_shouldNotFailWithNullPropertyName() throws Exception { adminService.getGlobalProperty(null); } /** * @see {@link AdministrationService#getGlobalProperty(String)} */ @Test @Verifies(value = "should get property value given valid property name", method = "getGlobalProperty(String)") public void getGlobalProperty_shouldGetPropertyValueGivenValidPropertyName() throws Exception { // put the global property into the database executeDataSet("org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"); String propertyValue = adminService.getGlobalProperty("a_valid_gp_key"); Assert.assertEquals("correct-value", propertyValue); } /** * @see {@link AdministrationService#getGlobalProperty(String,String)} */ @Test @Verifies(value = "should not fail with null default value", method = "getGlobalProperty(String,String)") public void getGlobalProperty_shouldNotFailWithNullDefaultValue() throws Exception { adminService.getGlobalProperty("asdfsadfsafd", null); } /** * @see {@link AdministrationService#getGlobalProperty(String,String)} */ @Test @Verifies(value = "should return default value if property name does not exist", method = "getGlobalProperty(String,String)") public void getGlobalProperty_shouldReturnDefaultValueIfPropertyNameDoesNotExist() throws Exception { String invalidKey = "asdfasdf"; String propertyValue = adminService.getGlobalProperty(invalidKey); Assert.assertNull(propertyValue); // make sure there isn't a gp String value = adminService.getGlobalProperty(invalidKey, "default"); Assert.assertEquals("default", value); } /** * @see {@link AdministrationService#getGlobalPropertiesByPrefix(String)} */ @Test @Verifies(value = "should return all relevant global properties in the database", method = "getGlobalPropertiesByPrefix(String)") public void getGlobalPropertiesByPrefix_shouldReturnAllRelevantGlobalPropertiesInTheDatabase() throws Exception { executeDataSet("org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"); List<GlobalProperty> properties = adminService.getGlobalPropertiesByPrefix("fake.module."); for (GlobalProperty property : properties) { Assert.assertTrue(property.getProperty().startsWith("fake.module.")); Assert.assertTrue(property.getPropertyValue().startsWith("correct-value")); } } /** * @see {@link AdministrationService#getAllowedLocales()} */ @Test @Verifies(value = "should not fail if not global property for locales allowed defined yet", method = "getAllowedLocales()") public void getAllowedLocales_shouldNotFailIfNotGlobalPropertyForLocalesAllowedDefinedYet() throws Exception { Context.getAdministrationService().purgeGlobalProperty( new GlobalProperty(OpenmrsConstants.GLOBAL_PROPERTY_LOCALE_ALLOWED_LIST)); Context.getAdministrationService().getAllowedLocales(); } /** * @see {@link AdministrationService#getGlobalPropertyByUuid(String)} */ @Test @Verifies(value = "should find object given valid uuid", method = "getGlobalPropertyByUuid(String)") public void getGlobalPropertyByUuid_shouldFindObjectGivenValidUuid() throws Exception { String uuid = "4f55827e-26fe-102b-80cb-0017a47871b3"; GlobalProperty prop = Context.getAdministrationService().getGlobalPropertyByUuid(uuid); Assert.assertEquals("locale.allowed.list", prop.getProperty()); } /** * @see {@link AdministrationService#getGlobalPropertyByUuid(String)} */ @Test @Verifies(value = "should return null if no object found with given uuid", method = "getGlobalPropertyByUuid(String)") public void getGlobalPropertyByUuid_shouldReturnNullIfNoObjectFoundWithGivenUuid() throws Exception { Assert.assertNull(Context.getAdministrationService().getGlobalPropertyByUuid("some invalid uuid")); } /** * @see AdministrationService#saveGlobalProperties(List) */ @Test @Verifies(value = "should delete property from database if not in list", method = "saveGlobalProperties(List<QGlobalProperty;>)") public void saveGlobalProperties_shouldDeletePropertyFromDatabaseIfNotInList() throws Exception { List<GlobalProperty> globalProperties = Context.getAdministrationService().getAllGlobalProperties(); GlobalProperty firstGlobalProperty = globalProperties.remove(0); Context.getAdministrationService().saveGlobalProperties(globalProperties); Assert.assertNull(Context.getAdministrationService().getGlobalProperty(firstGlobalProperty.getProperty())); } /** * @see AdministrationService#saveGlobalProperties(List) */ @Test @Verifies(value = "should not fail with empty list", method = "saveGlobalProperties(List<QGlobalProperty;>)") public void saveGlobalProperties_shouldNotFailWithEmptyList() throws Exception { Context.getAdministrationService().saveGlobalProperties(new ArrayList<GlobalProperty>()); } /** * @see AdministrationService#saveGlobalProperties(List) */ @Test @Verifies(value = "should save all global properties to the database", method = "saveGlobalProperties(List<QGlobalProperty;>)") public void saveGlobalProperties_shouldSaveAllGlobalPropertiesToTheDatabase() throws Exception { // get the current global properties List<GlobalProperty> globalProperties = Context.getAdministrationService().getAllGlobalProperties(); // and now add some new ones to it globalProperties.add(new GlobalProperty("new prop1", "new prop value1", "desc")); globalProperties.add(new GlobalProperty("new prop2", "new prop value2", "desc")); Context.getAdministrationService().saveGlobalProperties(globalProperties); Assert.assertEquals("new prop value1", Context.getAdministrationService().getGlobalProperty("new prop1")); Assert.assertEquals("new prop value2", Context.getAdministrationService().getGlobalProperty("new prop2")); } /** * @see AdministrationService#saveGlobalProperties(List) */ @Test @Verifies(value = "should assign uuid to all new properties", method = "saveGlobalProperties(List<QGlobalProperty;>)") public void saveGlobalProperties_shouldAssignUuidToAllNewProperties() throws Exception { // get the current global properties List<GlobalProperty> globalProperties = Context.getAdministrationService().getAllGlobalProperties(); // and now add a new one to it and save it globalProperties.add(new GlobalProperty("new prop", "new prop value", "desc")); Context.getAdministrationService().saveGlobalProperties(globalProperties); Assert.assertNotNull(Context.getAdministrationService().getGlobalPropertyObject("new prop").getUuid()); } /** * @see {@link AdministrationService#getAllGlobalProperties()} */ @Test @Verifies(value = "should return all global properties in the database", method = "getAllGlobalProperties()") public void getAllGlobalProperties_shouldReturnAllGlobalPropertiesInTheDatabase() throws Exception { executeDataSet(ADMIN_INITIAL_DATA_XML); Assert.assertEquals(10, Context.getAdministrationService().getAllGlobalProperties().size()); } /** * @see {@link AdministrationService#getAllowedLocales()} */ @Test @Verifies(value = "should return at least one locale if no locales defined in database yet", method = "getAllowedLocales()") public void getAllowedLocales_shouldReturnAtLeastOneLocaleIfNoLocalesDefinedInDatabaseYet() throws Exception { Assert.assertTrue(Context.getAdministrationService().getAllowedLocales().size() > 0); } /** * @see {@link AdministrationService#getGlobalPropertyObject(String)} */ @Test @Verifies(value = "should return null when no global property match given property name", method = "getGlobalPropertyObject(String)") public void getGlobalPropertyObject_shouldReturnNullWhenNoGlobalPropertyMatchGivenPropertyName() throws Exception { executeDataSet(ADMIN_INITIAL_DATA_XML); Assert.assertNull(Context.getAdministrationService().getGlobalPropertyObject("magicResistSkill")); } /** * @see {@link AdministrationService#getImplementationId()} */ @Test @Verifies(value = "should return null if no implementation id is defined yet", method = "getImplementationId()") public void getImplementationId_shouldReturnNullIfNoImplementationIdIsDefinedYet() throws Exception { executeDataSet(ADMIN_INITIAL_DATA_XML); Assert.assertNull(Context.getAdministrationService().getImplementationId()); } /** * @see {@link AdministrationService#getPresentationLocales()} */ @Test @Ignore //TODO: This test fails for some reason @Verifies(value = "should return at least one locale if no locales defined in database yet", method = "getPresentationLocales()") public void getPresentationLocales_shouldReturnAtLeastOneLocaleIfNoLocalesDefinedInDatabaseYet() throws Exception { Assert.assertTrue(Context.getAdministrationService().getPresentationLocales().size() > 0); } /** * @see {@link AdministrationService#getPresentationLocales()} */ @Test @Verifies(value = "should not return more locales than message source service locales", method = "getPresentationLocales()") public void getPresentationLocales_shouldNotReturnMoreLocalesThanMessageSourceServiceLocales() throws Exception { Assert.assertFalse(Context.getAdministrationService().getPresentationLocales().size() > Context .getMessageSourceService().getLocales().size()); } /** * @see {@link AdministrationService#getSystemVariables()} */ @Test @Verifies(value = "should return all registered system variables", method = "getSystemVariables()") public void getSystemVariables_shouldReturnAllRegisteredSystemVariables() throws Exception { // The method implementation adds 12 system variables Assert.assertEquals(12, Context.getAdministrationService().getSystemVariables().size()); } /** * @see {@link AdministrationService#purgeGlobalProperty(GlobalProperty)} */ @Test @Verifies(value = "should delete global property from database", method = "purgeGlobalProperty(GlobalProperty)") public void purgeGlobalProperty_shouldDeleteGlobalPropertyFromDatabase() throws Exception { executeDataSet(ADMIN_INITIAL_DATA_XML); AdministrationService as = Context.getAdministrationService(); Assert.assertEquals(10, as.getAllGlobalProperties().size()); as.purgeGlobalProperty(as.getGlobalPropertyObject("a_valid_gp_key")); Assert.assertEquals(9, as.getAllGlobalProperties().size()); } /** * @see {@link AdministrationService#saveGlobalProperty(GlobalProperty)} */ @Test @Verifies(value = "should create global property in database", method = "saveGlobalProperty(GlobalProperty)") public void saveGlobalProperty_shouldCreateGlobalPropertyInDatabase() throws Exception { executeDataSet(ADMIN_INITIAL_DATA_XML); AdministrationService as = Context.getAdministrationService(); as.saveGlobalProperty(new GlobalProperty("detectHiddenSkill", "100")); Assert.assertNotNull(as.getGlobalProperty("detectHiddenSkill")); } /** * @see {@link AdministrationService#saveGlobalProperty(GlobalProperty)} */ @Test @Verifies(value = "should overwrite global property if exists", method = "saveGlobalProperty(GlobalProperty)") public void saveGlobalProperty_shouldOverwriteGlobalPropertyIfExists() throws Exception { executeDataSet(ADMIN_INITIAL_DATA_XML); AdministrationService as = Context.getAdministrationService(); GlobalProperty gp = as.getGlobalPropertyObject("a_valid_gp_key"); Assert.assertEquals("correct-value", gp.getPropertyValue()); gp.setPropertyValue("new-even-more-correct-value"); as.saveGlobalProperty(gp); Assert.assertEquals("new-even-more-correct-value", as.getGlobalProperty("a_valid_gp_key")); } /** * @see {@link AdministrationService#getAllowedLocales()} */ @Test @Verifies(value = "should not return duplicates even if the global property has them", method = "getAllowedLocales()") public void getAllowedLocales_shouldNotReturnDuplicatesEvenIfTheGlobalPropertyHasThem() throws Exception { Context.getAdministrationService().saveGlobalProperty( new GlobalProperty(OpenmrsConstants.GLOBAL_PROPERTY_LOCALE_ALLOWED_LIST, "en,fr,es,en")); Assert.assertEquals(3, Context.getAdministrationService().getAllowedLocales().size()); } /** * @see {@link AdministrationService#getGlobalPropertyValue()} */ @Test @Verifies(value = "should get property value in the proper type specified", method = "getGlobalPropertyValue()") public void getGlobalPropertyValue_shouldReturnValueInTheSpecifiedIntegerType() throws Exception { // put the global property into the database executeDataSet("org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"); Object value = adminService.getGlobalPropertyValue("valid.integer", new Integer(4)); Assert.assertTrue(value instanceof Integer); Assert.assertEquals(new Integer(1234), value); } /** * @see {@link AdministrationService#getGlobalPropertyValue()} */ @Test @Verifies(value = "should return default value if property name does not exist", method = "getGlobalPropertyValue()") public void getGlobalPropertyValue_shouldReturnDefaultValueForMissingProperty() throws Exception { // put the global property into the database executeDataSet("org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"); Object value = adminService.getGlobalPropertyValue("does.not.exist", new Integer(1234)); Assert.assertEquals(new Integer(1234), value); } /** * @see {@link AdministrationService#getGlobalPropertyValue()} */ @Test @Verifies(value = "should get property value in the proper type specified", method = "getGlobalPropertyValue()") public void getGlobalPropertyValue_shouldReturnValueInTheSpecifiedDoubleType() throws Exception { // put the global property into the database executeDataSet("org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"); Object retValue = adminService.getGlobalPropertyValue("valid.double", new Double(4.34)); Assert.assertTrue(retValue instanceof Double); Assert.assertEquals(new Double(1234.54), retValue); } /** * @see {@link AdministrationService#getGlobalProperty(String)} */ @Test @Verifies(value = "should get property in case sensitive way", method = "getGlobalProperty(String)") public void getGlobalProperty_shouldGetPropertyInCaseSensitiveWay() throws Exception { executeDataSet("org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"); // sanity check String orig = adminService.getGlobalProperty("another-global-property"); Assert.assertEquals("anothervalue", orig); // try to get a global property with invalid case String noprop = adminService.getGlobalProperty("ANOTher-global-property", "boo"); Assert.assertEquals("boo", noprop); } /** * @see {@link AdministrationService#saveGlobalProperty(GlobalProperty)} */ @Test @Verifies(value = "should allow different properties to have the same string with different case", method = "saveGlobalProperty(GlobalProperty)") public void saveGlobalProperty_shouldAllowDifferentPropertiesToHaveTheSameStringWithDifferentCase() throws Exception { executeDataSet("org/openmrs/api/include/AdministrationServiceTest-globalproperties.xml"); // sanity check String orig = adminService.getGlobalProperty("another-global-property"); Assert.assertEquals("anothervalue", orig); // should match current gp GlobalProperty gp = new GlobalProperty("ANOTher-global-property", "somethingelse"); adminService.saveGlobalProperty(gp); String prop = adminService.getGlobalProperty("ANOTher-global-property", "boo"); Assert.assertEquals("somethingelse", prop); } /** * @see {@link AdministrationService#saveGlobalProperties(List<QGlobalProperty;>)} */ @Test @Verifies(value = "should save properties with case difference only", method = "saveGlobalProperties(List<QGlobalProperty;>)") public void saveGlobalProperties_shouldSavePropertiesWithCaseDifferenceOnly() throws Exception { List<GlobalProperty> props = new ArrayList<GlobalProperty>(); props.add(new GlobalProperty("a.property.key", "something")); props.add(new GlobalProperty("a.property.KEY", "somethingelse")); adminService.saveGlobalProperties(props); // make sure that we now have two properties props = adminService.getAllGlobalProperties(); Assert.assertEquals(2, props.size()); } }