Android中的网络请求:

httpUrlConnection

在Android 2.2及以下版本使用 httpURLconnection存在一些bug,所以建议在2.2及以下使用httpClient,2.3及以上使用httpUrlConnection。

**特点:

1.API简单,体积较小,因而非常适用于Android项目。
2.压缩和缓存机制可以有效地减少网络访问的流量,在提升速度和省电方面也起到了较大的作用。

**用法

1.get一般用于从服务器获取数据,post一般用于向服务器提交数据。
2.设置请求方式使用函数setRequestMethod(“POST”)进行设置。
3.获取服务器返回的输入流,使用getInputStream方法获取。
4.关闭连接,通过disconnect方法关闭当前的连接。

**get

public String get(String urlPath){
        HttpURLConnection connection = null;
        InputStream is = null;
        try {
            URL url = new URL(urlPath);
            connection =      (HttpURLConnection)url.openConnection();
            connection.setRequestMethod("GET");
            //不使用缓存
            connection.setUseCaches(false);  
            connection.setConnectTimeout(3000);
            // 设置读取超时时间
            connection.setReadTimeout(3000);
            //设置是否从httpUrlConnection读入,默认情况下是true  
            connection.setDoInput(true);     
            if (connection.getResponseCode() == HttpURLConnection.HTTP_OK){
                is = connection.getInputStream();
                BufferedReader reader = new BufferedReader(new InputStreamReader(is));
                StringBuilder response = new StringBuilder();
                String line;
                while ((line = reader.readLine()) != null){
                    response.append(line);
                }
                return response.toString();
            }
        } catch (Exception e) {
            e.printStackTrace();
        }finally {
            if (connection != null){
                connection.disconnect();
                connection = null;
            }
        }
        if (is != null){
            try {
                is.close();
                is = null;
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return null;
    }

**post

public String post(String urlPath , Map<String , String> params){
        if (params == null || params.size() == 0 ){
            return get(urlPath);
        }
        OutputStream os = null;
        InputStream is = null;
        HttpURLConnection connection = null;
        StringBuffer body = getParamString(params);
        byte[] data = body.toString().getBytes();
        try {
            URL url = new URL(urlPath);
            connection = (HttpURLConnection) url.openConnection();
            connection.setRequestMethod("POST");
            //不使用缓存
            connection.setUseCaches(false);
            connection.setConnectTimeout(3000);
            //设置读取超时时间
            connection.setReadTimeout(3000);
            //设置是否从httpUrlConnection读入,默认情况下是true
            connection.setDoInput(true);
            connection.setRequestProperty("Content-Type" , "application/x-www-form-urlencoded");
            connection.setRequestProperty("Content-Length" , String.valueOf(data.length));
            os = connection.getOutputStream();
            //写入参数
            os.write(data);
            if (connection.getResponseCode() == HttpURLConnection.HTTP_OK){
                is = connection.getInputStream();
                //包装字节流为字符流
                BufferedReader reader = new BufferedReader(new InputStreamReader(is));
                StringBuilder response = new StringBuilder();
                String line;
                while ((line = reader.readLine()) != null){
                    response.append(line);

                }
                return response.toString();
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            if (os != null){
                try {
                    os.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }

            if (is != null){
                try {
                    is.close();
                    is = null;
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }

            if (connection != null){
                connection.disconnect();
                connection = null;
            }
        }
        return null;
    }
private StringBuffer getParamString(Map<String , String> params){
        StringBuffer result = new StringBuffer();
        Iterator<Map.Entry<String , String>> iterator = params.entrySet().iterator();
        while (iterator.hasNext()){
            Map.Entry<String , String> param = iterator.next();
            String key = param.getKey();
            String value = param.getValue();
            result.append(key).append("=").append(value);
            if (iterator.hasNext()){
                result.append("&");
            }
        }
        return result;
    }

Okhttp

request是okhttp中访问的请求,builder是辅助类,response即okhttp中的响应
okhttp官方文档并不建议我们创建多个okhttpclient,因此全局使用一个。如果有需要,可以使用clone方法,在进行自定义。

请求缓存
对网络资源进行缓存

      okhttpclient client = new okhttpclient();

      file sdfile = getexternalcachedir();
      int cachesize = 10*1024*10;
      client.setcache(new cache(sdcache.getabsolutefile(),cachesize);

      request resquest = new request.builder() 
       .url(url)
       .build();

     response response1 = client.newcall(request).execute();
     string body = response1.body().string();
     string cache1 = response1.cacheresponse();
     string newwork1 = resonse1.newworkresponse();

      response response2 = client.newcall(request).execute();
      string body2 = response2.body().string();
      string cache2 = response2.cacheresponse();
      string newwork2 = response.newworkresponse();

即使在有缓存的情况下我们依然需要去后台请求最新的资源,这个时候可以使用强制走网络来要求必须请求网络数据

 request = request.newbuilder().cachecontrol(cachecontrol.force_newwork).build();

可以使用force_cache强制使用缓存数据,但如果请求必须从网络获取才有数据,但又使用了force_cache策略就会返回504错误;

   request = request.newbuilder().cachecontrol(cachecontrol.force_cache).build();

取消操作

网络请求中。经常会使用到对请求的cancel操作,okhttp的也提供了这方面的接口,call的cancel操作。使用call.cancel()可以立即停止掉一个正在执行的call,如果一个线程正在写请求或者读响应,将会引发ioexecption,同时可以通过reuest.builder.tag(tag)给请求设置一个标签,并使用okhttpclient.cancel(object tag)来取消所有带有这个tag的call,但是如果该请求已经在做读写操作的时候,cancel是无法成功的,会抛出ioexecption异常

    call call = client.newcall(request);
    executor.schedule(new runnable(){
     public void run(){
     call.cancel();
     }
     },1,timeunit.seconds};
    response response = call.execte();

http post提交json数据

      public static final MediaType JSON = MediaType.parse("application/json;charset=utf-8");

       OkHttpClient client = new OkHttpClient();

          string Post(strint url , string json){

           requestbody body = requestbody.create(JSON ,     json);
           request  request = new request.builder().url(url).post(body).build();
           response response = client.newcall(request).execute();
            if(reponse.issuccessful()){
             return response.body().string();
            }
      }

okhttp通过post方式把键值对数据传送到服务器

  okhttpclient client = new okhttpclient();
  string post(string url , string json){

  requestbody  body = new formencodingbuilder()
  .add("platform" , "android")
  .add("name","bug")
  .add("subject","xxxx").builder();

  request request = new request.Builder().url (url).post(body).builder();
 response response = client.newcall(request).excute();}

synchronous get(同步get)

下载一个文件,响应体的string()方法对于小文档来说十分方便、高效。但是如果响应体太大(超过1M),应避免使用string()方法,因为它会把整个文档加载到内存中,对于超过MB的响应body,应使用流的方式处理body

    okhttpclient client = new okhttpclient();
    public void run(){
     request request = new request.builder()
      .url("http://publicobject.com/helloworld.txt")
      .builder();
     response response = client.newcall(request).excute();
      headers headers = response.headers();
      string headerName = headers.name();
      string body = response.body.string();
    }

asynchronous get(异步get)

在一个工作线程中下载文件时,当响应可读时回调callback接口是,读取响应时会阻塞当前线程,okhttp现阶段不提供异步api来接收响应体。

     okhttpclient client = new okhttpclient();
     public void run(){
         request request = new request.builder()
            .url(url)
            .builder();
        client.newcall(request).enqueue(new callback(){

         public void onresponse(call call,response response){
              headers headers = response.headers();
            for(int i=0;i<headers.size();i++){
              string name = headers.name(i);
              string value = headers.value(i);
           }
         string body = response.body().string();
         }
         });
    }

post streaming(post方式提交流)

以流的方式post提交请求体,请求体的内容有流写入产生,这个例子是流直接写入okio的bufferedsink。程序可能会使用outputstream,可以使用bufferedsink.outputstream()来获取。

    mediatype type = mediatype.parse("text/x-markdown ;     charset=utf-8");

     okhttpclient client = new okhttpclient();

     public void run(){
       requestbody body = new requestbody(){
         public mediatype contenttype(){
         return MEDIA_THPE_MARKDOWN;
         }
         public void writeto(bufferdsink sink){
         sink.writeutf8("numbers\n);
         sink.writeutf8("-----\n");
         for(int i=0;i<+997;i++){
         skin.writeutf8(string format("*%s = %s\n",i,foctor(i)))
         }
        }
         private string factor(int n ){
        for (int i=2;i<n;i++{
        int x= n/i;
        if(x*i == n)return factor(x)+"x"+i;
        }
         return integer.tostring(n);
         }
        };

      request request = new request.builder()
       .url(url)
       .post(body)
       .build();

    response response = client.newcall(request).excute();
    response responsebody = response.body().string();
     }

posting a file(post 方式提交文件)

mediatype type = mediatype.creat("text/x-markdown" , charset=utf-8);
  okhttpclient client = new okhttpclient();
   public void run(){
    file file = new file("readme.md");
    request request = new request.builder()                                                  .url(url)         .post(requestbody.create(media_type_markdown,file)
.build();

 response response= client.newcall(request).execute();
 string responsebody = response.body().string();
    }

使用formencodingbuilder来构建和html标签相同效果的请求体。键值对将使用一种html兼容的形式的URL编码来进行编码。

         okhttpclient client =new okhttpclient();
     public void run (){
         requestbody body = new formbody.builder()
            .add("search","Jurassic Park")
            .build();
         request request = new request.buider()
            .url(url)
            .post(body)
            .build();
           response response = client.newcall(request).excute();
           string responsebody = response.body();
     }

okhttp中的坑

没有帮我缓存并发送cookie给服务器

1.okhttp 3.0开始,默认不保存cookie,要自己使用cookiejar来保存cookie。

2.使用builder来构建okhttpclient才能设置cookiejar。

3.使用下面的代码可以帮你自动管理cooKie
//记录下正确姿势
OkHttpClient mHttpClient = new OkHttpClient.Builder().cookieJar(new CookieJar() {
private final HashMap

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值