使用Okhttp持久化Cookie

前言

依赖:

compile ‘com.squareup.okhttp3:okhttp:3.10.0’

对于简单的使用方法这里不做赘述了,一般的项目中都是需要登录再去获取对应的接口的数据,这里针对于登录后保持cookie然后访问剩余接口信息的功能实现

新建一个HttpClient

            OkHttpClient httpClient = new OkHttpClient.Builder()
                        .cookieJar(new CookieJar() {

                            //自定义
                            private final HashMap> cookieStore = new HashMap>();

                            //复写
                            @Override
                            public void saveFromResponse(HttpUrl url, List cookies) {
                                cookieStore.put(url,cookies);
                            }

                            //复写
                            @Override
                            public List loadForRequest(HttpUrl url) {
                                List cookies = cookieStore.get(url);
                                return cookies != null ? cookies : new ArrayList();
                            }
                        }).build();

所谓的Cookie我们可以简单的理解为存储的为键值对:key = value,我们建立一个HashMap作为存储url为key,对应的url服务器返回给我们的cookie数组

一个cookie就是一对值,服务器可能返回给我们的多个cookie,例如:

name = Tom 一个cookie

age = 13 另外一个cookie

saveFromResponse(HttpUrl url,List cookies),用来获取服务器端返回的Response中返回的Cookies(可能是很多个),存储在cookieStore这个变量中

loadForRequest(HttpUrl url),用来根据url这个key来从cookieStore中获取去对应的所有的Cookie

登录代码

                //创建Form表单
                FormBody loginBody = new FormBody.Builder()
                        .add("username","admin")
                        .add("password","admin")
                        .build();

                //创建请求
                final Request loginRequest = new Request.Builder()
                        .url("http://192.168.1.21:8080/manage/user/login.do")
                        .post(loginBody)
                        .build();

                //发起网络连接
                okhttp3.Call loginCall = httpClient.newCall(loginRequest);
                try {
                    okhttp3.Response loginResponse = loginCall.execute();
                    String loginResutl = loginResponse.body().string();
                    //isSuccessFul没有做处理 这里是成功的返回

                    //从登录成功后的Response中获取所有的Cookie
                    Headers loginHeaders = loginResponse.headers();
                    HttpUrl loginUrl = loginRequest.url();
                    List cookies = Cookie.parseAll(loginUrl,loginHeaders);
                    if(cookies!=null){
                        //将登录成功的Url对应的所有的Cookie通过Cookiejar的方法保存到cookieStore中去,方便我们下次根据登录成功的url来获取对应的cookie
                        httpClient.cookieJar().saveFromResponse(loginUrl,cookies);
                    }

                    Log.d(TAG,loginResutl);
                } catch (IOException e) {
                    e.printStackTrace();
                }

登录成功后访问其他的接口


                //根据cookieStore中拿到登录成功url对应的cookie,拼接成key = value的形式的字符串
                StringBuilder cookieStr = new StringBuilder();
                List cookies = httpClient.cookieJar().loadForRequest(loginRequest.url());
                for(Cookie cookie : cookies){
                    cookieStr.append(cookie.name()).append("=").append(cookie.value());
                }

                //这是一个查询产品详细信息的接口
                FormBody contentBody = new FormBody.Builder()
                        .add("productId","29")
                        .build();
                //将cookie信息放到请求头中去
                Request contentRequest = new Request.Builder()
                        .url("http://192.168.1.21:8080/manage/product/detail.do")
                        .header("Cookie",cookieStr.toString())
                        .post(contentBody)
                        .build();


                okhttp3.Call contentCall = httpClient.newCall(contentRequest);
                try {
                    okhttp3.Response contentResponse = contentCall.execute();
                    String contentResult = contentResponse.body().string();
                    Log.d(TAG,contentResult);
                } catch (IOException e) {
                    e.printStackTrace();
                }

Cookie作为持久化的机制

首先,Cookie是存储在客户端也可认为是浏览器端,Session存储在服务器端,当我们登录淘宝后是不是就可以访问淘宝的所有的网站了,而不是访问一个页面就要登录一次吧,这里就是Session和Cookie在起作用


浏览器 - - - - - - > 服务器(服务器为用户创建一个Session)

浏览器 <- - - SessionID返回- - - 服务器(服务器在确认登录成功后可以在session存储一些标示这个用户的唯一信息)

浏览器就SeesionId保存在了Cookie中,接着用户访问其他页面的时候,服务器就知道该用户的Session是哪一个并从中取出标示信息和该用户的信息做比对,匹配上了就说明这个回话存在即用户不需要登录就可以接着访问页面了

小结

从上面的代码逻辑来看的话,关键点在于获取登录成功后服务器返回的Cookie信息,并将Cookie信息作为访问其他页面的Cookie信息即可

所以我们也可以自己去处理而不用使用new CookieJar()的形式,可以自己单独将登录成功后的Cookie信息单独拿出来保存即可

当我们想要实现免密登录,我们只需要将Cookie存储在文件中或者数据库中即可

你可能感兴趣的:(android)