カスタムを実装する必要なく、Jerseyにはフォーマットの「拡張子」をチェックするUriConnegFilter
があります。例
https://example.com/rest/countries.xml
https://example.com/rest/countries.json
のためにあなたは、マッピング
final Map<String, MediaType> mappings = new HashMap<>();
mappings.put("json", MediaType.APPLICATION_JSON_TYPE);
mappings.put("xml", MediaType.APPLICATION_XML_TYPE);
return new ResourceConfig()
.property(ServerProperties.MEDIA_TYPE_MAPPINGS, mappings);
を設定する必要がありますここでは、単にメディアタイプの拡張をマッピングしています。ジャージーは残りをするでしょう。
実際にクエリパラメータを使用する場合は、@PreMatching
ContainerRequestFilter
と入力してクエリパラメータを確認し、それに応じてAccept
ヘッダーを設定します。
@Provider
@PreMatching
@Priority(3000)
public static class QueryConnegFilter implements ContainerRequestFilter {
private static final Map<String, String> mappings;
static {
Map<String, String> map = new HashMap<>();
map.put("xml", MediaType.APPLICATION_XML);
map.put("json", MediaType.APPLICATION_JSON);
mappings = Collections.unmodifiableMap(map);
}
@Override
public void filter(ContainerRequestContext request) throws IOException {
final String format = request.getUriInfo().getQueryParameters().getFirst("format");
if (format != null) {
final String mediaType = mappings.get(format);
if (mediaType != null) {
request.getHeaders().putSingle(HttpHeaders.ACCEPT, mediaType);
}
}
}
}
次にアプリケーションに登録するだけで済みます。今、あなたはここで
https://example.com/rest/countries?format=xml
https://example.com/rest/countries?format=json
を行うことができますフォーマットはリクエストパラメータとして渡す必要がある
import org.glassfish.jersey.filter.LoggingFilter;
import org.glassfish.jersey.server.ResourceConfig;
import org.glassfish.jersey.server.ServerProperties;
import org.glassfish.jersey.test.JerseyTest;
import org.junit.Test;
import javax.annotation.Priority;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.container.ContainerRequestContext;
import javax.ws.rs.container.ContainerRequestFilter;
import javax.ws.rs.container.PreMatching;
import javax.ws.rs.core.HttpHeaders;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.ext.Provider;
import javax.xml.bind.annotation.XmlRootElement;
import java.io.IOException;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.logging.Logger;
import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.CoreMatchers.is;
import static org.hamcrest.MatcherAssert.assertThat;
/**
* Run it like any other JUnit test. Only two required dependencies:
*
* <dependency>
* <groupId>org.glassfish.jersey.test-framework.providers</groupId>
* <artifactId>jersey-test-framework-provider-grizzly2</artifactId>
* <version>${jersey2.version}</version>
* </dependency>
* <dependency>
* <groupId>org.glassfish.jersey.media</groupId>
* <artifactId>jersey-media-json-jackson</artifactId>
* <version>${jersey2.version}</version>
* </dependency>
*
* @author Paul Samsotha.
*/
public class UriConnegTests extends JerseyTest {
@XmlRootElement
public static class Model {
private String message;
public Model() {}
public Model(String message) { this.message = message; }
public String getMessage() { return this.message; }
public void setMessage(String message) { this.message = message; }
}
@Path("test")
public static class TestResource {
@GET
@Produces({"application/json", "application/xml"})
public Model get() {
return new Model("Hello World");
}
}
@Provider
@PreMatching
@Priority(3000)
public static class QueryConnegFilter implements ContainerRequestFilter {
private static final Map<String, String> mappings;
static {
Map<String, String> map = new HashMap<>();
map.put("xml", MediaType.APPLICATION_XML);
map.put("json", MediaType.APPLICATION_JSON);
mappings = Collections.unmodifiableMap(map);
}
@Override
public void filter(ContainerRequestContext request) throws IOException {
final String format = request.getUriInfo().getQueryParameters().getFirst("format");
if (format != null) {
final String mediaType = mappings.get(format);
if (mediaType != null) {
request.getHeaders().putSingle(HttpHeaders.ACCEPT, mediaType);
}
}
}
}
@Override
public ResourceConfig configure() {
final Map<String, MediaType> mappings = new HashMap<>();
mappings.put("json", MediaType.APPLICATION_JSON_TYPE);
mappings.put("xml", MediaType.APPLICATION_XML_TYPE);
return new ResourceConfig()
.register(TestResource.class)
.register(QueryConnegFilter.class)
.register(new LoggingFilter(Logger.getAnonymousLogger(), true))
.property(ServerProperties.MEDIA_TYPE_MAPPINGS, mappings);
}
@Test
public void returnsXmlFromExtension() {
final String expected = "<message>Hello World</message>";
final String data = target("test.xml")
.request()
.get(String.class);
assertThat(data, containsString(expected));
}
@Test
public void returnsJsonFromExtension() {
final String expected = "{\"message\":\"Hello World\"}";
final String data = target("test.json")
.request()
.get(String.class);
assertThat(data, is(expected));
}
@Test
public void returnsXmlFromQuery() {
final String expected = "<message>Hello World</message>";
final String data = target("test")
.queryParam("format", "xml")
.request()
.get(String.class);
assertThat(data, containsString(expected));
}
@Test
public void returnsJsonFromQuery() {
final String expected = "{\"message\":\"Hello World\"}";
final String data = target("test")
.queryParam("format", "json")
.request()
.get(String.class);
assertThat(data, is(expected));
}
}
上記の両方のオプションとの完全な作業テストです。ヘッダー内のフォーマットを渡すことは私の選択肢ではありません。 – eztam
ヘッダーを使用しないと、あなたはそれを持っていると思います。あなたはさらに、toxml/tojsonメソッドを汎用の "toFormat"メソッドの背後にあるユーティリティに抽象化することができます。これはロジックを押し戻し、サービスクラスでコードがよりきれいに見えるようにします。それともこの記事はhttp://stackoverflow.com/questions/20212405/how-to-set-accept-header-on-the-server-side-in-jersey-1-x-for-an-incoming-を助けます要求する。 – caburse