Ensure that additional snippets are only called once

Previously, when additional snippets were added to a
RestDocumentationResultHandler, those snippets would then be called
for every subsequent call to handle(MvcResult). This is problematic as
the snippets and their configuration are specific to a particular
MvcResult that is being documented.

This commit updates RestDocumentationResultHandler so that it clears
its additional snippets each time handle(MvcResult) is called.

Closes gh-243
This commit is contained in:
Andy Wilkinson
2016-05-24 11:30:49 +01:00
parent b81c03646f
commit ad549ae7c0
2 changed files with 70 additions and 1 deletions

View File

@@ -44,6 +44,8 @@ import static org.springframework.restdocs.mockmvc.IterableEnumeration.iterable;
*/
public class RestDocumentationResultHandler implements ResultHandler {
private final List<Snippet> additionalSnippets;
private final String identifier;
private final OperationRequestPreprocessor requestPreprocessor;
@@ -80,6 +82,7 @@ public class RestDocumentationResultHandler implements ResultHandler {
this.requestPreprocessor = requestPreprocessor;
this.responsePreprocessor = responsePreprocessor;
this.snippets = new ArrayList<>(Arrays.asList(snippets));
this.additionalSnippets = new ArrayList<>();
}
@Override
@@ -110,7 +113,7 @@ public class RestDocumentationResultHandler implements ResultHandler {
* @return this {@code ResultDocumentationResultHandler}
*/
public RestDocumentationResultHandler snippets(Snippet... snippets) {
this.snippets.addAll(Arrays.asList(snippets));
this.additionalSnippets.addAll(Arrays.asList(snippets));
return this;
}
@@ -120,6 +123,8 @@ public class RestDocumentationResultHandler implements ResultHandler {
(List<Snippet>) result.getRequest().getAttribute(
"org.springframework.restdocs.mockmvc.defaultSnippets"));
combinedSnippets.addAll(this.snippets);
combinedSnippets.addAll(this.additionalSnippets);
this.additionalSnippets.clear();
return combinedSnippets;
}

View File

@@ -0,0 +1,64 @@
/*
* 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.mockmvc;
import java.util.Arrays;
import org.junit.Test;
import org.mockito.Matchers;
import org.springframework.mock.web.MockHttpServletRequest;
import org.springframework.mock.web.MockHttpServletResponse;
import org.springframework.restdocs.operation.Operation;
import org.springframework.restdocs.snippet.Snippet;
import org.springframework.test.web.servlet.MvcResult;
import static org.mockito.BDDMockito.given;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
/**
* Tests for {@link RestDocumentationResultHandler}.
*
* @author Andy Wilkinson
*/
public class RestDocumentationResultHandlerTests {
@Test
public void additionalSnippetsAreOnlyCalledOnce() throws Exception {
Snippet snippet = mock(Snippet.class);
RestDocumentationResultHandler resultHandler = new RestDocumentationResultHandler(
"test", snippet);
Snippet defaultSnippet = mock(Snippet.class);
Snippet additionalSnippet = mock(Snippet.class);
resultHandler.snippets(additionalSnippet);
MvcResult result = mock(MvcResult.class);
MockHttpServletRequest request = new MockHttpServletRequest("GET",
"http://localhost");
request.setAttribute("org.springframework.restdocs.mockmvc.defaultSnippets",
Arrays.asList(defaultSnippet));
given(result.getRequest()).willReturn(request);
given(result.getResponse()).willReturn(new MockHttpServletResponse());
resultHandler.handle(result);
resultHandler.handle(result);
verify(defaultSnippet, times(2)).document(Matchers.any(Operation.class));
verify(snippet, times(2)).document(Matchers.any(Operation.class));
verify(additionalSnippet, times(1)).document(Matchers.any(Operation.class));
}
}