包含 headers 列表的 REST 调用

REST Call with list of headers

我有以下用于调用休息调用的代码片段。我有大约 8 headers 可以通过这个休息电话。但问题是很难管理。如果将来 headers 的列表增加,我需要更改 evaluateChange 方法签名以包含额外的 headers 作为方法 params.

@Path("/v1/restclienturi/")
@Consumes({ MediaType.APPLICATION_JSON })
@Produces({ MediaType.APPLICATION_JSON })
public interface RestClient {

    @POST
    @Path("/samplecall/evaluate")
    Response evaluateChange(
            @HeaderParam("HEADER1") String header1,
            @HeaderParam("HEADER2") String header2,
            @HeaderParam("HEADER3") String header3,
            @HeaderParam("HEADER4") String header4,
            @HeaderParam("HEADER5") String header5,
            @HeaderParam("HEADER6") String header6,
            @HeaderParam("HEADER7") String header7,
            @HeaderParam("HEADER8") String header8,
            @Context HttpServletResponse response, Request request);
}

请提供您的想法或代码片段来适应这一点。

我尝试了以下代码片段,但它不起作用(其中 headerMap 包含其中的所有 8 headers):

@Path("/v1/restclienturi/")
@Consumes({ MediaType.APPLICATION_JSON })
@Produces({ MediaType.APPLICATION_JSON })
public interface RestClient {

    @POST
    @Path("/samplecall/evaluate")
    Response evaluateChange(
            @RequestHeader Map<String, String> headerMap,
            @Context HttpServletResponse response, Request request);
}

不太清楚你的意思,但如果你想得到所有的headers,这个怎么样:

public Response evaluateChange(@Context HttpHeaders headers, ...) {
    String header1 = headers.getRequestHeader("HEADER1").get(0);
    ...
}

在这里找到了更多关于此的代码:http://www.mkyong.com/webservices/jax-rs/get-http-header-in-jax-rs/

编辑:如何使用 key-values 的映射调用方法。

public class MapHttpHeaders implements HttpHeaders {
   private Map<String, String> values;

   public MapHttpHeaders(Map<String, String> values) {
      this.values = values;
   }

   @Override
   public String getHeaderString(String key) {
      return values.get(key);
   }

   @Override
   public List<String> getRequestHeader(String key) {
      String value = getHeaderString(key);
      if (value == null) {
         return null;
      } else {
         return asList(value);
      }
   }
   ...and so on...
}

然后就这样做:

evaluateChange(new MapHttpHeaders(values), ...);

你不能直接注入 HttpServletRequest 然后使用它的 getHeader(String name) 方法吗?

API

@POST
@Path("/samplecall/evaluate")
Response evaluateChange(
        @RequestHeader Map<String, String> headerMap,
        @Context HttpServletResponse response, 
        @Context HttpServletRequest httpRequest,
        Request request);

实现

@Override
public Response evaluateChange(
        @RequestHeader Map<String, String> headerMap,
        @Context HttpServletResponse response, 
        @Context HttpServletRequest httpRequest,
        Request request) {


    String header1 = httpRequest.getHeader("HEADER1");
    ...

当然,这样你就在实现中隐藏了部分合约。

我找到了使用 javax.ws.rs.core.Form 的解决方案:

 @Path("/v1/restclienturi/")
@Consumes({ MediaType.APPLICATION_JSON })
@Produces({ MediaType.APPLICATION_JSON })
public interface RestClient {

    @POST
    @Path("/samplecall/evaluate")
    Response evaluateChange(
            @Form MyHeader headers,
            @Context HttpServletResponse response, Request request);
}

下面是 MyHeader 是一个 pojo:

public class MyHeader{
@HeaderParam("HEADER1")
    private String header1;

    @HeaderParam("HEADER2")
    private String header2;
.....
// getters and setters present
}

实例化 MyHeader 并设置值以将其传递给 REST 服务,例如:

MyHeader headers = new MyHeader();
headers.setHeader1("HEADER1_VALUE");
...

并调用:evaluateChange(headers, null,request);

问题: 这种方法的一个很大的问题是,每次添加一个新的 header 时,我们都需要更改代码来设置和获取值。如果解决方案类似于作为集合传递,那么在添加新 header 时我们不会涉及代码更改。喜欢:

Map<String,String> headersMap = new HashMap();
headers.put("HEADER1","HEADER1_VALUE");
....
evaluateChange(headersMap,null,request);

我正在寻找这样的解决方案。但是上面的代码不起作用。寻找建议。

不确定为什么要尝试 Map 而不仅仅是 List:

@Path("/v1/restclienturi/")
@Consumes({ MediaType.APPLICATION_JSON })
@Produces({ MediaType.APPLICATION_JSON })
public interface RestClient {

    @POST
    @Path("/samplecall/evaluate")
    Response evaluateChange(
            @HeaderParam("HEADER") List<String> headers,
            @Context HttpServletResponse response, Request request
    );
}

现在我没有测试这个,但这需要调用所有 HeaderParams 'HEADER',并且它们 will/should 按照出现的顺序存储在 List<String> 中。

您可以将 MultivaluedHashMap (javax.ws.rs.core.MultivaluedHashMap) 中的所有 headers 集发送到表单。这是 Form 可接受的构造函数参数。

    MultivaluedMap<String, String> headerMap = new MultivaluedHashMap<String, String>();
    headersMap.putSingle("HEADER1","HEADER1_VALUE");
    headersMap.putSingle("HEADER2","HEADER1_VALUE");
    .
    .
    .
    headersMap.putSingle("HEADER8","HEADER8_VALUE");

    evaluateChange(headersMap,null,request);

并如下更改 evaluateChange

Response evaluateChange(
        @Form MultivaluedMap headers,
        @Context HttpServletResponse response, Request request);

希望这对您有所帮助..祝您好运!!