diff --git a/omod-2.0/src/test/java/org/openmrs/module/webservices/rest/doc/SwaggerSpecificationCreatorTest.java b/omod-2.0/src/test/java/org/openmrs/module/webservices/rest/doc/SwaggerSpecificationCreatorTest.java index 290c5592a..aa09097df 100644 --- a/omod-2.0/src/test/java/org/openmrs/module/webservices/rest/doc/SwaggerSpecificationCreatorTest.java +++ b/omod-2.0/src/test/java/org/openmrs/module/webservices/rest/doc/SwaggerSpecificationCreatorTest.java @@ -42,6 +42,7 @@ import org.openmrs.module.webservices.rest.web.api.RestService; import org.openmrs.module.webservices.rest.web.representation.Representation; import org.openmrs.module.webservices.rest.web.v1_0.resource.openmrs1_8.ObsResource1_8; +import org.openmrs.module.webservices.rest.web.v1_0.resource.openmrs1_8.PatientResource1_8; import org.openmrs.module.webservices.rest.web.v1_0.resource.openmrs1_8.PersonResource1_8; import org.openmrs.web.test.BaseModuleWebContextSensitiveTest; @@ -283,7 +284,7 @@ public void createOnlySubresourceDefinitions() { } @Test - public void generateGETModel_shouldCheckForOpenMRSResource() throws NoSuchFieldException { + public void generateGETModel_shouldCheckForOpenMRSResource() { Model model = SwaggerGenerationUtil.generateGETModel(new ObsResource1_8(), Representation.DEFAULT); Assert.assertTrue(model instanceof ModelImpl); @@ -305,7 +306,7 @@ public void generateGETModel_shouldCheckForOpenMRSResource() throws NoSuchFieldE } @Test - public void generateGETModel_shouldReturnAnArrayPropertyWithRefPropertyWhenFieldIsASet() throws NoSuchFieldException { + public void generateGETModel_shouldReturnAnArrayPropertyWithRefPropertyWhenFieldIsASet() { Model model = SwaggerGenerationUtil.generateGETModel(new PersonResource1_8(), Representation.DEFAULT); Assert.assertTrue(model instanceof ModelImpl); @@ -321,6 +322,24 @@ public void generateGETModel_shouldReturnAnArrayPropertyWithRefPropertyWhenField RefProperty refProperty = (RefProperty) arrayProperty.getItems(); assertEquals("#/definitions/PersonAttributeGet", refProperty.get$ref()); } + + @Test + public void generateGETModelPatient_shouldReturnAnArrayPropertyWithRefPropertyWhenFieldIsASet() { + Model model = SwaggerGenerationUtil.generateGETModel(new PatientResource1_8(), Representation.DEFAULT); + Assert.assertTrue(model instanceof ModelImpl); + + Map propertyMap = model.getProperties(); + System.out.println(propertyMap); + Assert.assertTrue(propertyMap.containsKey("identifiers")); + + Property property = propertyMap.get("identifiers"); + Assert.assertTrue(property instanceof ArrayProperty); + ArrayProperty arrayProperty = (ArrayProperty) property; + Assert.assertTrue(arrayProperty.getItems() instanceof RefProperty); + + RefProperty refProperty = (RefProperty) arrayProperty.getItems(); + assertEquals("#/definitions/PatientIdentifierGet", refProperty.get$ref()); + } /** * Ensure that resources not directly related to the webservices.rest package are successfully diff --git a/omod-common/src/main/java/org/openmrs/module/webservices/docs/swagger/SwaggerGenerationUtil.java b/omod-common/src/main/java/org/openmrs/module/webservices/docs/swagger/SwaggerGenerationUtil.java index 4d6b2df8d..6b226ddcb 100644 --- a/omod-common/src/main/java/org/openmrs/module/webservices/docs/swagger/SwaggerGenerationUtil.java +++ b/omod-common/src/main/java/org/openmrs/module/webservices/docs/swagger/SwaggerGenerationUtil.java @@ -21,9 +21,11 @@ import io.swagger.models.properties.RefProperty; import io.swagger.models.properties.StringProperty; import org.apache.commons.lang.StringUtils; +import org.openmrs.api.context.Context; import org.openmrs.module.webservices.docs.swagger.core.property.EnumProperty; import org.openmrs.module.webservices.rest.web.annotation.Resource; import org.openmrs.module.webservices.rest.web.annotation.SubResource; +import org.openmrs.module.webservices.rest.web.api.RestService; import org.openmrs.module.webservices.rest.web.representation.Representation; import org.openmrs.module.webservices.rest.web.resource.impl.DelegatingResourceDescription; import org.openmrs.module.webservices.rest.web.resource.impl.DelegatingResourceHandler; @@ -295,7 +297,7 @@ public static Property createPropertyForType(Class type, String operationType } else if (Set.class.equals(type) || List.class.equals(type)) { Class elementType = getGenericTypeFromField(field); if (isOpenMRSResource(elementType)) { - String resourceName = getResourceNameBySupportedClass(elementType); + String resourceName = getSubResourceNameBySupportedClass(elementType); if (resourceName == null) { return new StringProperty(); } @@ -335,6 +337,31 @@ public static String getResourceNameBySupportedClass(Class supportedClass) { return null; } + public static String getSubResourceNameBySupportedClass(Class supportedClass) { + org.openmrs.module.webservices.rest.web.resource.api.Resource resource = Context.getService(RestService.class).getResourceHandlerForSupportedClass(supportedClass); + + if (resource == null) { + return null; + } + + Resource annotation = resource.getClass().getAnnotation(Resource.class); + SubResource subResourceAnnotation = resource.getClass().getAnnotation(SubResource.class); + + if (annotation != null && annotation.supportedClass().equals(supportedClass)) { + return annotation.name().substring(annotation.name().indexOf('/') + 1); + } else if (subResourceAnnotation != null && subResourceAnnotation.supportedClass().equals(supportedClass)) { + Resource parentResourceAnnotation = subResourceAnnotation.parent().getAnnotation(Resource.class); + + String resourceName = subResourceAnnotation.path(); + String resourceParentName = parentResourceAnnotation.name().substring( + parentResourceAnnotation.name().indexOf('/') + 1); + + String combinedName = capitalize(resourceParentName) + capitalize(resourceName); + return combinedName.replace("/", ""); + } + return null; + } + public static String capitalize(String name) { if (name == null || name.isEmpty()) return name; return name.substring(0, 1).toUpperCase() + name.substring(1); diff --git a/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/RestService.java b/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/RestService.java index 4922db767..d1a1f95b4 100644 --- a/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/RestService.java +++ b/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/RestService.java @@ -73,7 +73,14 @@ public interface RestService { * @throws APIException */ public List> getResourceHandlers() throws APIException; - + + + /** + * @param resourceClass the resource class e.g PatientIdentifier.class + * @return the resource handler for the provided class e.g PatientIdentifierResource1_8 + */ + Resource getResourceHandlerForSupportedClass(Class resourceClass); + /** * Initializes all Resources and Search handlers for use; called after module startup */ diff --git a/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/impl/RestServiceImpl.java b/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/impl/RestServiceImpl.java index 9ffc4c06e..02ab424ea 100644 --- a/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/impl/RestServiceImpl.java +++ b/omod-common/src/main/java/org/openmrs/module/webservices/rest/web/api/impl/RestServiceImpl.java @@ -442,7 +442,7 @@ public Resource getResourceBySupportedClass(Class resourceClass) throws APIEx if (HibernateProxy.class.isAssignableFrom(resourceClass)) { resourceClass = resourceClass.getSuperclass(); } - + Resource resource = resourcesBySupportedClasses.get(resourceClass); if (resource == null) { @@ -689,6 +689,19 @@ public Set getSearchHandlers(String resourceName) { } return searchHandlersByResource.get(resourceName); } + + /** + * @see RestService#getResourceHandlerForSupportedClass(Class) + * Should return search resources for given resource class + * @param resourceClass the resource class e.g. PatientIdentifier + */ + @Override + public Resource getResourceHandlerForSupportedClass(Class resourceClass) { + if (resourcesBySupportedClasses == null) { + initializeResources(); + } + return resourcesBySupportedClasses.get(resourceClass); + } /** * @see RestService#initialize()