OkHttp 简介

An HTTP & HTTP/2 client for Android and Java applications.

其相关网址:
1.okhttp github网址
https://github.com/square/okhttp 2.okhttp官方网址
http://square.github.io/okhttp/

使用时需要在build.gradle添加库的依赖

dependencies {
implementation("com.squareup.okhttp3:okhttp:3.14.1")
 implementation("com.squareup.okio:okio:2.2.2")
 }

在AndroidManifest.xml中添加网络权限:

<uses-permission android:name="android.permission.INTERNET"/>

官方给出的二个核心使用代码:
(1) GET A URL
This program downloads a URL and prints its contents as a string.

public class GetExample {
  OkHttpClient client = new OkHttpClient();

  String run(String url) throws IOException {
    Request request = new Request.Builder()
        .url(url)
        .build();

    try (Response response = client.newCall(request).execute()) {
      return response.body().string();
    }
  }

  public static void main(String[] args) throws IOException {
    GetExample example = new GetExample();
    String response = example.run("https://raw.github.com/square/okhttp/master/README.md");
    System.out.println(response);
  }
}

(2) POST TO A SERVER
This program posts data to a service.

public class PostExample {
  public static final MediaType JSON = MediaType.get("application/json; charset=utf-8");

  OkHttpClient client = new OkHttpClient();

  String post(String url, String json) throws IOException {
    RequestBody body = RequestBody.create(JSON, json);
    Request request = new Request.Builder()
        .url(url)
        .post(body)
        .build();
    try (Response response = client.newCall(request).execute()) {
      return response.body().string();
    }
  }

  String bowlingJson(String player1, String player2) {
    return "{'winCondition':'HIGH_SCORE',"
        + "'name':'Bowling',"
        + "'round':4,"
        + "'lastSaved':1367702411696,"
        + "'dateStarted':1367702378785,"
        + "'players':["
        + "{'name':'" + player1 + "','history':[10,8,6,7,8],'color':-13388315,'total':39},"
        + "{'name':'" + player2 + "','history':[6,10,5,10,10],'color':-48060,'total':41}"
        + "]}";
  }

  public static void main(String[] args) throws IOException {
    PostExample example = new PostExample();
    String json = example.bowlingJson("Jesse", "Jake");
    String response = example.post("http://www.roundsapp.com/post", json);
    System.out.println(response);
  }
}

Android Demo

此Demo主要是实现下面这三个功能:
1.使用get方法, 下载一个图片并显示在Image控件中:
2.使用post方法,调用FormBody传递键值对参数
3.使用post方法,调用MediaType传递JSON格式的数据

布局文件activity_main.xml
主要是有二个button,一个显示下载的图片的ImageView.

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <ImageView
        android:id="@+id/imageView"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        android:background="@mipmap/ic_launcher"/>

    <Button
        android:id="@+id/buttonGetImage"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="下载图片--Okhttp"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toBottomOf="@id/imageView"
        />

    <Button
        android:id="@+id/buttonPostDemo"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Post--Okhttp"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toBottomOf="@id/buttonGetImage"
        />

</android.support.constraint.ConstraintLayout>

具体实现逻辑:

public class MainActivity extends AppCompatActivity {

    private static final String TAG = "OKHTTP_DEMO";

    private ImageView imageView;
    private Button buttonGetImage;
    private Button buttonPostDemo;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        init();
    }

    private void init() {
        imageView = (ImageView) findViewById(R.id.imageView);

        buttonGetImage = (Button) findViewById(R.id.buttonGetImage);
        buttonGetImage.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                getImage();
            }
        });

        buttonPostDemo = (Button) findViewById(R.id.buttonPostDemo);
        buttonPostDemo.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                postDemo();
            }
        });

    }

    private void postDemo() {
        postDataWithParame();
        postDataWithJSON();
    }

    private void postDataWithJSON() {
        OkHttpClient client = new OkHttpClient();
        MediaType JSON = MediaType.parse("application/json; charset=utf-8");
        String valueJSON = "{username:admin;password:adminpassword}";
        RequestBody body = RequestBody.create(JSON, valueJSON);
        Request request = new Request.Builder()
                .url("http://www.baidu.com")
                .post(body)
                .build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                Log.i(TAG,"postDataWithJSON--onFailure");
            }

            @Override
            public void onResponse(Call call, Response response) throws IOException {
                Log.i(TAG,"postDataWithJSON--onResponse--response.toString():"+response.toString());
            }
        });
    }

    private void postDataWithParame() {
        OkHttpClient client = new OkHttpClient();
        FormBody.Builder formBody = new FormBody.Builder();
        formBody.add("username","hexiaoming");
        Request request = new Request.Builder()
                .url("http://www.baidu.com")
                .post(formBody.build())
                .build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                Log.i(TAG,"postDataWithParame--onFailure");
            }

            @Override
            public void onResponse(Call call, Response response) throws IOException {
                Log.i(TAG,"postDataWithParame--onResponse--response.toString():"+response.toString());
            }
        });
    }

    public void getImage() {
        OkHttpClient client = new OkHttpClient();
        final Request request = new Request
                .Builder()
                .get()
                .url("")
                .build();
        Call call = client.newCall(request);
        call.enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                Log.i(TAG,"下载图片失败");
            }

            @Override
            public void onResponse(Call call, Response response) throws IOException {
                Log.i(TAG,"response.code():"+response.code());
                Log.i(TAG,"response.toString():"+response.toString());
                InputStream inputStream = response.body().byteStream();
                //将图片显示到ImageView中
                final Bitmap bitmap = BitmapFactory.decodeStream(inputStream);
                runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        imageView.setImageBitmap(bitmap);
                    }
                });
            }
        });
    }

}

显示如图:

android开发笔记之OkHttp_android

打印日志:

05-11 17:44:06.901 13875-13944/com.readygo.okhttpdemo I/OKHTTP_DEMO: response.code():200 response.toString():Response{protocol=h2, code=200, message=,url=}
05-11 17:44:15.085 13875-14130/com.readygo.okhttpdemo I/OKHTTP_DEMO: postDataWithParame--onResponse--response.toString():Response{protocol=http/1.1, code=302, message=Found, url=http://www.baidu.com/}
05-11 17:44:15.110 13875-14132/com.readygo.okhttpdemo I/OKHTTP_DEMO: postDataWithJSON--onResponse--response.toString():Response{protocol=http/1.1, code=302, message=Found, url=http://www.baidu.com/}

问题处理

我编译时,as报了一个错误:

Process: com.readygo.okhttpdemo, PID: 31073
    java.lang.BootstrapMethodError: Exception from call site #5 bootstrap method

网上查找说:
踩坑日记 :okhttp3 使用报错 java.lang.BootstrapMethodError: Exception from call site #3 bootstrap method

所以,按上面所说在build.gradle添加:

compileOptions{
        sourceCompatibility JavaVersion.VERSION_1_8
        targetCompatibility JavaVersion.VERSION_1_8
    }

如下:

android {
    compileSdkVersion 28
    defaultConfig {
        applicationId "com.readygo.okhttpdemo"
        minSdkVersion 27
        targetSdkVersion 28
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }

    compileOptions{
        sourceCompatibility JavaVersion.VERSION_1_8
        targetCompatibility JavaVersion.VERSION_1_8
    }

}

参考资料

1.okio github
https://github.com/square/okio 2.Android OKHttp使用详解
https://www.jianshu.com/p/2663ce3da0db 3.Android OkHttp3简介和使用详解
4.Android OkHttp的基本用法
https://www.jianshu.com/p/c478d7a20d03 5.OkHttpUtils 帮助类
https://github.com/guozhengXia/OkHttpUtils