Skip to content

Commit

Permalink
Merge pull request kongchen#638 from warrenc5/json_mapper_feature
Browse files Browse the repository at this point in the history
add a configuration feature which configures the JSON object mapper
  • Loading branch information
who authored Sep 7, 2018
2 parents 3d97cb1 + af4fd83 commit d7de392
Show file tree
Hide file tree
Showing 5 changed files with 182 additions and 7 deletions.
40 changes: 33 additions & 7 deletions README.md
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# Swagger Maven Plugin
# Swagger Maven Plugin
[![Build Status](https://travis-ci.org/kongchen/swagger-maven-plugin.png)](https://travis-ci.org/kongchen/swagger-maven-plugin)
[![Maven Central](https://maven-badges.herokuapp.com/maven-central/com.github.kongchen/swagger-maven-plugin/badge.svg)](https://maven-badges.herokuapp.com/maven-central/com.github.kongchen/swagger-maven-plugin)

Expand All @@ -22,7 +22,7 @@ Version 3.1.0+ of this plugin depends on the re-packaged/re-branded io.swagger.s


# Usage
Import the plugin in your project by adding following configuration in your `plugins` block:
Import the plugin in your project by adding following configuration in your `plugins` block:

```xml
<build>
Expand Down Expand Up @@ -83,11 +83,11 @@ The `executions` block is used to specify the phase of the build lifecycle you w
| `typesToSkip` | Nodes of class names to explicitly skip during parameter processing. More details [below](#typesToSkip)|
| `apiModelPropertyAccessExclusions` | Allows the exclusion of specified `@ApiModelProperty` fields. This can be used to hide certain model properties from the swagger spec. More details [below](#apiModelPropertyAccessExclusions)|
| `jsonExampleValues` | If `true`, all example values in `@ApiModelProperty` will be handled as json raw values. This is useful for creating valid examples in the generated json for all property types, including non-string ones. |
| `modelConverters` | List of custom implementations of `io.swagger.converter.ModelConverter` that should be used when generating the swagger files. |
| `modelConverters` | List of custom implementations of `io.swagger.converter.ModelConverter` that should be used when generating the swagger files. |
| `swaggerExtensions` | List of custom implementations of `io.swagger.jaxrs.ext.SwaggerExtension` that should be used when generating the swagger files. |
| `operationIdFormat` | Format of `operationId` used in Swagger spec. For historical reasons default is Java method name. Since 3.1.8, for new APIs suggested format is: `{{className}}_{{methodName}}_{{httpMethod}}`. `{{packageName}}` token is also supported. |


| `enabledObjectMapperFeatures` | List of ConfigFeature enums that are supported by ObjectMapper.configure - the feature is set to true. https://github.com/swagger-api/swagger-spec/blob/master/versions/2.0.md#features) here, see more details [below](#features)|
| `disabledObjectMapperFeatures` | List of ConfigFeature enums that are supported by ObjectMapper.configure - the feature is set to false. https://github.com/swagger-api/swagger-spec/blob/master/versions/2.0.md#features) here, see more details [below](#features)|
| `operationIdFormat` | Format of `operationId` used in Swagger spec. For historical reasons default is Java method name. Since 3.1.8, for new APIs suggested format is: `{{className}}_{{methodName}}_{{httpMethod}}`. `{{packageName}}` token is also supported. |
# <a id="templatefile">Template File</a>

If you'd like to generate a template-driven static document, such as markdown or HTML documentation, you'll need to specify a [handlebars](https://github.com/jknack/handlebars.java) template file in ```templatePath```.
Expand Down Expand Up @@ -133,7 +133,7 @@ or define several definitions in a json file and specify the json path like this

The file will be read by `getClass().getResourceAsStream`, so please note the path you configured.

Alternatively, specify the __absolute__ file path to the json definition file:
Alternatively, specify the __absolute__ file path to the json definition file:

```xml
<securityDefinition>
Expand Down Expand Up @@ -258,6 +258,25 @@ or `custom.json` by adding the following to your pom.xml:

The above setting attaches the generated file to Maven for install/deploy purpose with `swagger-ui`as classifier and `json` as type

# <a id="features">Object Mapper Configuration Features</a>

Enables or disables the static Json.mapper config, by setting the feature of a known enum to true or false respectively.

N.B. Inner class fully qualified domain names are using $

```
<configuration>
...
<enabledObjectMapperFeatures>
<feature>com.fasterxml.jackson.databind.SerializationFeature.WRITE_ENUMS_USING_TO_STRING</feature>
<feature>com.fasterxml.jackson.core.JsonParser$Feature.ALLOW_NUMERIC_LEADING_ZEROS</feature>
</enabledObjectMapperFeatures>
...
<disabledObjectMapperFeatures>
<feature>com.fasterxml.jackson.databind.SerializationFeature.FAIL_ON_EMPTY_BEANS</feature>
</disabledObjectMapperFeatures>
</configuration>
```


# Example
Expand Down Expand Up @@ -331,6 +350,13 @@ There's a [sample here](https://github.com/swagger-maven-plugin/swagger-maven-ex
<swaggerExtensions>
<swaggerExtension>com.example.VendorExtension</swaggerExtension>
</swaggerExtensions>
<enabledObjectMapperFeatures>
<feature>com.fasterxml.jackson.databind.SerializationFeature.WRITE_ENUMS_USING_TO_STRING</feature>
<feature>com.fasterxml.jackson.core.JsonParser$Feature.ALLOW_NUMERIC_LEADING_ZEROS</feature>
</enabledObjectMapperFeatures>
<disabledObjectMapperFeatures>
<feature>com.fasterxml.jackson.databind.SerializationFeature.FAIL_ON_EMPTY_BEANS</feature>
</disabledObjectMapperFeatures>
<operationIdFormat>{{className}}_{{methodName}}_{{httpMethod}}</operationIdFormat>
</apiSource>
</apiSources>
Expand Down
37 changes: 37 additions & 0 deletions src/main/java/com/github/kongchen/swagger/docgen/mavenplugin/ApiDocumentMojo.java
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import com.github.kongchen.swagger.docgen.AbstractDocumentSource;
import com.github.kongchen.swagger.docgen.GenerateException;
import io.swagger.util.Json;

import org.apache.maven.plugin.AbstractMojo;
import org.apache.maven.plugin.MojoExecutionException;
Expand All @@ -15,7 +16,10 @@
import org.apache.maven.project.MavenProjectHelper;

import java.io.File;
import java.lang.reflect.Method;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;

/**
* User: kongchen
Expand All @@ -32,6 +36,18 @@ public class ApiDocumentMojo extends AbstractMojo {
@Parameter
private List<ApiSource> apiSources;

/**
* A set of feature enums which should be enabled on the JSON object mapper
*/
@Parameter
private List<String> enabledObjectMapperFeatures;

/**
* A set of feature enums which should be enabled on the JSON object mapper
*/
@Parameter
private List<String> disabledObjectMapperFeatures;


@Parameter(defaultValue = "${project}", readonly = true)
private MavenProject project;
Expand Down Expand Up @@ -84,6 +100,16 @@ public void execute() throws MojoExecutionException, MojoFailureException {

try {
getLog().debug(apiSources.toString());

if (enabledObjectMapperFeatures!=null) {
configureObjectMapperFeatures(enabledObjectMapperFeatures,true);

}

if (disabledObjectMapperFeatures!=null) {
configureObjectMapperFeatures(disabledObjectMapperFeatures,false);
}

for (ApiSource apiSource : apiSources) {
validateConfiguration(apiSource);
AbstractDocumentSource documentSource = apiSource.isSpringmvc()
Expand Down Expand Up @@ -195,4 +221,15 @@ private String getSwaggerDirectoryName(String swaggerDirectory) {
return new File(swaggerDirectory).getName();
}

private void configureObjectMapperFeatures(List<String> features, boolean enabled) throws Exception {
for (String feature : features) {
int i= feature.lastIndexOf(".");
Class clazz = Class.forName(feature.substring(0,i));
Enum e = Enum.valueOf(clazz,feature.substring(i+1));
getLog().debug("enabling " + e.getDeclaringClass().toString() + "." + e.name() + "");
Method method = Json.mapper().getClass().getMethod("configure",e.getClass(),boolean.class);
method.invoke(Json.mapper(),e,enabled);
}
}

}
34 changes: 34 additions & 0 deletions src/test/java/com/github/kongchen/smp/integration/SwaggerMavenPluginTest.java
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
package com.github.kongchen.smp.integration;

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import com.github.kongchen.smp.integration.utils.PetIdToStringModelConverter;
import com.github.kongchen.swagger.docgen.mavenplugin.ApiDocumentMojo;
import com.github.kongchen.swagger.docgen.mavenplugin.ApiSource;
Expand Down Expand Up @@ -35,13 +37,17 @@
import static com.github.kongchen.smp.integration.utils.TestUtils.changeDescription;
import static com.github.kongchen.smp.integration.utils.TestUtils.createTempDirPath;
import static com.github.kongchen.smp.integration.utils.TestUtils.setCustomReader;
import io.swagger.util.Json;
import java.util.logging.Level;
import java.util.logging.Logger;
import static net.javacrumbs.jsonunit.JsonAssert.assertJsonEquals;
import static net.javacrumbs.jsonunit.core.Option.IGNORING_ARRAY_ORDER;

/**
* @author chekong on 8/15/14.
*/
public class SwaggerMavenPluginTest extends AbstractMojoTestCase {

private File swaggerOutputDir = new File(getBasedir(), "generated/swagger-ui");
private File docOutput = new File(getBasedir(), "generated/document.html");
private ApiDocumentMojo mojo;
Expand Down Expand Up @@ -294,4 +300,32 @@ private void assertGeneratedSwaggerSpecYaml(String description, String expectedO
assertJsonEquals(expectJson, actualJson, Configuration.empty().when(IGNORING_ARRAY_ORDER));
}

@Test
public void testFeatureIsAccepted() throws Exception {
File testPom = new File(getBasedir(), "src/test/resources/plugin-config.xml");
mojo = (ApiDocumentMojo) lookupMojo("generate", testPom);
mojo.execute();

assertTrue(Json.mapper().isEnabled(SerializationFeature.WRITE_ENUMS_USING_TO_STRING));
assertTrue(Json.mapper().isEnabled(JsonParser.Feature.ALLOW_NUMERIC_LEADING_ZEROS));
}

@Test
public void testFeatureIsNotFoundFail() throws Exception {
File testPom = new File(getBasedir(), "src/test/resources/plugin-config-feature-fail.xml");
mojo = (ApiDocumentMojo) lookupMojo("generate", testPom);
try {
mojo.execute();
fail();
} catch (Exception x) {
Logger.getAnonymousLogger().log(Level.FINE,x.getMessage(),x);
assertTrue(Json.mapper().isEnabled(SerializationFeature.WRITE_ENUMS_USING_TO_STRING));
assertTrue(x.getMessage().contains("com.fasterxml.jackson.core.JsonParser.Feature"));
assertNotNull(x.getCause());
assertTrue(x.getCause().getMessage().contains("com.fasterxml.jackson.core.JsonParser.Feature"));
}
}



}
71 changes: 71 additions & 0 deletions src/test/resources/plugin-config-feature-fail.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
<project>
<build>
<plugins>
<plugin>
<groupId>com.github.kongchen</groupId>
<artifactId>swagger-maven-plugin</artifactId>
<version>3.0-M2-SNAPSHOT</version>
<configuration>
<apiSources>
<apiSource>
<springmvc>false</springmvc>
<locations>
<location>com.wordnik.jaxrs</location>
</locations>
<schemes>
<scheme>http</scheme>
<scheme>https</scheme>
</schemes>
<securityDefinitions>
<securityDefinition>
<name>basicAuth</name>
<type>basic</type>
</securityDefinition>
<securityDefinition>
<name>api_key_2</name>
<type>apiKey</type>
<in>header</in>
</securityDefinition>
<securityDefinition>
<json>/securityDefinition.json</json>
</securityDefinition>
</securityDefinitions>
<!-- Support classpath or file absolute path here.
1) classpath e.g: "classpath:/markdown.hbs", "classpath:/templates/hello.html"
2) file e.g: "${basedir}/src/main/resources/markdown.hbs",
"${basedir}/src/main/resources/template/hello.html" -->
<templatePath>classpath:/templates/strapdown.html.hbs</templatePath>
<outputPath>${basedir}/generated/document.html</outputPath>
<outputFormats>json</outputFormats>
<swaggerDirectory>${basedir}/generated/swagger-ui</swaggerDirectory>
<swaggerApiReader>com.wordnik.jaxrs.VendorExtensionsJaxrsReader</swaggerApiReader>
<attachSwaggerArtifact>true</attachSwaggerArtifact>
<swaggerUIDocBasePath>http://www.example.com/restapi/doc</swaggerUIDocBasePath>
<modelSubstitute>/override.map</modelSubstitute>
<apiModelPropertyAccessExclusions>
<apiModelPropertyAccessExclusion>secret-property</apiModelPropertyAccessExclusion>
<apiModelPropertyAccessExclusion>another-secret-property</apiModelPropertyAccessExclusion>
<apiModelPropertyAccessExclusion>exclude-when-jev-option-not-set</apiModelPropertyAccessExclusion>
</apiModelPropertyAccessExclusions>
<swaggerExtensions>
<swaggerExtension>com.wordnik.sample.VendorExtensionWithoutReader</swaggerExtension>
</swaggerExtensions>
</apiSource>
</apiSources>
<enabledObjectMapperFeatures>
<feature>com.fasterxml.jackson.databind.SerializationFeature.WRITE_ENUMS_USING_TO_STRING</feature>
<feature>com.fasterxml.jackson.core.JsonParser.Feature.ALLOW_NUMERIC_LEADING_ZEROS</feature>
</enabledObjectMapperFeatures>
</configuration>
<executions>
<execution>
<phase>compile</phase>
<goals>
<goal>generate</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
7 changes: 7 additions & 0 deletions src/test/resources/plugin-config.xml
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,13 @@
</swaggerExtensions>
</apiSource>
</apiSources>
<enabledObjectMapperFeatures>
<feature>com.fasterxml.jackson.databind.SerializationFeature.WRITE_ENUMS_USING_TO_STRING</feature>
<feature>com.fasterxml.jackson.core.JsonParser$Feature.ALLOW_NUMERIC_LEADING_ZEROS</feature>
</enabledObjectMapperFeatures>
<disabledObjectMapperFeatures>
<feature>com.fasterxml.jackson.databind.SerializationFeature.FAIL_ON_EMPTY_BEANS</feature>
</disabledObjectMapperFeatures>
</configuration>
<executions>
<execution>
Expand Down

0 comments on commit d7de392

Please sign in to comment.