Merge branch 'gh-57'

This commit is contained in:
Andy Wilkinson
2015-04-21 11:04:07 +01:00
3 changed files with 163 additions and 94 deletions

View File

@@ -26,6 +26,7 @@ import java.util.Map.Entry;
import org.springframework.http.MediaType;
import org.springframework.mock.web.MockHttpServletResponse;
import org.springframework.util.StringUtils;
import com.fasterxml.jackson.databind.ObjectMapper;
@@ -65,16 +66,19 @@ public abstract class LinkExtractors {
/**
* Returns the {@code LinkExtractor} for the given {@code contentType} or {@code null}
* if there is no extractor for the content type.
*
* @param contentType The content type
*
* @param contentType The content type, may include parameters
* @return The extractor for the content type, or {@code null}
*/
public static LinkExtractor extractorForContentType(String contentType) {
if (MediaType.APPLICATION_JSON_VALUE.equals(contentType)) {
return atomLinks();
}
else if ("application/hal+json".equals(contentType)) {
return halLinks();
if (StringUtils.hasText(contentType)) {
MediaType mediaType = MediaType.parseMediaType(contentType);
if (mediaType.isCompatibleWith(MediaType.APPLICATION_JSON)) {
return atomLinks();
}
if (mediaType.isCompatibleWith(HalLinkExtractor.HAL_MEDIA_TYPE)) {
return halLinks();
}
}
return null;
}
@@ -96,7 +100,10 @@ public abstract class LinkExtractors {
}
@SuppressWarnings("unchecked")
private static class HalLinkExtractor extends JsonContentLinkExtractor {
static class HalLinkExtractor extends JsonContentLinkExtractor {
private static final MediaType HAL_MEDIA_TYPE = new MediaType("application",
"hal+json");
@Override
public Map<String, List<Link>> extractLinks(Map<String, Object> json) {
@@ -141,7 +148,7 @@ public abstract class LinkExtractors {
}
@SuppressWarnings("unchecked")
private static class AtomLinkExtractor extends JsonContentLinkExtractor {
static class AtomLinkExtractor extends JsonContentLinkExtractor {
@Override
public Map<String, List<Link>> extractLinks(Map<String, Object> json) {

View File

@@ -0,0 +1,124 @@
/*
* Copyright 2014-2015 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.hypermedia;
import static org.junit.Assert.assertEquals;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.junit.runners.Parameterized.Parameters;
import org.springframework.mock.web.MockHttpServletResponse;
import org.springframework.util.FileCopyUtils;
/**
* Parameterized tests for {@link LinkExtractors} with various payloads.
*
* @author Andy Wilkinson
*/
@RunWith(Parameterized.class)
public class LinkExtractorsPayloadTests {
private final LinkExtractor linkExtractor;
private final String linkType;
@Parameters
public static Collection<Object[]> data() {
return Arrays.asList(new Object[] { LinkExtractors.halLinks(), "hal" },
new Object[] { LinkExtractors.atomLinks(), "atom" });
}
public LinkExtractorsPayloadTests(LinkExtractor linkExtractor, String linkType) {
this.linkExtractor = linkExtractor;
this.linkType = linkType;
}
@Test
public void singleLink() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("single-link"));
assertLinks(Arrays.asList(new Link("alpha", "http://alpha.example.com")), links);
}
@Test
public void multipleLinksWithDifferentRels() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("multiple-links-different-rels"));
assertLinks(Arrays.asList(new Link("alpha", "http://alpha.example.com"),
new Link("bravo", "http://bravo.example.com")), links);
}
@Test
public void multipleLinksWithSameRels() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("multiple-links-same-rels"));
assertLinks(Arrays.asList(new Link("alpha", "http://alpha.example.com/one"),
new Link("alpha", "http://alpha.example.com/two")), links);
}
@Test
public void noLinks() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("no-links"));
assertLinks(Collections.<Link> emptyList(), links);
}
@Test
public void linksInTheWrongFormat() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("wrong-format"));
assertLinks(Collections.<Link> emptyList(), links);
}
private void assertLinks(List<Link> expectedLinks, Map<String, List<Link>> actualLinks) {
Map<String, List<Link>> expectedLinksByRel = new HashMap<>();
for (Link expectedLink : expectedLinks) {
List<Link> expectedlinksWithRel = expectedLinksByRel.get(expectedLink
.getRel());
if (expectedlinksWithRel == null) {
expectedlinksWithRel = new ArrayList<>();
expectedLinksByRel.put(expectedLink.getRel(), expectedlinksWithRel);
}
expectedlinksWithRel.add(expectedLink);
}
assertEquals(expectedLinksByRel, actualLinks);
}
private MockHttpServletResponse createResponse(String contentName) throws IOException {
MockHttpServletResponse response = new MockHttpServletResponse();
FileCopyUtils.copy(new FileReader(getPayloadFile(contentName)),
response.getWriter());
return response;
}
private File getPayloadFile(String name) {
return new File("src/test/resources/link-payloads/" + this.linkType + "/" + name
+ ".json");
}
}

View File

@@ -16,112 +16,50 @@
package org.springframework.restdocs.hypermedia;
import static org.junit.Assert.assertEquals;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import static org.hamcrest.CoreMatchers.instanceOf;
import static org.hamcrest.CoreMatchers.nullValue;
import static org.junit.Assert.assertThat;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.junit.runners.Parameterized.Parameters;
import org.springframework.mock.web.MockHttpServletResponse;
import org.springframework.restdocs.hypermedia.Link;
import org.springframework.restdocs.hypermedia.LinkExtractor;
import org.springframework.restdocs.hypermedia.LinkExtractors;
import org.springframework.util.FileCopyUtils;
import org.springframework.restdocs.hypermedia.LinkExtractors.AtomLinkExtractor;
import org.springframework.restdocs.hypermedia.LinkExtractors.HalLinkExtractor;
/**
* Tests for {@link LinkExtractors}.
*
*
* @author Andy Wilkinson
*/
@RunWith(Parameterized.class)
public class LinkExtractorsTests {
private final LinkExtractor linkExtractor;
private final String linkType;
@Parameters
public static Collection<Object[]> data() {
return Arrays.asList(new Object[] { LinkExtractors.halLinks(), "hal" },
new Object[] { LinkExtractors.atomLinks(), "atom" });
}
public LinkExtractorsTests(LinkExtractor linkExtractor, String linkType) {
this.linkExtractor = linkExtractor;
this.linkType = linkType;
@Test
public void nullContentTypeYieldsNullExtractor() {
assertThat(LinkExtractors.extractorForContentType(null), nullValue());
}
@Test
public void singleLink() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("single-link"));
assertLinks(Arrays.asList(new Link("alpha", "http://alpha.example.com")), links);
public void emptyContentTypeYieldsNullExtractor() {
assertThat(LinkExtractors.extractorForContentType(""), nullValue());
}
@Test
public void multipleLinksWithDifferentRels() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("multiple-links-different-rels"));
assertLinks(Arrays.asList(new Link("alpha", "http://alpha.example.com"),
new Link("bravo", "http://bravo.example.com")), links);
public void applicationJsonContentTypeYieldsAtomExtractor() {
LinkExtractor linkExtractor = LinkExtractors
.extractorForContentType("application/json");
assertThat(linkExtractor, instanceOf(AtomLinkExtractor.class));
}
@Test
public void multipleLinksWithSameRels() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("multiple-links-same-rels"));
assertLinks(Arrays.asList(new Link("alpha", "http://alpha.example.com/one"),
new Link("alpha", "http://alpha.example.com/two")), links);
public void applicationHalJsonContentTypeYieldsHalExtractor() {
LinkExtractor linkExtractor = LinkExtractors
.extractorForContentType("application/hal+json");
assertThat(linkExtractor, instanceOf(HalLinkExtractor.class));
}
@Test
public void noLinks() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("no-links"));
assertLinks(Collections.<Link> emptyList(), links);
public void contentTypeWithParameterYieldsExtractor() {
LinkExtractor linkExtractor = LinkExtractors
.extractorForContentType("application/json;foo=bar");
assertThat(linkExtractor, instanceOf(AtomLinkExtractor.class));
}
@Test
public void linksInTheWrongFormat() throws IOException {
Map<String, List<Link>> links = this.linkExtractor
.extractLinks(createResponse("wrong-format"));
assertLinks(Collections.<Link> emptyList(), links);
}
private void assertLinks(List<Link> expectedLinks, Map<String, List<Link>> actualLinks) {
Map<String, List<Link>> expectedLinksByRel = new HashMap<>();
for (Link expectedLink : expectedLinks) {
List<Link> expectedlinksWithRel = expectedLinksByRel.get(expectedLink
.getRel());
if (expectedlinksWithRel == null) {
expectedlinksWithRel = new ArrayList<>();
expectedLinksByRel.put(expectedLink.getRel(), expectedlinksWithRel);
}
expectedlinksWithRel.add(expectedLink);
}
assertEquals(expectedLinksByRel, actualLinks);
}
private MockHttpServletResponse createResponse(String contentName) throws IOException {
MockHttpServletResponse response = new MockHttpServletResponse();
FileCopyUtils.copy(new FileReader(getPayloadFile(contentName)),
response.getWriter());
return response;
}
private File getPayloadFile(String name) {
return new File("src/test/resources/link-payloads/" + this.linkType + "/" + name
+ ".json");
}
}