From d11d82b9e01fc79b2555f1a9ad89cdf29a6a4773 Mon Sep 17 00:00:00 2001 From: Deepak Michael Date: Wed, 17 Aug 2011 20:46:44 +0530 Subject: [PATCH] Swagger: AS3 sdk - templates, structure and updates for generating as3 library --- build.xml | 22 +- conf/as3/sample/as3_code_gen_conf.json | 30 +++ conf/as3/structure/lib/ASAXB-0.1.1.swc | Bin 0 -> 46948 bytes .../com/wordnik/swagger/common/ApiInvoker.as | 223 ++++++++++++++++++ .../wordnik/swagger/common/ApiUrlHelper.as | 42 ++++ .../swagger/common/ApiUserCredentials.as | 55 +++++ .../com/wordnik/swagger/common/SwaggerApi.as | 82 +++++++ .../com/wordnik/swagger/common/XMLWriter.as | 28 +++ .../wordnik/swagger/event/ApiClientEvent.as | 36 +++ .../as3/com/wordnik/swagger/event/Response.as | 52 ++++ .../com/wordnik/swagger/exception/ApiError.as | 10 + .../swagger/exception/ApiErrorCodes.as | 34 +++ .../swagger/model/DefinitionWrapper.as | 13 + conf/as3/templates/EnumObject.st | 30 +++ conf/as3/templates/ModelObject.st | 29 +++ conf/as3/templates/ResourceObject.st | 111 +++++++++ conf/as3/templates/VersionChecker.st | 20 ++ .../swagger/codegen/FieldDefinition.java | 8 + .../swagger/codegen/LibraryCodeGenerator.java | 65 ++++- .../swagger/codegen/ResourceMethod.java | 11 +- .../config/DataTypeMappingProvider.java | 10 + .../codegen/config/LanguageConfiguration.java | 20 ++ .../codegen/config/NamingPolicyProvider.java | 12 + .../as3/As3DataTypeMappingProvider.java | 185 +++++++++++++++ .../codegen/config/as3/As3LibCodeGen.java | 85 +++++++ .../config/as3/As3NamingPolicyProvider.java | 25 ++ .../common/CamelCaseNamingPolicyProvider.java | 14 ++ .../java/JavaDataTypeMappingProvider.java | 13 +- .../codegen/resource/EndpointOperation.java | 18 +- .../swagger/codegen/resource/ModelField.java | 9 +- 30 files changed, 1282 insertions(+), 10 deletions(-) create mode 100644 conf/as3/sample/as3_code_gen_conf.json create mode 100644 conf/as3/structure/lib/ASAXB-0.1.1.swc create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/common/ApiInvoker.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/common/ApiUrlHelper.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/common/ApiUserCredentials.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/common/SwaggerApi.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/common/XMLWriter.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/event/ApiClientEvent.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/event/Response.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiError.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiErrorCodes.as create mode 100644 conf/as3/structure/src/main/as3/com/wordnik/swagger/model/DefinitionWrapper.as create mode 100644 conf/as3/templates/EnumObject.st create mode 100644 conf/as3/templates/ModelObject.st create mode 100644 conf/as3/templates/ResourceObject.st create mode 100644 conf/as3/templates/VersionChecker.st create mode 100644 src/main/java/com/wordnik/swagger/codegen/config/as3/As3DataTypeMappingProvider.java create mode 100644 src/main/java/com/wordnik/swagger/codegen/config/as3/As3LibCodeGen.java create mode 100644 src/main/java/com/wordnik/swagger/codegen/config/as3/As3NamingPolicyProvider.java diff --git a/build.xml b/build.xml index 39d67768494..b88687f74f1 100644 --- a/build.xml +++ b/build.xml @@ -104,7 +104,7 @@ Must specify the parameter for apiConfiguration - eg. -DapiConfiguration==../api-server-lib/java/config/apiConfiguration.json + eg. -DapiConfiguration=../api-server-lib/java/config/apiConfiguration.json apiConfiguration to be used : ${apiConfiguration} @@ -120,6 +120,26 @@ + + + + Must specify the parameter for apiConfiguration + eg. -DapiConfiguration=../api-server-lib/as3/config/apiConfiguration.json + + + apiConfiguration to be used : ${apiConfiguration} + + + + + + + + + + + + diff --git a/conf/as3/sample/as3_code_gen_conf.json b/conf/as3/sample/as3_code_gen_conf.json new file mode 100644 index 00000000000..7d95d614b7c --- /dev/null +++ b/conf/as3/sample/as3_code_gen_conf.json @@ -0,0 +1,30 @@ +{ + "apiUrl":"http://swagr.api.wordnik.com/v4/", + + "apiKey":"special-key", + + "defaultServiceBaseClass":"SwaggerApi", + + "defaultModelBaseClass":"Object", + + "serviceBaseClasses":{}, + + "defaultModelImports":[], + + "defaultServiceImports":["mx.rpc.AsyncToken","mx.utils.UIDUtil", + "flash.utils.Dictionary","flash.events.EventDispatcher", + "com.wordnik.swagger.common.ApiUserCredentials","com.wordnik.swagger.event.Response", + "com.wordnik.swagger.common.SwaggerApi"], + + "modelPackageName":"com.wordnik.swagger.model", + + "apiPackageName":"com.wordnik.swagger.api", + + "ignoreMethods":["WordAPI.getWordFrequency","WordAPI.getAudio","WordAPI.getWordStats","WordAPI.getFlickrImages"], + + "ignoreModels":["wordStats","photo","sizes"], + + "outputDirectory":"../api-server-temp/as3ApiSDK/src/main/as3/com/wordnik/swagger/", + + "libraryHome":"../api-server-temp/as3ApiSDK" +} \ No newline at end of file diff --git a/conf/as3/structure/lib/ASAXB-0.1.1.swc b/conf/as3/structure/lib/ASAXB-0.1.1.swc new file mode 100644 index 0000000000000000000000000000000000000000..c93590267846ce45564dfeff8275a0030e39b2fc GIT binary patch literal 46948 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 + } + + public function reset():void { + xml=new XML(); + } + + public function addProperty(propertyName:String, propertyValue:String):XML { + var xmlProperty:XML= + xmlProperty.setName(propertyName); + xmlProperty.appendChild(propertyValue); + xml.appendChild(xmlProperty); + return xmlProperty; + } + + public function addAttribute(propertyName:String, attribute:String, attributeValue:String):void { + xml.elements(propertyName)[0].@[attribute]=attributeValue; + } + } +} \ No newline at end of file diff --git a/conf/as3/structure/src/main/as3/com/wordnik/swagger/event/ApiClientEvent.as b/conf/as3/structure/src/main/as3/com/wordnik/swagger/event/ApiClientEvent.as new file mode 100644 index 00000000000..5484669a3f2 --- /dev/null +++ b/conf/as3/structure/src/main/as3/com/wordnik/swagger/event/ApiClientEvent.as @@ -0,0 +1,36 @@ +package com.wordnik.swagger.event { +import com.wordnik.swagger.event.Response; + +import flash.events.Event; + +/** + * Event dispatched by the SDK to communicate success events and failure events. + * If a custom dispatcher has been assigned by the consumer on the WordnikClient then the dispatcher dispatches + * the ApiClientEvent to indicate success or failure of the invocation using the Response + */ +public class ApiClientEvent extends Event{ + + /** + * Event type to indicate a unsuccessful invocation + */ + public static const FAILURE_EVENT:String = "unsuccesfulInvocation"; + + /** + * Event type to indicate a successful invocation + */ + public static const SUCCESS_EVENT:String = "successfulInvocation"; + + /** + * The Response object which contains response info + */ + public var response: Response; + /** + * Any additional info + */ + public var message:String; + + public function ApiClientEvent(type:String,bubbles:Boolean = false,cancelable:Boolean = false) { + super(type, bubbles, cancelable); + } +} +} \ No newline at end of file diff --git a/conf/as3/structure/src/main/as3/com/wordnik/swagger/event/Response.as b/conf/as3/structure/src/main/as3/com/wordnik/swagger/event/Response.as new file mode 100644 index 00000000000..f09aae7e90a --- /dev/null +++ b/conf/as3/structure/src/main/as3/com/wordnik/swagger/event/Response.as @@ -0,0 +1,52 @@ +package com.wordnik.swagger.event { + +/** + * Response contains info on the result of a Wordnik API invocation. + * A completion listener will expect this WNResult object as a parameter. + */ +public class Response { + + /** + * Indicates whether the invoked operation failed or succeeded + */ + public var isSuccess:Boolean; + + /** + * The payload of the succesful operation eg. a Word in a WordRequest + */ + public var payload:Object; + + /** + * Error message in case of failure + */ + public var errorMessage:String; + + /** + * A request Id that was passed in by the user as a param when invoking the operation + */ + public var requestId:String; + private static const API_ERROR_MSG:String = "Api error response: "; + + public function Response(isSuccessful: Boolean, payload: Object = null, errorMessage: String = null, requestId: String = null) { + this.isSuccess = isSuccessful; + this.payload = payload; + this.errorMessage = getFriendlyMessage(errorMessage); + } + + private static function getFriendlyMessage(errorMessage: String): String{ + var result: String = errorMessage; + if(errorMessage == null) + return null; + var errorCode: String; + var errorCodeArray: Array = errorMessage.match(/(?<=HTTP\/1.1 )[0-9][0-9][0-9]/); + if(errorCodeArray != null && errorCodeArray.length == 1){ + errorCode = String(errorCodeArray[0]); + } + var msgArray: Array = errorMessage.match(/(?<=HTTP\/1.1 [0-9][0-9][0-9] )[^]*/); + if(msgArray != null && msgArray.length == 1){ + result = API_ERROR_MSG + String(msgArray[0]); + } + return result; + } +} +} \ No newline at end of file diff --git a/conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiError.as b/conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiError.as new file mode 100644 index 00000000000..13d09415829 --- /dev/null +++ b/conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiError.as @@ -0,0 +1,10 @@ +package com.wordnik.swagger.exception +{ + public class ApiError extends Error + { + public function ApiError(id:*=0, message:*="") + { + super(message,id); + } + } +} \ No newline at end of file diff --git a/conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiErrorCodes.as b/conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiErrorCodes.as new file mode 100644 index 00000000000..abe12178361 --- /dev/null +++ b/conf/as3/structure/src/main/as3/com/wordnik/swagger/exception/ApiErrorCodes.as @@ -0,0 +1,34 @@ +package com.wordnik.swagger.exception +{ + public class ApiErrorCodes + { + /** + * System exception. + */ + public static const SYSTEM_EXCEPTION: Number = 0; + + /** + * With Arguments as current key. + */ + public static const API_KEY_NOT_VALID: Number = 1000; + /** + * With arguments as current token value + */ + public static const AUTH_TOKEN_NOT_VALID: Number = 1001; + /** + * With arguments as input JSON and output class anme + */ + public static const ERROR_CONVERTING_JSON_TO_JAVA: Number = 1002; + /** + * With arguments as JAVA class name + */ + public static const ERROR_CONVERTING_JAVA_TO_JSON: Number = 1003; + + public static const ERROR_FROM_WEBSERVICE_CALL: Number = 1004; + /** + * With arguments as current API server name + */ + public static const API_SERVER_NOT_VALID: Number = 1005; + + } +} \ No newline at end of file diff --git a/conf/as3/structure/src/main/as3/com/wordnik/swagger/model/DefinitionWrapper.as b/conf/as3/structure/src/main/as3/com/wordnik/swagger/model/DefinitionWrapper.as new file mode 100644 index 00000000000..82e48aa1d64 --- /dev/null +++ b/conf/as3/structure/src/main/as3/com/wordnik/swagger/model/DefinitionWrapper.as @@ -0,0 +1,13 @@ +package com.wordnik.swagger.model +{ + public class DefinitionWrapper + { + /** + * + * + * + */ + [XmlElements(name="definition", type="com.wordnik.swagger.model.Definition")] + public var definition: Array = new Array(); + } +} \ No newline at end of file diff --git a/conf/as3/templates/EnumObject.st b/conf/as3/templates/EnumObject.st new file mode 100644 index 00000000000..9cbc2c661c5 --- /dev/null +++ b/conf/as3/templates/EnumObject.st @@ -0,0 +1,30 @@ +package $packageName$; + +$imports:{ import | +import $import$; +}$ + +/** + * $enum.description$ + * NOTE: This class is auto generated by the drive code generator program so please do not edit the class manually. + * @author deepak + * + */ +public enum $className$ { + + $values: { value | $value.name$($value.value$)};separator=", "$; + + final $enumValueType$ value; + + $className$($enumValueType$ value) { + this.value = value; + } + + public $enumValueType$ getValue() { + return value; + } + + @Override public String toString() { + return String.valueOf(this.getValue()); + } +}; \ No newline at end of file diff --git a/conf/as3/templates/ModelObject.st b/conf/as3/templates/ModelObject.st new file mode 100644 index 00000000000..e8e00f07c22 --- /dev/null +++ b/conf/as3/templates/ModelObject.st @@ -0,0 +1,29 @@ +package $packageName$ { + +$imports:{ import | +import $import$; +}$ + + /** + * $model.description$ + * NOTE: This class is auto generated by the drive code generator program so please do not edit the class manually. + * @author deepak + * + */ + public class $className$ extends $extends$ { + + $fields:{ field | + + /** + * $field.description$ + * $if(field.required)$@Required$endif$ + * $if(field.allowableValues)$[AllowableValues(value="$field.allowedValuesString$"]$endif$ + */ +$if(!field.fieldDefinition.collectionItemType)$ + [XmlElement(name="$field.fieldDefinition.name$")]$endif$ +$if(field.fieldDefinition.collectionItemType)$ + [XmlElements(name="$field.fieldDefinition.name$", type="$field.fieldDefinition.collectionItemType$")]$endif$ + public var $field.fieldDefinition.name$: $field.fieldDefinition.returnType$ $field.fieldDefinition.initialization$;$\r$}$ + + } +} \ No newline at end of file diff --git a/conf/as3/templates/ResourceObject.st b/conf/as3/templates/ResourceObject.st new file mode 100644 index 00000000000..20ae8ce82a2 --- /dev/null +++ b/conf/as3/templates/ResourceObject.st @@ -0,0 +1,111 @@ +package $packageName$ { + + +import $exceptionPackageName$.ApiErrorCodes; +import $exceptionPackageName$.ApiError; +import $modelPackageName$.*; + + +$imports:{ import | +import $import$; +}$ + + /** + * NOTE: This class is auto generated by the drive code generator program so please do not edit the class manually. + * @author deepak + * + */ + public class $resource$ extends $extends$ { + + /** + * Constructor for the $resource$ api client + * @param apiCredentials Wrapper object for tokens and hostName required towards authentication + * @param eventDispatcher Optional event dispatcher that when provided is used by the SDK to dispatch any Response + */ + public function $resource$(apiCredentials: ApiUserCredentials, eventDispatcher: EventDispatcher = null) { + super(apiCredentials, eventDispatcher); + } + + +$methods:{ method | + /** + * $method.description$ +$method.arguments:{ argument | + * @param $argument.name$ $argument.description$ + $if(argument.allowedValues)$ + * Allowed values are - $argument.allowedValues$ + $endif$}$ + * +$if(!method.responseVoid)$ + * @return $method.returnValue$ {@link $method.returnClassName$} $endif$ + */ +$if(method.hasArguments)$ + [MethodArgumentNames(value="$method.argumentNames; separator=", "$")]$endif$ + public function $method.name$($method.argumentDefinitions; separator=", "$): String { + +$if(method.authToken)$ + if(authToken == null || authToken.length == 0) { + throw new ApiError(ApiErrorCodes.AUTH_TOKEN_NOT_VALID); + }$endif$ + var requestId: String = getUniqueId(); + //parse inputs + var resourcePath: String = "$method.resourcePath$"; + resourcePath = resourcePath.replace("{format}","xml"); + var method: String = "$method.methodType$"; + var queryParams:Dictionary = new Dictionary(); +$if(!method.inputModel)$ +$method.queryParameters:{ argument | + if( $argument.name$ != null) { + queryParams["$argument.name$"] = toPathValue($argument.name$); + } +}$ +$method.pathParameters:{ argument | + if( $argument.name$ != null) { + resourcePath = resourcePath.replace("{$argument.name$}", $argument.name$); + } +}$ +$endif$ +$if(method.inputModel)$ +$method.queryParameters:{ argument | + if( $argument.inputModelClassArgument$ != null && $argument.methodNameFromModelClass$ != null) { + queryParams["$argument.name$"] = $argument.methodNameFromModelClass$; + } +}$ +$method.pathParameters:{ argument | + if( $argument.inputModelClassArgument$ != null && $argument.methodNameFromModelClass$ != null) { + resourcePath = resourcePath.replace("{$argument.name$}", $argument.methodNameFromModelClass$); + } +}$ +$endif$ + //make the API Call +$if(method.postObject)$ +$if(method.authToken)$ + var token:AsyncToken = getApiInvoker().invokeAPI(authToken, resourcePath, method, queryParams, postData); +$endif$ +$if(!method.authToken)$ + var token:AsyncToken = getApiInvoker().invokeAPI(null, resourcePath, method, queryParams, postData); +$endif$ +$endif$ + +$if(!method.postObject)$ +$if(method.authToken)$ + var token:AsyncToken = getApiInvoker().invokeAPI(authToken, resourcePath, method, queryParams, null); +$endif$ +$if(!method.authToken)$ + var token:AsyncToken = getApiInvoker().invokeAPI(null, resourcePath, method, queryParams, null); +$endif$ +$endif$ + + token.requestId = requestId; + token.completionEventType = "$method.name$"; + + //create output objects if the response has more than one object +$if(!method.responseVoid)$ + token.returnType = $method.returnClassName$; + +$endif$ + return requestId; + } +}$ + } +} diff --git a/conf/as3/templates/VersionChecker.st b/conf/as3/templates/VersionChecker.st new file mode 100644 index 00000000000..76fc590418a --- /dev/null +++ b/conf/as3/templates/VersionChecker.st @@ -0,0 +1,20 @@ +package $packageName$ { + +/** + * Maintains the compatible server version against which the drive is written + * @author deepak + * + */ + public class VersionChecker { + + private var compatibleVersion: String = "$apiVersion$"; + + /** + * Gets the version against which the driver code was written + */ + public function getCompatibleVersion(): String { + return compatibleVersion; + } + } + +} \ No newline at end of file diff --git a/src/main/java/com/wordnik/swagger/codegen/FieldDefinition.java b/src/main/java/com/wordnik/swagger/codegen/FieldDefinition.java index 615e24fe5cf..c357d0b6feb 100644 --- a/src/main/java/com/wordnik/swagger/codegen/FieldDefinition.java +++ b/src/main/java/com/wordnik/swagger/codegen/FieldDefinition.java @@ -28,6 +28,8 @@ public class FieldDefinition { private String initialization; private List importDefinitions = new ArrayList(); + + private String collectionItemType; public String getReturnType() { return returnType; @@ -61,5 +63,11 @@ public class FieldDefinition { return name.substring(0,1).toUpperCase() + name.substring(1); } + public void setCollectionItemType(String collectionItemType) { + this.collectionItemType = collectionItemType; + } + public String getCollectionItemType() { + return collectionItemType; + } } diff --git a/src/main/java/com/wordnik/swagger/codegen/LibraryCodeGenerator.java b/src/main/java/com/wordnik/swagger/codegen/LibraryCodeGenerator.java index 622966190ae..540b081d001 100644 --- a/src/main/java/com/wordnik/swagger/codegen/LibraryCodeGenerator.java +++ b/src/main/java/com/wordnik/swagger/codegen/LibraryCodeGenerator.java @@ -106,7 +106,13 @@ public class LibraryCodeGenerator { } generateModelClasses(resources, aTemplateGroup); generateModelClassesForInput(resources, aTemplateGroup); - generateEnumForAllowedValues(resources, aTemplateGroup); + if(languageConfig.isGenerateHelperEnums()){ + generateEnumForAllowedValues(resources, aTemplateGroup); + } + + if(languageConfig.isGenerateOutputWrappers()) { + generateOutputWrappers(resources, aTemplateGroup); + } generateAPIClasses(resources, aTemplateGroup); } @@ -139,7 +145,7 @@ public class LibraryCodeGenerator { List imports = new ArrayList(); imports.addAll(this.config.getDefaultModelImports()); for(ModelField param : model.getFields()){ - for(String importDef : param.getFieldDefinition(this.getDataTypeMappingProvider()).getImportDefinitions()){ + for(String importDef : param.getFieldDefinition(this.getDataTypeMappingProvider(), config, nameGenerator).getImportDefinitions()){ if(!imports.contains(importDef)){ imports.add(importDef); } @@ -182,7 +188,7 @@ public class LibraryCodeGenerator { List imports = new ArrayList(); imports.addAll(this.config.getDefaultModelImports()); for(ModelField param : model.getFields()){ - for(String importDef : param.getFieldDefinition(this.getDataTypeMappingProvider()).getImportDefinitions()){ + for(String importDef : param.getFieldDefinition(this.getDataTypeMappingProvider(), config, nameGenerator).getImportDefinitions()){ if(!imports.contains(importDef)){ imports.add(importDef); } @@ -265,6 +271,57 @@ public class LibraryCodeGenerator { } } + private void generateOutputWrappers(List resources, StringTemplateGroup templateGroup) { + List generatedClasses = new ArrayList(); + StringTemplate template; + + for(Resource resource: resources) { + if(resource.getEndPoints() != null) { + for(Endpoint endpoint : resource.getEndPoints()){ + if(endpoint.getOperations() != null) { + for(EndpointOperation operation : endpoint.getOperations()){ + ResourceMethod method = operation.generateMethod(endpoint, resource, dataTypeMappingProvider, nameGenerator); + if(codeGenRulesProvider.isModelIgnored( nameGenerator.applyMethodNamingPolicy( method.getReturnClassName() ))){ + continue; + } + if(method.getOutputWrapperModel() != null) { + Model model = method.getOutputWrapperModel(); + method.setReturnClassName(model.getName()); + if(model != null){ + if(!generatedClasses.contains(model.getName())) { + List imports = new ArrayList(); + imports.addAll(this.config.getDefaultModelImports()); + for(ModelField param : model.getFields()){ + for(String importDef : param.getFieldDefinition(this.getDataTypeMappingProvider(), config, nameGenerator).getImportDefinitions()){ + if(!imports.contains(importDef)){ + imports.add(importDef); + } + } + } + template = templateGroup.getInstanceOf(MODEL_OBJECT_TEMPLATE); + + template.setAttribute("fields", model.getFields()); + template.setAttribute("imports", imports); + template.setAttribute("extends", config.getDefaultModelBaseClass()); + template.setAttribute("annotationPackageName", languageConfig.getAnnotationPackageName()); + template.setAttribute("className", model.getGenratedClassName()); + template.setAttribute(PACKAGE_NAME, config.getModelPackageName()); + File aFile = new File(languageConfig.getModelClassLocation()+model.getGenratedClassName()+languageConfig.getClassFileExtension()); + writeFile(aFile, template.toString(), "Output wrapper model class"); + generatedClasses.add(model.getName()); + } + } + } + + } + } + } + } + } + + + } + /** * Generates one API class for each resource and each end point in the resource is translated as method. * @param resources @@ -328,7 +385,7 @@ public class LibraryCodeGenerator { imports.addAll(this.config.getDefaultModelImports()); imports.addAll(this.getDataTypeMappingProvider().getListIncludes()); for(ModelField param : model.getFields()){ - for(String importDef : param.getFieldDefinition(this.getDataTypeMappingProvider()).getImportDefinitions()){ + for(String importDef : param.getFieldDefinition(this.getDataTypeMappingProvider(), config, nameGenerator).getImportDefinitions()){ if(!imports.contains(importDef)){ imports.add(importDef); } diff --git a/src/main/java/com/wordnik/swagger/codegen/ResourceMethod.java b/src/main/java/com/wordnik/swagger/codegen/ResourceMethod.java index 151479de00f..f8b551f998f 100644 --- a/src/main/java/com/wordnik/swagger/codegen/ResourceMethod.java +++ b/src/main/java/com/wordnik/swagger/codegen/ResourceMethod.java @@ -53,7 +53,8 @@ public class ResourceMethod { private boolean postObject; private Model inputModel; - + + private Model outputWrapperModel; public String getTitle() { return title; @@ -200,4 +201,12 @@ public class ResourceMethod { } return false; } + + public void setOutputWrapperModel(Model outputWrapperModel) { + this.outputWrapperModel = outputWrapperModel; + } + + public Model getOutputWrapperModel() { + return outputWrapperModel; + } } diff --git a/src/main/java/com/wordnik/swagger/codegen/config/DataTypeMappingProvider.java b/src/main/java/com/wordnik/swagger/codegen/config/DataTypeMappingProvider.java index 947e5397128..db7ddc3d3f7 100644 --- a/src/main/java/com/wordnik/swagger/codegen/config/DataTypeMappingProvider.java +++ b/src/main/java/com/wordnik/swagger/codegen/config/DataTypeMappingProvider.java @@ -187,4 +187,14 @@ public interface DataTypeMappingProvider { * @return */ public String getGenericType(String type); + + /** + * Returns the syntax for defintion of an object of type and name + * + * @param argumentType + * @param argumentName + * @return + */ + public String getArgumentDefinition(String argumentType, String argumentName); + } diff --git a/src/main/java/com/wordnik/swagger/codegen/config/LanguageConfiguration.java b/src/main/java/com/wordnik/swagger/codegen/config/LanguageConfiguration.java index 57bdf721088..a70dbbb16d0 100644 --- a/src/main/java/com/wordnik/swagger/codegen/config/LanguageConfiguration.java +++ b/src/main/java/com/wordnik/swagger/codegen/config/LanguageConfiguration.java @@ -41,6 +41,10 @@ public class LanguageConfiguration { private String annotationPackageName; + private boolean generateHelperEnums = true; + + private boolean generateOutputWrappers = false; + public String getClassFileExtension() { return classFileExtension; } @@ -109,4 +113,20 @@ public class LanguageConfiguration { public void setLibraryHome(String libraryHome) { this.libraryHome = libraryHome; } + + public void setGenerateHelperEnums(boolean generateHelperEnums) { + this.generateHelperEnums = generateHelperEnums; + } + + public boolean isGenerateHelperEnums() { + return generateHelperEnums; + } + + public void setGenerateOutputWrappers(boolean generateOutputWrappers) { + this.generateOutputWrappers = generateOutputWrappers; + } + + public boolean isGenerateOutputWrappers() { + return generateOutputWrappers; + } } diff --git a/src/main/java/com/wordnik/swagger/codegen/config/NamingPolicyProvider.java b/src/main/java/com/wordnik/swagger/codegen/config/NamingPolicyProvider.java index b85b0042256..185dfac8d1d 100644 --- a/src/main/java/com/wordnik/swagger/codegen/config/NamingPolicyProvider.java +++ b/src/main/java/com/wordnik/swagger/codegen/config/NamingPolicyProvider.java @@ -97,6 +97,18 @@ public interface NamingPolicyProvider { */ public String getInputObjectName(String serviceName, String resourcePath); + /** + * Generate the name of the wrapper class used as a wrapper for a list of items returned by a service + * + * Example: get definitions API returns a list of definition objects as the result. This will be wrapped by an + * object. The object's name will be determined by invoking this service. + * eg. DefinitionList for a wrapper of 'definition's + * + * @param wrapperItemName + * @return + */ + public String getOutputWrapperName(String wrapperItemName); + /** * Generates a name for an enum for the param or field name. * diff --git a/src/main/java/com/wordnik/swagger/codegen/config/as3/As3DataTypeMappingProvider.java b/src/main/java/com/wordnik/swagger/codegen/config/as3/As3DataTypeMappingProvider.java new file mode 100644 index 00000000000..045749d6833 --- /dev/null +++ b/src/main/java/com/wordnik/swagger/codegen/config/as3/As3DataTypeMappingProvider.java @@ -0,0 +1,185 @@ +package com.wordnik.swagger.codegen.config.as3; + +import com.wordnik.swagger.codegen.config.DataTypeMappingProvider; +import com.wordnik.swagger.codegen.config.NamingPolicyProvider; +import com.wordnik.swagger.codegen.config.common.CamelCaseNamingPolicyProvider; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +/** + * User: ramesh + * Date: 5/31/11 + * Time: 7:03 AM + */ +public class As3DataTypeMappingProvider implements DataTypeMappingProvider { + + public static Map primitiveValueMap = new HashMap(); + static{ + primitiveValueMap.put("string", "String"); + primitiveValueMap.put("String", "String"); + primitiveValueMap.put("int", "Number"); + primitiveValueMap.put("integer", "int"); + primitiveValueMap.put("Integer", "int"); + primitiveValueMap.put("boolean", "Boolean"); + primitiveValueMap.put("Boolean", "Boolean"); + primitiveValueMap.put("long", "Number"); + primitiveValueMap.put("Long", "Number"); + primitiveValueMap.put("double", "Number"); + primitiveValueMap.put("Double", "Number"); + primitiveValueMap.put("float", "Number"); + primitiveValueMap.put("Float", "Number"); + primitiveValueMap.put("Date", "Date"); + primitiveValueMap.put("date", "Date"); + } + + public static Map primitiveObjectMap = new HashMap(); + static{ + primitiveObjectMap.put("string", "String"); + primitiveObjectMap.put("String", "String"); + primitiveObjectMap.put("int", "int"); + primitiveObjectMap.put("integer", "int"); + primitiveObjectMap.put("Integer", "int"); + primitiveObjectMap.put("boolean", "Boolean"); + primitiveObjectMap.put("Boolean", "Boolean"); + primitiveObjectMap.put("long", "Number"); + primitiveObjectMap.put("Long", "Number"); + primitiveObjectMap.put("double", "Number"); + primitiveObjectMap.put("Double", "Number"); + primitiveObjectMap.put("float", "Number"); + primitiveObjectMap.put("Float", "Number"); + primitiveObjectMap.put("Date", "Date"); + primitiveObjectMap.put("date", "Date"); + } + + private NamingPolicyProvider nameGenerator = new CamelCaseNamingPolicyProvider(); + + public boolean isPrimitiveType(String type) { + if(type.equalsIgnoreCase("String") || type.equalsIgnoreCase("int") || type.equalsIgnoreCase("integer") || type.equalsIgnoreCase("double") || + type.equalsIgnoreCase("boolean") || type.equalsIgnoreCase("float")|| type.equalsIgnoreCase("long") || type.equalsIgnoreCase("Number") ){ + return true; + } + return false; + } + + /** + * If the data type is primitive and it is expecting object structure then return primitive objects + * else return primitive types + * @param type + * @param primitiveObject -- indicates if the object is primitive or not + * @return + */ + public String getObjectType(String type, boolean primitiveObject) { + if(isPrimitiveType(type)){ + if(primitiveObject){ + return primitiveObjectMap.get(type); + }else{ + return primitiveValueMap.get(type); + } + }else{ + return nameGenerator.applyClassNamingPolicy(type); + } + } + + public String getListReturnTypeSignature(String typeClass) { + return "Array"; + } + + public String getReturnTypeForVoidMethods() { + return "void"; + } + + public String getMapReturnTypeSignature(String typeClass) { + return "Object"; + } + + public String getSetReturnTypeSignature(String typeClass) { + return "Array"; + } + + public String generateListInitialization(String typeClass) { + return " new Array()"; + } + + public String generateMapInitialization(String typeClass) { + return " new Object()"; + } + + public String generateSetInitialization(String typeClass) { + return " new Array()"; + } + + public List getListIncludes() { + List imports = new ArrayList(); + return imports; + } + + public List getMapIncludes() { + List imports = new ArrayList(); + imports.add("flash.utils.Dictionary"); + return imports; + } + + public List getSetIncludes() { + List imports = new ArrayList(); + return imports; } + + + public List getDateIncludes() { + List imports = new ArrayList(); + return imports; + } + + /** + * Gets the short name of the class the class. + * Input can be MAP, LIST or regular string. In case of map or list the class name will be class name + * that map or list is returning. + * @param type + * @return + */ + public String getClassType(String type, boolean primitiveObject) { + String classShortName = ""; + if(type.startsWith("List[")){ + classShortName = type.substring(5, type.length()-1); + classShortName = getObjectType(classShortName, true); + }else if (type.startsWith("Map[")) { + classShortName = type.substring(4, type.length()-1); + classShortName = getObjectType(classShortName, true); + }else if (type.startsWith("Set[")) { + classShortName = type.substring(4, type.length()-1); + classShortName = getObjectType(classShortName, true); + }else if (type.equals("ok")) { + classShortName = "void"; + }else{ + classShortName = getObjectType(type, true); + } + return classShortName; + } + + public String getArgumentDefinition(String argumentType, String argumentName) { + return argumentName + ": " + argumentType; + } + + /** + * Gets the class of the expected return value for a type string. Examples of type Strings are int, User, List[User] + * If the type string is a collection type like a map or list the string value returned would be the class + * that map or list is returning. + * + * @param type + * @return + */ + public String getGenericType(String type) { + if(type.equalsIgnoreCase("void")|| type.equalsIgnoreCase("ok")){ + return "void"; + } + String classShortName = ""; + if(type.startsWith("List[") || type.startsWith("Map[") || type.startsWith("Set[")){ + classShortName = "Array"; + }else{ + classShortName = getObjectType(type, true); + } + return classShortName; + } +} diff --git a/src/main/java/com/wordnik/swagger/codegen/config/as3/As3LibCodeGen.java b/src/main/java/com/wordnik/swagger/codegen/config/as3/As3LibCodeGen.java new file mode 100644 index 00000000000..473bb03ff21 --- /dev/null +++ b/src/main/java/com/wordnik/swagger/codegen/config/as3/As3LibCodeGen.java @@ -0,0 +1,85 @@ +package com.wordnik.swagger.codegen.config.as3; + +import com.wordnik.swagger.codegen.LibraryCodeGenerator; +import com.wordnik.swagger.codegen.config.LanguageConfiguration; +import com.wordnik.swagger.codegen.config.common.CamelCaseNamingPolicyProvider; +import com.wordnik.swagger.codegen.exception.CodeGenerationException; +import com.wordnik.swagger.codegen.util.FileUtil; + +import java.io.File; + +/** + * User: deepakmichael + * Date: 17/08/11 + * Time: 5:02 PM + */ +public class As3LibCodeGen extends LibraryCodeGenerator{ + public static void main(String[] args) { + if(args.length < 1){ + throw new CodeGenerationException("Invalid number of arguments passed: No command line argument was passed to the program for config json"); + } + if(args.length == 1) { + String configPath = args[0]; + As3LibCodeGen codeGenerator = new As3LibCodeGen(configPath); + codeGenerator.generateCode(); + } + if(args.length == 4) { + String apiServerURL = args[0]; + if(!apiServerURL.endsWith("/")){ + apiServerURL = apiServerURL + "/"; + } + String apiKey = args[1]; + String packageName = args[2]; + String libraryHome = args[3]; + if(libraryHome.endsWith("/")){ + libraryHome = libraryHome.substring(0, libraryHome.length()-1); + } + String modelPackageName = packageName+".model"; + String apiPackageName = packageName+".api"; + String classOutputDir = libraryHome + "/src/main/as3/" + packageName.replace(".","/"); + As3LibCodeGen codeGenerator = new As3LibCodeGen(apiServerURL, apiKey, modelPackageName, + apiPackageName, classOutputDir, libraryHome); + codeGenerator.generateCode(); + } + + } + + public As3LibCodeGen(String apiServerURL, String apiKey, String modelPackageName, String apiPackageName, + String classOutputDir, String libraryHome){ + super(apiServerURL, apiKey, modelPackageName, apiPackageName, classOutputDir, libraryHome); + this.setDataTypeMappingProvider(new As3DataTypeMappingProvider()); + this.setNameGenerator(new As3NamingPolicyProvider()); + } + + public As3LibCodeGen(String configPath){ + super(configPath); + this.setDataTypeMappingProvider(new As3DataTypeMappingProvider()); + this.setNameGenerator(new As3NamingPolicyProvider()); + } + + @Override + protected LanguageConfiguration initializeLangConfig(LanguageConfiguration as3Configuration) { + as3Configuration.setClassFileExtension(".as"); + as3Configuration.setTemplateLocation("conf/as3/templates"); + as3Configuration.setStructureLocation("conf/as3/structure"); + as3Configuration.setExceptionPackageName("com.wordnik.swagger.exception"); + as3Configuration.setAnnotationPackageName("com.wordnik.swagger.annotations"); + + //create ouput directories + FileUtil.createOutputDirectories(as3Configuration.getModelClassLocation(), as3Configuration.getClassFileExtension()); + FileUtil.createOutputDirectories(as3Configuration.getResourceClassLocation(), as3Configuration.getClassFileExtension()); +/* + FileUtil.clearFolder(as3Configuration.getLibraryHome() + "/src/main/java/com/wordnik/swagger/runtime"); + FileUtil.createOutputDirectories(as3Configuration.getLibraryHome() + "/src/main/java/com/wordnik/swagger/runtime", "as"); +*/ + FileUtil.clearFolder(as3Configuration.getLibraryHome() + "/src/main/as3/com/wordnik/swagger/common"); + FileUtil.clearFolder(as3Configuration.getLibraryHome() + "/src/main/as3/com/wordnik/swagger/exception"); + FileUtil.clearFolder(as3Configuration.getLibraryHome() + "/src/main/as3/com/wordnik/swagger/event"); + FileUtil.copyDirectory(new File(as3Configuration.getStructureLocation()), new File(as3Configuration.getLibraryHome())); + + as3Configuration.setGenerateHelperEnums(false); + as3Configuration.setGenerateOutputWrappers(true); + return as3Configuration; + } + +} diff --git a/src/main/java/com/wordnik/swagger/codegen/config/as3/As3NamingPolicyProvider.java b/src/main/java/com/wordnik/swagger/codegen/config/as3/As3NamingPolicyProvider.java new file mode 100644 index 00000000000..165940e7867 --- /dev/null +++ b/src/main/java/com/wordnik/swagger/codegen/config/as3/As3NamingPolicyProvider.java @@ -0,0 +1,25 @@ +package com.wordnik.swagger.codegen.config.as3; + +import com.wordnik.swagger.codegen.config.common.CamelCaseNamingPolicyProvider; + +/** + * User: deepakmichael + * Date: 16/08/11 + * Time: 11:01 AM + */ +public class As3NamingPolicyProvider extends CamelCaseNamingPolicyProvider { + + /** + * Gets the signature of the method that gets value for give attribute name. + * + * Example: If class name is user and attibute name is email the out in java language will be + * user.getEmail() + * + * @param className + * @param attributeName + * @return + */ + public String createGetterMethodName(String className, String attributeName) { + return className+"."+ attributeName; + } +} diff --git a/src/main/java/com/wordnik/swagger/codegen/config/common/CamelCaseNamingPolicyProvider.java b/src/main/java/com/wordnik/swagger/codegen/config/common/CamelCaseNamingPolicyProvider.java index 42204c545a3..a4663f412c6 100644 --- a/src/main/java/com/wordnik/swagger/codegen/config/common/CamelCaseNamingPolicyProvider.java +++ b/src/main/java/com/wordnik/swagger/codegen/config/common/CamelCaseNamingPolicyProvider.java @@ -141,6 +141,20 @@ public class CamelCaseNamingPolicyProvider implements NamingPolicyProvider { return inputobjectName; } + /** + * Generate the name of the wrapper class used as a wrapper for a list of items returned by a service + *

+ * Example: get definitions API returns a list of definition objects as the result. This will be wrapped by an + * object. The object's name will be determined by invoking this service. + * eg. DefinitionList for a wrapper of 'definition's + * + * @param wrapperItemName + * @return + */ + public String getOutputWrapperName(String wrapperItemName) { + return applyClassNamingPolicy(wrapperItemName) + "Wrapper"; + } + /** * Generates a name for an enum for the param or field name. *

diff --git a/src/main/java/com/wordnik/swagger/codegen/config/java/JavaDataTypeMappingProvider.java b/src/main/java/com/wordnik/swagger/codegen/config/java/JavaDataTypeMappingProvider.java index f34ae08d5d0..bd0eafd351e 100644 --- a/src/main/java/com/wordnik/swagger/codegen/config/java/JavaDataTypeMappingProvider.java +++ b/src/main/java/com/wordnik/swagger/codegen/config/java/JavaDataTypeMappingProvider.java @@ -158,7 +158,18 @@ public class JavaDataTypeMappingProvider implements DataTypeMappingProvider { return classShortName; } - /** + /** + * Returns the syntax for defintion of an object of type and name + * + * @param argumentType + * @param argumentName + * @return + */ + public String getArgumentDefinition(String argumentType, String argumentName) { + return argumentType + " " + argumentName; + } + + /** * Gets the class of the expected return value for a type string. Examples of type Strings are int, User, List[User] * If the type string is a collection type like a map or list the string value returned would be the class * that map or list is returning. diff --git a/src/main/java/com/wordnik/swagger/codegen/resource/EndpointOperation.java b/src/main/java/com/wordnik/swagger/codegen/resource/EndpointOperation.java index 761fd112faa..a83fb3ae8e2 100644 --- a/src/main/java/com/wordnik/swagger/codegen/resource/EndpointOperation.java +++ b/src/main/java/com/wordnik/swagger/codegen/resource/EndpointOperation.java @@ -291,7 +291,7 @@ public class EndpointOperation { if (method.getArguments() != null && method.getArguments().size() > 0) { for(MethodArgument arg: method.getArguments()) { if(!arg.getName().equalsIgnoreCase(FORMAT_PARAM_NAME)){ - argumentDefinitions.add(arg.getDataType() + " " + arg.getName()); + argumentDefinitions.add( dataTypeMapper.getArgumentDefinition(arg.getDataType(), arg.getName()) ); argumentNames.add(arg.getName()); } } @@ -306,7 +306,21 @@ public class EndpointOperation { method.setReturnValue(dataTypeMapper.getClassType(responseClass, false)); method.setReturnClassName(dataTypeMapper.getGenericType(responseClass)); - + //if this is a list return type + if(method.getReturnClassName().equals(dataTypeMapper.getListReturnTypeSignature(responseClass))){ + String returnValueTypeName = method.getReturnValue(); + Model outputWrapperModel = new Model(); + outputWrapperModel.setName(nameGenerator.getOutputWrapperName(returnValueTypeName)); + List fields = new ArrayList(); + ModelField aModelField = new ModelField(); + aModelField.setName(nameGenerator.applyMethodNamingPolicy(returnValueTypeName)); + aModelField.setParamType(responseClass); + fields.add(aModelField); + outputWrapperModel.setFields(fields); + method.setOutputWrapperModel(outputWrapperModel); + //method.setReturnClassName(outputWrapperModel.getName()); + } + //get description string for exception method.setExceptionDescription(calculateExceptionMessage()); } diff --git a/src/main/java/com/wordnik/swagger/codegen/resource/ModelField.java b/src/main/java/com/wordnik/swagger/codegen/resource/ModelField.java index a23d1ef29aa..3b9107eb5b7 100644 --- a/src/main/java/com/wordnik/swagger/codegen/resource/ModelField.java +++ b/src/main/java/com/wordnik/swagger/codegen/resource/ModelField.java @@ -17,7 +17,9 @@ package com.wordnik.swagger.codegen.resource; import com.wordnik.swagger.codegen.FieldDefinition; +import com.wordnik.swagger.codegen.config.ApiConfiguration; import com.wordnik.swagger.codegen.config.DataTypeMappingProvider; +import com.wordnik.swagger.codegen.config.NamingPolicyProvider; import java.util.ArrayList; import java.util.List; @@ -170,7 +172,7 @@ public class ModelField { return fieldDefinition; } - public FieldDefinition getFieldDefinition(DataTypeMappingProvider dataTypeMapper) { + public FieldDefinition getFieldDefinition(DataTypeMappingProvider dataTypeMapper, ApiConfiguration config, NamingPolicyProvider nameGenerator) { if(fieldDefinition == null) { fieldDefinition = new FieldDefinition(); String type = paramType.trim(); @@ -180,6 +182,11 @@ public class ModelField { if(type.startsWith("List[")){ fieldDefinition.getImportDefinitions().addAll(dataTypeMapper.getListIncludes()); String entryType = type.substring(5, type.length()-1); + if (dataTypeMapper.isPrimitiveType(entryType)) { + fieldDefinition.setCollectionItemType(entryType); + } else { + fieldDefinition.setCollectionItemType(config.getModelPackageName() + "." + nameGenerator.applyClassNamingPolicy(entryType)); + } entryType = dataTypeMapper.getClassType(entryType, true); String returnType = dataTypeMapper.getListReturnTypeSignature(entryType); fieldDefinition.setReturnType(returnType);