Provide a default output directory for snippets based on build tool

Rather than requiring an output directory to be explcitly configured,
a default is now automatically configured based on the build tool
that's being used. When using Gradle, snippets will be generated in
build/generated-snippets. When using Maven, snippets will be
generated in target/generated-snippets.

See gh-297
This commit is contained in:
Gerrit Meier
2016-10-09 12:54:15 +02:00
committed by Andy Wilkinson
parent c1540838a3
commit 3ac4a1acad
41 changed files with 245 additions and 47 deletions

View File

@@ -5,4 +5,5 @@
<suppressions>
<suppress files="[\\/]src[\\/]test[\\/]java[\\/]" checks="JavadocVariable" />
<suppress files="[\\/]src[\\/]test[\\/]java[\\/]" checks="JavadocMethod" />
<suppress files="RestDocsSnippetBlockMacro\.java" checks="RedundantModifier" />
</suppressions>

View File

@@ -31,8 +31,7 @@ import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.docu
public class CustomDefaultSnippets {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private WebApplicationContext context;

View File

@@ -29,7 +29,7 @@ import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.docu
public class CustomEncoding {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private WebApplicationContext context;

View File

@@ -30,7 +30,7 @@ import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.docu
public class CustomFormat {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private WebApplicationContext context;

View File

@@ -29,7 +29,7 @@ import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.docu
public class CustomUriConfiguration {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private WebApplicationContext context;

View File

@@ -38,8 +38,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
public class EveryTestPreprocessing {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"target/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
private WebApplicationContext context;

View File

@@ -30,8 +30,7 @@ import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.docu
public class ExampleApplicationTestNgTests {
public final ManualRestDocumentation restDocumentation = new ManualRestDocumentation(
"target/generated-snippets");
public final ManualRestDocumentation restDocumentation = new ManualRestDocumentation();
@SuppressWarnings("unused")
// tag::setup[]
private MockMvc mockMvc;

View File

@@ -30,8 +30,7 @@ import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.docu
public class ExampleApplicationTests {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"target/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@SuppressWarnings("unused")
// tag::setup[]

View File

@@ -29,7 +29,7 @@ import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.docu
public class ParameterizedOutput {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@SuppressWarnings("unused")
private MockMvc mockMvc;

View File

@@ -29,8 +29,7 @@ import static org.springframework.restdocs.restassured.RestAssuredRestDocumentat
public class CustomDefaultSnippets {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@SuppressWarnings("unused")
private RequestSpecification spec;

View File

@@ -28,7 +28,7 @@ import static org.springframework.restdocs.restassured.RestAssuredRestDocumentat
public class CustomEncoding {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@SuppressWarnings("unused")
private RequestSpecification spec;

View File

@@ -29,7 +29,7 @@ import static org.springframework.restdocs.restassured.RestAssuredRestDocumentat
public class CustomFormat {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@SuppressWarnings("unused")
private RequestSpecification spec;

View File

@@ -38,8 +38,7 @@ import static org.springframework.restdocs.restassured.RestAssuredRestDocumentat
public class EveryTestPreprocessing {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"target/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
// tag::setup[]
private RequestSpecification spec;

View File

@@ -29,8 +29,7 @@ import static org.springframework.restdocs.restassured.RestAssuredRestDocumentat
public class ExampleApplicationTestNgTests {
private final ManualRestDocumentation restDocumentation = new ManualRestDocumentation(
"build/generated-snippets");
private final ManualRestDocumentation restDocumentation = new ManualRestDocumentation();
@SuppressWarnings("unused")
// tag::setup[]

View File

@@ -28,8 +28,7 @@ import static org.springframework.restdocs.restassured.RestAssuredRestDocumentat
public class ExampleApplicationTests {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"build/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@SuppressWarnings("unused")
// tag::setup[]

View File

@@ -29,8 +29,7 @@ import static org.springframework.restdocs.restassured.RestAssuredRestDocumentat
public class ParameterizedOutput {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"build/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@SuppressWarnings("unused")
private RequestSpecification spec;

View File

@@ -42,7 +42,7 @@ import com.jayway.restassured.specification.RequestSpecification;
public class SampleRestAssuredApplicationTests {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
private RequestSpecification documentationSpec;

View File

@@ -61,7 +61,7 @@ import com.fasterxml.jackson.databind.ObjectMapper;
public class ApiDocumentation {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private NoteRepository noteRepository;

View File

@@ -61,7 +61,7 @@ import com.fasterxml.jackson.databind.ObjectMapper;
public class ApiDocumentation {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("target/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private NoteRepository noteRepository;

View File

@@ -58,7 +58,7 @@ import com.jayway.jsonpath.JsonPath;
public class GettingStartedDocumentation {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("target/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private ObjectMapper objectMapper;

View File

@@ -70,7 +70,7 @@ import com.fasterxml.jackson.databind.ObjectMapper;
public class ApiDocumentation {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
private RestDocumentationResultHandler documentationHandler;

View File

@@ -61,7 +61,7 @@ import com.jayway.jsonpath.JsonPath;
public class GettingStartedDocumentation {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("build/generated-snippets");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private ObjectMapper objectMapper;

View File

@@ -39,7 +39,7 @@ import org.testng.annotations.Test;
@WebAppConfiguration
public class SampleTestNgApplicationTests extends AbstractTestNGSpringContextTests {
private final ManualRestDocumentation restDocumentation = new ManualRestDocumentation("build/generated-snippets");
private final ManualRestDocumentation restDocumentation = new ManualRestDocumentation();
@Autowired
private WebApplicationContext context;

View File

@@ -1,6 +1,7 @@
rootProject.name = 'spring-restdocs'
include 'docs'
include 'spring-restdocs-asciidoctor-extensions'
include 'spring-restdocs-core'
include 'spring-restdocs-mockmvc'
include 'spring-restdocs-restassured'
include 'spring-restdocs-restassured'

View File

@@ -0,0 +1,6 @@
description = 'Spring REST Docs Asciidoctor Extensions'
dependencies {
compile 'org.asciidoctor:asciidoctorj:1.5.2'
optional 'junit:junit'
}

View File

@@ -0,0 +1,45 @@
/*
* Copyright 2014-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.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://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.restdocs.asciidoctor.extensions;
import org.asciidoctor.Asciidoctor;
import org.asciidoctor.extension.spi.ExtensionRegistry;
/**
* ExtensionRegistry for the Spring Rest Docs macros to get registered
* in all projects that include this asciidoctor extension module.
* <p>
* Macros provided:
* <ul>
* <li>{@link RestDocsSnippetBlockMacro}</li>
* </ul>
*
* @author Gerrit Meier
*/
public class RestDocsExtensionRegistry implements ExtensionRegistry {
/**
* the name that identifies the block macro in the asciidoctor document
* (e.g. <pre><b>snippet</b>::file_to_include[]</pre>)
*/
private static final String SNIPPET_BLOCK_NAME = "snippet";
@Override
public void register(Asciidoctor asciidoctor) {
asciidoctor.javaExtensionRegistry().blockMacro(SNIPPET_BLOCK_NAME, RestDocsSnippetBlockMacro.class);
}
}

View File

@@ -0,0 +1,66 @@
/*
* Copyright 2014-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.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://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.restdocs.asciidoctor.extensions;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.Map;
import org.asciidoctor.Asciidoctor;
import org.asciidoctor.OptionsBuilder;
import org.asciidoctor.ast.AbstractBlock;
import org.asciidoctor.extension.BlockMacroProcessor;
/**
* Block macro to include snippets generated by Spring Rest Docs in a convenient way.
* Defaults to <i>build</i> (gradle) or <i>target</i> directory to look for the generated-snippets folder and its content.
*
* @author Gerrit Meier
*/
class RestDocsSnippetBlockMacro extends BlockMacroProcessor {
private static final String GENERATED_SNIPPETS_PATH = "generated-snippets";
private static final String MAVEN_TARGET_PATH = "target" + File.separator + GENERATED_SNIPPETS_PATH;
private static final String GRADLE_BUILD_PATH = "build" + File.separator + GENERATED_SNIPPETS_PATH;
private static final String MAVEN_POM = "pom.xml";
public RestDocsSnippetBlockMacro(String macroName, Map<String, Object> config) {
super(macroName, config);
}
@Override
protected Object process(AbstractBlock parent, String fileToInclude, Map<String, Object> attributes) {
String generatedSnippetPath = getDefaultOutputDirectory() + File.separator + fileToInclude;
// since 'pass' context does not convert the content, we have to do this manually
String convertedContent = Asciidoctor.Factory.create().convertFile(
new File(generatedSnippetPath),
OptionsBuilder.options().toFile(false).inPlace(false).get());
return createBlock(parent, "pass", convertedContent, attributes, getConfig());
}
private static String getDefaultOutputDirectory() {
String executingDirectory = Paths.get(".").toFile().getAbsolutePath();
if (Files.exists(Paths.get(MAVEN_POM))) {
return executingDirectory + File.separator + MAVEN_TARGET_PATH;
}
return executingDirectory + File.separator + GRADLE_BUILD_PATH;
}
}

View File

@@ -0,0 +1 @@
org.springframework.restdocs.asciidoctor.extensions.RestDocsExtensionRegistry

View File

@@ -0,0 +1,54 @@
/*
* Copyright 2014-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.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://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.restdocs.asciidoctor.extensions;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import org.asciidoctor.Asciidoctor;
import org.asciidoctor.Options;
import org.junit.Before;
import org.junit.Test;
import static org.hamcrest.CoreMatchers.equalTo;
import static org.junit.Assert.assertThat;
/**
* Tests for {@link RestDocsSnippetBlockMacro}.
*
* @author Gerrit Meier
*/
public class RestDocsSnippetBlockMacroTest {
@Before
public void prepareIncludeFiles() throws Exception {
Files.createDirectories(Paths.get("build/generated-snippets/"));
Files.copy(Paths.get("src/test/resources/rest_docs_macro.adoc"),
Paths.get("build/generated-snippets/rest_docs_macro.adoc"), StandardCopyOption.REPLACE_EXISTING);
}
@Test
public void replaceRestDocsSnippetBlockWithFile() {
Asciidoctor asciidoctor = Asciidoctor.Factory.create();
asciidoctor.javaExtensionRegistry().blockMacro("snippet", RestDocsSnippetBlockMacro.class);
assertThat(asciidoctor.convert("snippet::rest_docs_macro.adoc[]", new Options()),
equalTo("<div class=\"paragraph\">\n<p>test text</p>\n</div>"));
}
}

View File

@@ -32,6 +32,14 @@ public class JUnitRestDocumentation
private final ManualRestDocumentation delegate;
/**
* Creates a new {@code JUnitRestDocumentation} instance that will generate snippets
* to &lt;gradle/maven build path&gt;/generated-snippet.
*/
public JUnitRestDocumentation() {
this.delegate = new ManualRestDocumentation();
}
/**
* Creates a new {@code JUnitRestDocumentation} instance that will generate snippets
* to the given {@code outputDirectory}.

View File

@@ -17,6 +17,8 @@
package org.springframework.restdocs;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;
/**
* {@code ManualRestDocumentation} is used to manually manage the
@@ -31,10 +33,23 @@ import java.io.File;
*/
public final class ManualRestDocumentation implements RestDocumentationContextProvider {
private static final String GENERATED_SNIPPETS_PATH = "generated-snippets";
private static final String MAVEN_TARGET_PATH = "target" + File.separator + GENERATED_SNIPPETS_PATH;
private static final String GRADLE_BUILD_PATH = "build" + File.separator + GENERATED_SNIPPETS_PATH;
private static final String MAVEN_POM = "pom.xml";
private final File outputDirectory;
private RestDocumentationContext context;
/**
* Creates a new {@code ManualRestDocumentation} instance that will generate snippets
* to &lt;gradle/maven build path&gt;/generated-snippet.
*/
public ManualRestDocumentation() {
this(getDefaultOutputDirectory());
}
/**
* Creates a new {@code ManualRestDocumentation} instance that will generate snippets
* to the given {@code outputDirectory}.
@@ -79,4 +94,12 @@ public final class ManualRestDocumentation implements RestDocumentationContextPr
return this.context;
}
private static String getDefaultOutputDirectory() {
String executingDirectory = Paths.get(".").toFile().getAbsolutePath();
if (Files.exists(Paths.get(MAVEN_POM))) {
return executingDirectory + File.separator + MAVEN_TARGET_PATH;
}
return executingDirectory + File.separator + GRADLE_BUILD_PATH;
}
}

View File

@@ -32,6 +32,14 @@ public class RestDocumentation implements TestRule, RestDocumentationContextProv
private final JUnitRestDocumentation delegate;
/**
* Creates a new {@code RestDocumentation} instance that will generate snippets to the
* to &lt;gradle/maven build path&gt;/generated-snippet.
*/
public RestDocumentation() {
this.delegate = new JUnitRestDocumentation();
}
/**
* Creates a new {@code RestDocumentation} instance that will generate snippets to the
* given {@code outputDirectory}.

View File

@@ -195,8 +195,7 @@ public class RestDocumentationConfigurerTests {
}
private RestDocumentationContext createContext() {
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation(
"build");
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation("build");
manualRestDocumentation.beforeTest(null, null);
RestDocumentationContext context = manualRestDocumentation.beforeOperation();
return context;

View File

@@ -83,8 +83,7 @@ public class RestDocumentationContextPlaceholderResolverTests {
}
private RestDocumentationContext createContext(String methodName) {
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation(
"build");
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation("build");
manualRestDocumentation.beforeTest(getClass(), methodName);
RestDocumentationContext context = manualRestDocumentation.beforeOperation();
return context;

View File

@@ -70,8 +70,7 @@ public class StandardWriterResolverTests {
}
private RestDocumentationContext createContext(String outputDir) {
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation(
outputDir);
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation(outputDir);
manualRestDocumentation.beforeTest(getClass(), null);
RestDocumentationContext context = manualRestDocumentation.beforeOperation();
return context;

View File

@@ -123,8 +123,7 @@ public class OperationBuilder extends OperationTestRule {
}
private RestDocumentationContext createContext() {
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation(
this.outputDirectory.getAbsolutePath());
ManualRestDocumentation manualRestDocumentation = new ManualRestDocumentation(this.outputDirectory.getAbsolutePath());
manualRestDocumentation.beforeTest(null, null);
RestDocumentationContext context = manualRestDocumentation.beforeOperation();
return context;

View File

@@ -44,7 +44,7 @@ public class MockMvcRestDocumentationConfigurerTests {
private MockHttpServletRequest request = new MockHttpServletRequest();
@Rule
public JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation("test");
public JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Test
public void defaultConfiguration() {

View File

@@ -101,8 +101,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
public class MockMvcRestDocumentationIntegrationTests {
@Rule
public JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"build/generated-snippets");
public JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Autowired
private WebApplicationContext context;

View File

@@ -47,8 +47,7 @@ import static org.mockito.Mockito.verify;
public class RestAssuredRestDocumentationConfigurerTests {
@Rule
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"build");
public final JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
private final FilterableRequestSpecification requestSpec = mock(
FilterableRequestSpecification.class);

View File

@@ -91,8 +91,7 @@ import static org.springframework.restdocs.test.SnippetMatchers.snippet;
public class RestAssuredRestDocumentationIntegrationTests {
@Rule
public JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation(
"build/generated-snippets");
public JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
@Value("${local.server.port}")
private int port;