diff --git a/lib/src/jackson/java/com/diffplug/spotless/glue/json/JacksonJsonFormatterFunc.java b/lib/src/jackson/java/com/diffplug/spotless/glue/json/JacksonJsonFormatterFunc.java index 71215eb4a3..b8732c9cd8 100644 --- a/lib/src/jackson/java/com/diffplug/spotless/glue/json/JacksonJsonFormatterFunc.java +++ b/lib/src/jackson/java/com/diffplug/spotless/glue/json/JacksonJsonFormatterFunc.java @@ -21,6 +21,7 @@ import com.fasterxml.jackson.core.JsonFactory; import com.fasterxml.jackson.core.JsonFactoryBuilder; import com.fasterxml.jackson.core.JsonGenerator; +import com.fasterxml.jackson.core.JsonParser; import com.fasterxml.jackson.core.util.DefaultIndenter; import com.fasterxml.jackson.core.util.DefaultPrettyPrinter; import com.fasterxml.jackson.core.util.Separators; @@ -64,7 +65,12 @@ protected JsonFactory makeJsonFactory() { jsonFactory.configure(feature, toggle); }); + jacksonConfig.getJsonParserFeatureToToggle().forEach((rawFeature, toggle) -> { + // https://stackoverflow.com/questions/3735927/java-instantiating-an-enum-using-reflection + JsonParser.Feature feature = JsonParser.Feature.valueOf(rawFeature); + jsonFactory.configure(feature, toggle); + }); return jsonFactory; } diff --git a/lib/src/main/java/com/diffplug/spotless/json/JacksonJsonConfig.java b/lib/src/main/java/com/diffplug/spotless/json/JacksonJsonConfig.java index efff594663..33911878f2 100644 --- a/lib/src/main/java/com/diffplug/spotless/json/JacksonJsonConfig.java +++ b/lib/src/main/java/com/diffplug/spotless/json/JacksonJsonConfig.java @@ -27,6 +27,8 @@ public class JacksonJsonConfig extends JacksonConfig { protected Map jsonFeatureToToggle = new LinkedHashMap<>(); + protected Map jsonParserFeatureToToggle = new LinkedHashMap<>(); + // https://github.com/revelc/formatter-maven-plugin/pull/280 // By default, Jackson adds a ' ' before separator, which is not standard with most IDE/JSON libraries protected boolean spaceBeforeSeparator = false; @@ -35,6 +37,10 @@ public Map getJsonFeatureToToggle() { return Collections.unmodifiableMap(jsonFeatureToToggle); } + public Map getJsonParserFeatureToToggle() { + return Collections.unmodifiableMap(jsonParserFeatureToToggle); + } + /** * Refers to com.fasterxml.jackson.core.JsonGenerator.Feature */ @@ -49,6 +55,13 @@ public void appendJsonFeatureToToggle(Map features) { this.jsonFeatureToToggle.putAll(features); } + /** + * Refers to com.fasterxml.jackson.core.JsonParser.Feature + */ + public void appendJsonParserFeatureToToggle(Map features) { + this.jsonParserFeatureToToggle.putAll(features); + } + public boolean isSpaceBeforeSeparator() { return spaceBeforeSeparator; } diff --git a/plugin-gradle/src/main/java/com/diffplug/gradle/spotless/JsonExtension.java b/plugin-gradle/src/main/java/com/diffplug/gradle/spotless/JsonExtension.java index 47db97b2e6..4e0898423d 100644 --- a/plugin-gradle/src/main/java/com/diffplug/gradle/spotless/JsonExtension.java +++ b/plugin-gradle/src/main/java/com/diffplug/gradle/spotless/JsonExtension.java @@ -169,6 +169,15 @@ public JacksonJsonGradleConfig jsonFeature(String feature, boolean toggle) { return this; } + /** + * Refers to com.fasterxml.jackson.core.JsonParser.Feature + */ + public JacksonJsonGradleConfig jsonParserFeature(String feature, boolean toggle) { + this.jacksonConfig.appendJsonParserFeatureToToggle(Collections.singletonMap(feature, toggle)); + formatExtension.replaceStep(createStep()); + return this; + } + @Override public JacksonJsonGradleConfig self() { return this; diff --git a/plugin-maven/src/main/java/com/diffplug/spotless/maven/json/JacksonJson.java b/plugin-maven/src/main/java/com/diffplug/spotless/maven/json/JacksonJson.java index ecf925ddbe..f6b5006ff7 100644 --- a/plugin-maven/src/main/java/com/diffplug/spotless/maven/json/JacksonJson.java +++ b/plugin-maven/src/main/java/com/diffplug/spotless/maven/json/JacksonJson.java @@ -44,12 +44,16 @@ public class JacksonJson implements FormatterStepFactory { @Parameter private Map jsonFeatures = Collections.emptyMap(); + @Parameter + private Map jsonParserFeatures = Collections.emptyMap(); + @Override public FormatterStep newFormatterStep(FormatterStepConfig stepConfig) { JacksonJsonConfig jacksonConfig = new JacksonJsonConfig(); jacksonConfig.appendFeatureToToggle(features); jacksonConfig.appendJsonFeatureToToggle(jsonFeatures); + jacksonConfig.appendJsonParserFeatureToToggle(jsonParserFeatures); jacksonConfig.setSpaceBeforeSeparator(spaceBeforeSeparator); return JacksonJsonStep diff --git a/testlib/src/main/resources/json/objectContainingComments.json b/testlib/src/main/resources/json/objectContainingComments.json new file mode 100644 index 0000000000..88d6dec3ed --- /dev/null +++ b/testlib/src/main/resources/json/objectContainingComments.json @@ -0,0 +1,22 @@ +{ + "compilerOptions": { + "target": "ES2022", + "lib": ["ES2023"], + "module": "ESNext", + "skipLibCheck": true, + + /* Bundler mode */ + "moduleResolution": "bundler", + "allowImportingTsExtensions": true, + "isolatedModules": true, + "moduleDetection": "force", + "noEmit": true, + + /* Linting */ + "strict": true, + "noUnusedLocals": true, + "noUnusedParameters": true, + "noFallthroughCasesInSwitch": true + }, + "include": ["vite.config.ts"] +} \ No newline at end of file diff --git a/testlib/src/main/resources/json/objectContainingCommentsAfter.json b/testlib/src/main/resources/json/objectContainingCommentsAfter.json new file mode 100644 index 0000000000..10b01c7212 --- /dev/null +++ b/testlib/src/main/resources/json/objectContainingCommentsAfter.json @@ -0,0 +1,18 @@ +{ + "compilerOptions" : { + "target" : "ES2022", + "lib" : [ "ES2023" ], + "module" : "ESNext", + "skipLibCheck" : true, + "moduleResolution" : "bundler", + "allowImportingTsExtensions" : true, + "isolatedModules" : true, + "moduleDetection" : "force", + "noEmit" : true, + "strict" : true, + "noUnusedLocals" : true, + "noUnusedParameters" : true, + "noFallthroughCasesInSwitch" : true + }, + "include" : [ "vite.config.ts" ] +} \ No newline at end of file diff --git a/testlib/src/test/java/com/diffplug/spotless/json/JacksonJsonStepTest.java b/testlib/src/test/java/com/diffplug/spotless/json/JacksonJsonStepTest.java index 4c6d7d7ce3..68786f36d5 100644 --- a/testlib/src/test/java/com/diffplug/spotless/json/JacksonJsonStepTest.java +++ b/testlib/src/test/java/com/diffplug/spotless/json/JacksonJsonStepTest.java @@ -21,6 +21,10 @@ import com.diffplug.spotless.StepHarness; import com.diffplug.spotless.TestProvisioner; +import java.util.Map; + +import static com.diffplug.spotless.json.JacksonJsonStep.defaultVersion; + class JacksonJsonStepTest { @Test void canSetCustomIndentationLevel() { @@ -31,4 +35,16 @@ void canSetCustomIndentationLevel() { String after = "json/singletonArrayAfter_Jackson.json"; stepHarness.testResource(before, after); } + + @Test + void canSetJsonParserFeature() { + JacksonJsonConfig jacksonJsonConfig = new JacksonJsonConfig(); + jacksonJsonConfig.appendJsonParserFeatureToToggle(Map.of("ALLOW_COMMENTS", true)); + FormatterStep step = JacksonJsonStep.create(jacksonJsonConfig, defaultVersion(), TestProvisioner.mavenCentral()); + StepHarness stepHarness = StepHarness.forStepNoRoundtrip(step); + + String before = "json/objectContainingComments.json"; + String after = "json/objectContainingCommentsAfter.json"; + stepHarness.testResource(before, after); + } }