2014-01-20 24 views
14

我需要知道如何在改进中添加授权cookie头。我看到了使用请求拦截器等的建议。下面是我正在尝试的,但是这是正确的吗?首先,我已经需要一个RequestAdatper来第一次获得会话ID。这只能由请求适配器的构建者设置。但是我需要提出一个请求来获取会话ID。我需要两个休息适配器,一个获得sessionId,另一个获取它之后。我真正需要的是一个适配器上的方法来设置cookie后,我得到它,但它似乎并不是这样一种方法。这变得尴尬。如何在改造中设置授权cookie?我在常见问题或教程中看不到这一点。RETROFIT&AUTH COOKIE

RequestInterceptor requestInterceptor = new RequestInterceptor() 
{ 
    @Override 
    public void intercept(RequestFacade request) { 
     request.addHeader("Set-Cookie", "sessionId="+sessionIdentifier); 
    } 
}; 

RestAdapter.Builder().setServer(serverURL)..setRequestIntercepter(requestIntercepter).build(); 

// but I don't have sessionId when this is first issued ??? 
+1

可能不需要为我的应用程序。但它是一个很好的问题,所以有人请回答。 – user3186731

+0

你最终做了什么,因为答案中的代码只是令人困惑......试图将它包含在我呼叫我的请求的同一页面中。 – Lion789

回答

26

保留对拦截器的引用,并将其视为单个元素,就像你自己会是RestAdapter一样。

public class ApiHeaders implements RequestInterceptor { 
    private String sessionId; 

    public void setSessionId(String sessionId) { 
    this.sessionId = sessionId; 
    } 

    public void clearSessionId() { 
    sessionId = null; 
    } 

    @Override public void intercept(RequestFacade request) { 
    if (sessionId != null) { 
     request.setHeader(...); 
    } 
    } 
} 

现在,只需在您的验证呼叫后致电setSessionId。所有后续请求都将包含标题。

+0

试图找出如何从类的外部调用setSessionId ... ApiHeaders.setSessionId不是一种方法... – Lion789

+0

@ Lion789你需要一个静态的setSessionId。 – wendigo

+0

@Jake Wharton:我们如何从响应中获得sessionId? – Chetna

12

你可以得到饼干这样

public class MyCookieManager extends CookieManager { 

    @Override 
    public void put(URI uri, Map<String, List<String>> stringListMap) throws IOException { 
     super.put(uri, stringListMap); 
     if (stringListMap != null && stringListMap.get("Set-Cookie") != null) 
      for (String string : stringListMap.get("Set-Cookie")) { 
       if (string.contains("JSESSIONID")) { 
        Preference.getInstance().setSessionId(string); 
       } 
      } 
    } 
} 

使用此设置的CookieHandler

MyCookieManager myCookieManager = new MyCookieManager(); 
     CookieHandler.setDefault(myCookieManager); 

,然后在您的要求使用这样的拦截

String sessionId = preference.getSessionId(); 
        if (sessionId != null) 
         requestFacade.addHeader(Cookie, sessionId); 
+0

工作得很好!谢谢@Chetna! –

7

步骤1.分析响应标头。 在覆盖success方法中调用此方法在您的回调中。

/** 
    * Method extracts cookie string from headers 
    * @param response with headers 
    * @return cookie string if present or null 
    */ 
    private String getCookieString(Response response) { 
     for (Header header : response.getHeaders()) { 
      if (null!= header.getName() && header.getName().equals("Set-Cookie")) { 
       return header.getValue(); 
      } 
     } 
     return null; 
    } 

步骤2.写一些静态类或单身保持Cookie,而且RequestInterceptor实例。在RequestInterceptor内部覆盖拦截方法来将你的cookies添加到Header。

public class RestAdapter { 
    private static String cookies; 

    public static String getCookies() { 
     return cookies; 
    } 

    public static void setCookies(String cookies) { 
     RestAdapter.cookies = cookies; 
    } 

    /** 
    * Injects cookies to every request 
    */ 
    private static final RequestInterceptor COOKIES_REQUEST_INTERCEPTOR = new RequestInterceptor() { 
     @Override 
     public void intercept(RequestFacade request) { 
      if (null != cookies && cookies.length() > 0) { 
       request.addHeader("Cookie", cookies); 
      } 
     } 
    }; 

    public static final RestInterface getService() { 
     return new RestAdapter.Builder() 
       .setEndpoint(Config.ENDPOINT) 
       .setRequestInterceptor(COOKIES_REQUEST_INTERCEPTOR) 
       .setConverter(new JacksonConverter()) 
       .setLogLevel(RestAdapter.LogLevel.NONE) 
       .build() 
       .create(RestInterface.class); 
    } 
} 
0

使用lib的简单解决方案。编译com.squareup.okhttp3:okhttp-urlconnection:3.2.0

JavaNetCookieJar jncj = new JavaNetCookieJar(CookieHandler.getDefault()); OkHttpClient.Builder().cookieJar(jncj).build();

4

据@ sbtgE的答案,但有一些修正。 CookieHandler.getDefault()可能为空,所以我使用CookieManager。

应用程序的的build.gradle:

dependencies { 
    ... 
    compile 'com.squareup.okhttp3:okhttp-urlconnection:3.4.1' 
} 

设置改造:

service = new Retrofit.Builder() 
     .baseUrl(/* your base URL */) 
     .addConverterFactory(/* your favourite converter */) 
     .client(
       new OkHttpClient.Builder() 
         // this line is the important one: 
         .cookieJar(new JavaNetCookieJar(new CookieManager())) 
         .build()) 
     .build() 
     .create(YourInterface.class); 
+0

如何在断开连接时清除cookie。 –

相关问题