David David - 5 months ago 125
Android Question

Set custom cookie in Retrofit

Is there a way to set a custom cookie on retrofit requests?

Either by using the

RequestInterceptor
or any other means?

Answer

Through the retrofit.RequestInterceptor:

@Override
public void intercept(RequestFacade request) {    
     request.addHeader("Cookie", "cookiename=cookievalue");
}

You can set a custom RequestInterceptor as follows:

String cookieKey = ...
String cookieValue = ...

RestAdapter adapter = new RestAdapter.Builder()
    .setRequestInterceptor(new RequestInterceptor() {
      @Override
      public void intercept(RequestFacade request) {
        // assuming `cookieKey` and `cookieValue` are not null 
        request.addHeader("Cookie", cookieKey + "=" + cookieValue);
      }
    })
    .setServer("http://...")
    .build();

YourService service = adapter.create(YourService.class);

And to read any cookies set by the server, attach a custom cookie manager like this:

OkHttpClient client = new OkHttpClient();
CustomCookieManager manager = new CustomCookieManager();
client.setCookieHandler(manager);

RestAdapter adapter = new RestAdapter.Builder()
    .setClient(new OkClient(client))
    ...
    .build();

where CustomCookieManager could look like this:

public class CustomCookieManager extends CookieManager {

  // The cookie key we're interested in.    
  private final String SESSION_KEY = "session-key";

  /**
   * Creates a new instance of this cookie manager accepting all cookies.
   */
  public CustomCookieManager() {
    super.setCookiePolicy(CookiePolicy.ACCEPT_ALL);
  }

  @Override
  public void put(URI uri, Map<String, List<String>> responseHeaders) throws IOException {

    super.put(uri, responseHeaders);

    if (responseHeaders == null || responseHeaders.get(Constants.SET_COOKIE_KEY) == null) {
      // No cookies in this response, simply return from this method.
      return;
    }

    // Yes, we've found cookies, inspect them for the key we're looking for.
    for (String possibleSessionCookieValues : responseHeaders.get(Constants.SET_COOKIE_KEY)) {

      if (possibleSessionCookieValues != null) {

        for (String possibleSessionCookie : possibleSessionCookieValues.split(";")) {

          if (possibleSessionCookie.startsWith(SESSION_KEY) && possibleSessionCookie.contains("=")) {

            // We can safely get the index 1 of the array: we know it contains
            // a '=' meaning it has at least 2 values after splitting.
            String session = possibleSessionCookie.split("=")[1];

            // store `session` somewhere

            return;
          }
        }
      }
    }
  }
}
Comments