栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 面试经验 > 面试问答

在Jersey中限制路径媒体类型映射

面试问答 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

在Jersey中限制路径媒体类型映射

首先,这绝不是错误。这是预期的行为。媒体类型映射的目的与处理文件无关,而是在内容标头可能不可用的情况下(例如在浏览器中)使用内容协商的另一种形式。

尽管不在正式规范中,但此功能是规范最终发布之前的草案的一部分。大多数实现都决定以一种或另一种方式包含它。泽西碰巧让您对其进行配置。因此可以在3.7.1请求预处理的规范中看到此处

    • M
      =
      {config.getMediaTypeMappings().keySet()}
    • L
      =
      {config.getLanguageMappings().keySet()}
    • m
      =
      null
    • l
      =
      null
    • 其中config是ApplicationConfig的应用程序提供的子类的实例。
    • 对于最终路径段中从右到左扫描的每个扩展名(一个

      .
      字符后跟一个或多个字母数字字符)
      e

    • (a)删除开头的“。” 来自的字符

      e

    • (b)如果
      m
      is
      null
      e
      is是的成员,
      M
      则从有效请求URI中删除相应的扩展名并设置
      m = e
    • (c)如果
      l
      is是
      null
      e
      is的成员,
      L
      则从有效请求URI中删除相应的扩展名并设置
      l = e
      。否则转到步骤4
    • 如果m不为null,则将Accept标头的值设置为
      config.getExtensionMappings().get(m)

3(b)基本上是说应将扩展名从请求的URI中删除,而4则表示应该有一些扩展名映射,将

json
(扩展名)映射到该扩展名
application/json
并将其设置为
Accept
标头。您可以从不同的测试中看到这种行为

@POST@Path("/files/{file}")@Produces({MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML})public Response doTest(@PathParam("file") String fileName, @Context HttpHeaders headers) {    String accept = headers.getHeaderString(HttpHeaders.ACCEPT);    return Response.ok(fileName + "; Accept: " + accept).build();}...Map<String, MediaType> map = new HashMap<>();map.put("xml", MediaType.APPLICATION_XML_TYPE);resourceCnfig.property(ServerProperties.MEDIA_TYPE_MAPPINGS, map);

curl -v http://localhost:8080/api/mapping/files/file.xml -X POST

结果:
file; Accept: application/xml

如果我们注释掉该配置属性,您将看到

Accept
尚未设置标头。

curl -v http://localhost:8080/api/mapping/files/file.xml -X POST

结果:
file.xml; Accept: */**

话虽如此…

配置时

ServerProperties.MEDIA_TYPE_MAPPINGS
org.glassfish.jersey.server.filter.UriConnegFilter
就是用于此功能的过滤器。您可以在源代码的204和211行中看到,其中过滤器正在剥离扩展名。

path = new StringBuilder(path).delete(index, index + suffix.length() + 1).toString();...rc.setRequestUri(uriInfo.getRequestUriBuilder().replacePath(path).build(new Object[0]));

因此,没有办法进行配置(至少就我看源代码而言),因此我们将不得不扩展该类,重写该

filter
方法,并至少取出实际进行替换的最后一行,然后注册过滤器。这是我为使其正常工作所做的。我只是复制并粘贴了过滤器中的代码,并在替换扩展名的行中添加了注释

import java.io.IOException;import java.util.List;import java.util.Map;import javax.annotation.Priority;import javax.ws.rs.container.ContainerRequestContext;import javax.ws.rs.container.PreMatching;import javax.ws.rs.core.Configuration;import javax.ws.rs.core.Context;import javax.ws.rs.core.MediaType;import javax.ws.rs.core.PathSegment;import javax.ws.rs.core.UriInfo;import org.glassfish.jersey.server.filter.UriConnegFilter;@PreMatching@Priority(3000)public class MyUriConnegFilter extends UriConnegFilter {    public MyUriConnegFilter(@Context Configuration config) {        super(config);    }    public MyUriConnegFilter(Map<String, MediaType> mediaTypeMappings,        Map<String, String> languageMappings) {        super(mediaTypeMappings, languageMappings);    }    @Override    public void filter(ContainerRequestContext rc) throws IOException {        UriInfo uriInfo = rc.getUriInfo();        String path = uriInfo.getRequestUri().getRawPath();        if (path.indexOf('.') == -1) { return;        }        List<PathSegment> l = uriInfo.getPathSegments(false);        if (l.isEmpty()) { return;        }        PathSegment segment = null;        for (int i = l.size() - 1; i >= 0; i--) { segment = (PathSegment) l.get(i); if (segment.getPath().length() > 0) {     break; }        }        if (segment == null) { return;        }        int length = path.length();        String[] suffixes = segment.getPath().split("\.");        for (int i = suffixes.length - 1; i >= 1; i--) { String suffix = suffixes[i]; if (suffix.length() != 0) {     MediaType accept = (MediaType) this.mediaTypeMappings.get(suffix);     if (accept != null) {         rc.getHeaders().putSingle("Accept", accept.toString());         int index = path.lastIndexOf('.' + suffix);         path = new StringBuilder(path).delete(index, index + suffix.length() + 1).toString();         suffixes[i] = "";         break;     } }        }        for (int i = suffixes.length - 1; i >= 1; i--) { String suffix = suffixes[i]; if (suffix.length() != 0) {     String acceptLanguage = (String) this.languageMappings.get(suffix);     if (acceptLanguage != null) {         rc.getHeaders().putSingle("Accept-Language", acceptLanguage);         int index = path.lastIndexOf('.' + suffix);         path = new StringBuilder(path).delete(index, index + suffix.length() + 1).toString();         suffixes[i] = "";         break;     } }        }        if (length != path.length()) { //rc.setRequestUri(uriInfo.getRequestUriBuilder().replacePath(path).build(new Object[0]));        }    }}

然后配置它

Map<String, MediaType> map = new HashMap<>();map.put("xml", MediaType.APPLICATION_XML_TYPE);map.put("json", MediaType.APPLICATION_JSON_TYPE);resourceConfig.register(new MyUriConnegFilter(map, null));

curl -v http://localhost:8080/api/mapping/files/file.xml -X POST

结果:
file.xml; Accept: application/xml

curl -v http://localhost:8080/api/mapping/files/file.json -X POST

结果:
file.json; Accept: application/json



转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/570936.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号