Java 使用jersey 2客户端刷新OAuth令牌

Java 使用jersey 2客户端刷新OAuth令牌,java,jersey,jersey-2.0,jersey-client,Java,Jersey,Jersey 2.0,Jersey Client,我目前正在将一个应用程序从jersey 1迁移到jersey 2。在旧应用程序中,我们对所有jersey客户端使用了ClientFilter,这些客户端自动刷新过期的OAuth令牌,如下所示: @覆盖 公共ClientResponse句柄(ClientRequest cr){ ClientResponse resp=getNext().handle(cr); if(resp.getStatus()==Status.UNAUTHORIZED.getStatusCode()){ //尝试刷新令牌 布

我目前正在将一个应用程序从jersey 1迁移到jersey 2。在旧应用程序中,我们对所有jersey客户端使用了
ClientFilter
,这些客户端自动刷新过期的OAuth令牌,如下所示:

@覆盖
公共ClientResponse句柄(ClientRequest cr){
ClientResponse resp=getNext().handle(cr);
if(resp.getStatus()==Status.UNAUTHORIZED.getStatusCode()){
//尝试刷新令牌
布尔刷新=刷新令牌(oAuthInfo);
如果(刷新){
resp=getNext().handle(cr);
}
}
返回响应;
}
这可能不是最优雅的方式,但好处是rest客户端用户自己不必关心过期的令牌


对于jersey 2的
ContainerResponseFilter
,这似乎不再那么简单了。我目前看到的唯一选项是使用
ClientRequestContext
,并尝试使用
getClient
getHeaders
等重新创建原始请求。。。然后在
ContainerResponseContext
中更新结果。然而,这似乎有点笨拙,因此我想知道,在使用jersey客户端的地方,是否有更方便的方法刷新OAuth令牌而不必处理此问题?

看起来没有比使用客户端筛选器截取响应更方便的方法了,如果需要,刷新令牌并尝试使用新令牌重复完全相同的请求。事实上,jersey自己的过滤器类也使用这种方法

在Jersey中可以找到从筛选器类中重复原始rest调用的示例代码:

静态布尔repeatRequest(ClientRequestContext请求、ClientResponseContext响应、字符串newAuthorizationHeader){
Client Client=request.getClient();
String方法=request.getMethod();
MediaType MediaType=request.getMediaType();
URI lUri=request.getUri();
WebTarget resourceTarget=client.target(lUri);
Invocation.Builder=resourceTarget.request(mediaType);
MultivaluedMap newHeaders=新的MultivaluedHashMap();
对于(Map.Entry:request.getHeaders().entrySet()){
if(HttpHeaders.AUTHORIZATION.equals(entry.getKey())){
继续;
}
newHeaders.put(entry.getKey(),entry.getValue());
}
添加(HttpHeaders.AUTHORIZATION,newAuthorizationHeader);
builder.headers(newHeaders);
builder.property(请求\属性\过滤器\重用,“true”);
调用调用;
if(request.getEntity()==null){
调用=builder.build(方法);
}否则{
调用=builder.build(方法,
Entity.Entity(request.getEntity(),request.getMediaType());
}
Response nextResponse=invocation.invoke();
if(nextResponse.hasEntity()){
response.setEntityStream(nextResponse.readEntity(InputStream.class));
}
多值Map headers=response.getHeaders();
headers.clear();
headers.putAll(nextResponse.getStringHeaders());
response.setStatus(nextResponse.getStatus());
返回response.getStatus()!=response.Status.UNAUTHORIZED.getStatusCode();
}
例如,如果从服务器收到
未经授权的
响应,此代码用于或重复具有所提供凭据的请求

static boolean repeatRequest(ClientRequestContext request, ClientResponseContext response, String newAuthorizationHeader) {
    Client client = request.getClient();

    String method = request.getMethod();
    MediaType mediaType = request.getMediaType();
    URI lUri = request.getUri();

    WebTarget resourceTarget = client.target(lUri);

    Invocation.Builder builder = resourceTarget.request(mediaType);

    MultivaluedMap<String, Object> newHeaders = new MultivaluedHashMap<String, Object>();

    for (Map.Entry<String, List<Object>> entry : request.getHeaders().entrySet()) {
        if (HttpHeaders.AUTHORIZATION.equals(entry.getKey())) {
            continue;
        }
        newHeaders.put(entry.getKey(), entry.getValue());
    }

    newHeaders.add(HttpHeaders.AUTHORIZATION, newAuthorizationHeader);
    builder.headers(newHeaders);

    builder.property(REQUEST_PROPERTY_FILTER_REUSED, "true");

    Invocation invocation;
    if (request.getEntity() == null) {
        invocation = builder.build(method);
    } else {
        invocation = builder.build(method,
                Entity.entity(request.getEntity(), request.getMediaType()));
    }
    Response nextResponse = invocation.invoke();

    if (nextResponse.hasEntity()) {
        response.setEntityStream(nextResponse.readEntity(InputStream.class));
    }
    MultivaluedMap<String, String> headers = response.getHeaders();
    headers.clear();
    headers.putAll(nextResponse.getStringHeaders());
    response.setStatus(nextResponse.getStatus());

    return response.getStatus() != Response.Status.UNAUTHORIZED.getStatusCode();
}