package com.quaie.wms.myhttpdiscuss; import android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.util.Log; import android.view.View; import android.widget.Button; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import okhttp3.Call; import okhttp3.Callback; import okhttp3.FormBody; import okhttp3.MediaType; import okhttp3.MultipartBody; import okhttp3.OkHttpClient; import okhttp3.Request; import okhttp3.RequestBody; import okhttp3.Response; public class MainActivity extends AppCompatActivity implements View.OnClickListener { private Button tongbuget; private Button yibuget; private Button tianjiaheader; private Button posejianzhidui; private Button poseString; private Button posefile; private Button yibuxiazai; private Button Multipart; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); initView(); } private void initView() { tongbuget = (Button) findViewById(R.id.tongbuget); tongbuget.setOnClickListener(this); yibuget = (Button) findViewById(R.id.yibuget); yibuget.setOnClickListener(this); tianjiaheader = (Button) findViewById(R.id.tianjiaheader); tianjiaheader.setOnClickListener(this); posejianzhidui = (Button) findViewById(R.id.posejianzhidui); posejianzhidui.setOnClickListener(this); posefile = (Button) findViewById(R.id.posefile); posefile.setOnClickListener(this); yibuxiazai = (Button) findViewById(R.id.yibuxiazai); yibuxiazai.setOnClickListener(this); poseString = (Button) findViewById(R.id.poseString); poseString.setOnClickListener(this); Multipart = (Button) findViewById(R.id.Multipart); Multipart.setOnClickListener(this); } @Override public void onClick(View v) { switch (v.getId()) { case R.id.tongbuget: tongbuGET(); break; case R.id.yibuget: yibuGET(); break; case R.id.tianjiaheader: tianjiaHeader(); break; case R.id.posejianzhidui: jianzhiduiPOSE(); break; case R.id.poseString: StringPOSE(); break; case R.id.posefile: filePOSE(); break; case R.id.yibuxiazai: yibuxiazaiFile(); break; case R.id.Multipart: sendMultipart(); break; } } /** * 同步GET * 同步GET的意思是一直等待http请求, 直到返回了响应. 在这之间会阻塞进程, * 所以通过get不能在Android的主线程中执行, 否则会报错. *
* Request是okhttp3 的请求对象,Response是okhttp3中的响应。通过response.isSuccessful()判断请求是否成功。 */ private void tongbuGET() { new Thread(new Runnable() { @Override public void run() { try { String url = "https://www.baidu.com"; OkHttpClient client = new OkHttpClient(); Request request = new Request.Builder().url(url).build(); //同步GET需要用 .execute() Response response = client.newCall(request).execute(); if (response.isSuccessful()) { Log.e("11111", "response = " + response.body().string()); } else { Log.e("11111", "okHttp is request error"); } } catch (IOException e) { e.printStackTrace(); } } }).start(); } /** * 异步GET * 有时候需要下载一份文件(比如网络图片),如果文件比较大,整个下载会比较耗时,通常我们会将耗时任务放到工作线程中 * 而使用okhttp3异步方法,不需要我们开启工作线程执行网络请求,返回的结果也在工作线程中 */ private void yibuGET() { Log.e("11111", "main thread id is " + Thread.currentThread().getId()); String url = "https://www.baidu.com"; OkHttpClient client = new OkHttpClient(); Request request = new Request.Builder().url(url).build(); /* //另一种设置请求的方式 Request.Builder requestBuilder = new Request.Builder().url("http://www.baidu.com"); //可以省略,默认是GET请求 requestBuilder.method("GET",null); Request request = requestBuilder.build(); */ //异步GET需要用 .enqueue client.newCall(request).enqueue(new Callback() { @Override public void onFailure(Call call, IOException e) { Log.e("11111", "Failure"); } @Override public void onResponse(Call call, Response response) throws IOException { // 注:该回调是子线程,非主线程 Log.e("11111", "callback thread id is " + Thread.currentThread().getId()); Log.e("11111", "response = " + response.body().string()); if (null != response.cacheResponse()) { String str = response.cacheResponse().toString(); Log.i("11111", "cache---" + str); } else { response.body().string(); String str = response.networkResponse().toString(); Log.i("11111", "network---" + str); } runOnUiThread(new Runnable() { @Override public void run() { Log.e("11111", "异步GET请求成功"); } }); } }); } /** * okhttp3添加请求头, * 需要在Request.Builder()使用.header(String key,String value)或者.addHeader(String key,String value); *
* 使用.header(String key,String value),如果key已经存在,将会移除该key对应的value,然后将新value添加进来,即替换掉原来的value; *
* 使用.addHeader(String key,String value),即使当前的可以已经存在值了,只会添加新value的值,并不会移除/替换原来的值。 */ private void tianjiaHeader() { new Thread(new Runnable() { @Override public void run() { try { OkHttpClient client = new OkHttpClient(); Request request = new Request.Builder() .url("https://api.github.com/repos/square/okhttp/issues") .header("User-Agent", "OkHttp Headers.java") .addHeader("Accept", "application/json; q=0.5") .addHeader("Accept", "application/vnd.github.v3+json") .build(); Response response = client.newCall(request).execute(); if (!response.isSuccessful()) throw new IOException("Unexpected code " + response); Log.e("11111", "Server: " + response.header("Server")); Log.e("11111", "Date: " + response.header("Date")); Log.e("11111", "Vary: " + response.headers("Vary")); if (response.isSuccessful()) { Log.e("11111", "response = " + response.body().string()); } else { Log.e("11111", "okHttp is request error"); } } catch (IOException e) { e.printStackTrace(); } } }).start(); } /** * POSE 文件 * 异步请求 * 同步用 okHttpClient.newCall(request).execute(); */ private void filePOSE() { //首先定义上传文件类型 final MediaType MEDIA_TYPE_MARKDOWN = MediaType.parse("text/x-markdown; charset=utf-8"); //将sdcard根目录的11111.txt文件上传到服务器上 OkHttpClient mOkHttpClient = new OkHttpClient(); File file = new File("/sdcard/test.txt"); Request request = new Request.Builder() .url("https://api.github.com/markdown/raw") .post(RequestBody.create(MEDIA_TYPE_MARKDOWN, file)) .build(); mOkHttpClient.newCall(request).enqueue(new Callback() { @Override public void onFailure(Call call, IOException e) { Log.e("11111", "onFailure"); } @Override public void onResponse(Call call, Response response) throws IOException { Log.i("11111", "response = " + response.body().string()); } }); } /** * POSE String串 * 可以使用Post方法发送一串字符串,但不建议发送超过1M的文本信息 */ private void StringPOSE() { final MediaType MEDIA_TYPE_MARKDOWN = MediaType.parse("text/x-markdown; charset=utf-8"); new Thread() { @Override public void run() { super.run(); try { OkHttpClient client = new OkHttpClient(); String postBody = "" + "Releases\n" + "--------\n" + "\n" + " * _1.0_ May 6, 2016\n" + " * _1.1_ June 15, 2016\n" + " * _1.2_ August 11, 2016\n"; Request request = new Request.Builder() .url("https://api.github.com/markdown/raw") .post(RequestBody.create(MEDIA_TYPE_MARKDOWN, postBody)) .build(); Response response = client.newCall(request).execute(); if (!response.isSuccessful()) throw new IOException("Unexpected code " + response); Log.e("11111", "response = " + response.body().string()); } catch (Exception e) { Log.e("11111", "Exception = " + e.toString().trim()); } } }.start(); } /** * POSE 键值对(JSON) * okhttp3使用FormBody.Builder创建请求的参数键值对 */ private void jianzhiduiPOSE() { new Thread(new Runnable() { @Override public void run() { // 请求完整url:http://api.k780.com:88/?app=weather.future&weaid=1&&appkey=10003&sign=b59bc3ef6191eb9f747dd4e83c99f2a4&format=json String url = "http://api.k780.com:88/"; OkHttpClient okHttpClient = new OkHttpClient(); String json = "{'app':'weather.future','weaid':'1','appkey':'10003'," + "'sign':'b59bc3ef6191eb9f747dd4e83c99f2a4','format':'json'}"; RequestBody formBody = new FormBody.Builder() .add("app", "weather.future") .add("weaid", "1") .add("appkey", "10003") .add("sign", "b59bc3ef6191eb9f747dd4e83c99f2a4") .add("format", "json") .build(); Request request = new Request.Builder() .url(url) .post(formBody) .build(); //同步pose //okhttp3.Response response = okHttpClient.newCall(request).execute(); //Log.e("11111", "response = " + response.body().string()); //异步pose Call call = okHttpClient.newCall(request); call.enqueue(new Callback() { @Override public void onFailure(Call call, IOException e) { Log.e("11111", "onFailure"); } @Override public void onResponse(Call call, Response response) throws IOException { String str = response.body().string(); Log.e("11111", "response = " + str); runOnUiThread(new Runnable() { @Override public void run() { Log.e("11111", "异步POSE键值对请求成功"); } }); } }); } }).start(); } /** * 异步下载文件 */ private void yibuxiazaiFile() { OkHttpClient mOkHttpClient = new OkHttpClient(); //指定下载文件在哪里 String url = "https://img-my.csdn.net/uploads/201603/26/1458988468_5804.jpg"; Request request = new Request.Builder().url(url).build(); mOkHttpClient.newCall(request).enqueue(new Callback() { @Override public void onFailure(Call call, IOException e) { Log.e("11111", "onFailure"); } @Override public void onResponse(Call call, Response response) { //把得到Response后将流写进指定的图片文件 InputStream inputStream = response.body().byteStream(); FileOutputStream fileOutputStream = null; try { //指定的图片文件并写入 fileOutputStream = new FileOutputStream(new File("/sdcard/11111.jpg")); byte[] buffer = new byte[2048]; int len = 0; while ((len = inputStream.read(buffer)) != -1) { fileOutputStream.write(buffer, 0, len); } fileOutputStream.flush(); } catch (IOException e) { Log.e("11111", "IOException"); e.printStackTrace(); } Log.e("11111", "文件下载成功"); } }); } /** * 上传文件同时还需要传其他类型的字段 */ private void sendMultipart() { final MediaType MEDIA_TYPE_PNG = MediaType.parse("image/png"); OkHttpClient mOkHttpClient = new OkHttpClient(); RequestBody requestBody = new MultipartBody.Builder() .setType(MultipartBody.FORM) //设置字段 .addFormDataPart("title", "11111") .addFormDataPart("image", "11111.jpg", RequestBody.create(MEDIA_TYPE_PNG, new File("/sdcard/11111.jpg"))) .build(); Request request = new Request.Builder() .header("Authorization", "Client-ID " + "...") .url("https://api.imgur.com/3/image") .post(requestBody) .build(); mOkHttpClient.newCall(request).enqueue(new Callback() { @Override public void onFailure(Call call, IOException e) { Log.e("11111", "onFailure"); } @Override public void onResponse(Call call, Response response) throws IOException { Log.e("11111", "response = " + response.body().string()); } }); } }
Okhttp3的固定步骤是:
一:创建请求队列:
方法一:
设置url
String url = "https://www.baidu.com";
设置OkHttpClient对象
OkHttpClient client = new OkHttpClient();
创建一个request
Request request = new Request.Builder().url(url).build();
方法二:
创建一个Request.Builder对象,指定url
Request.Builder requestBuilder = new Request.Builder().url("http://www.baidu.com");
设置请求方式默认是GET请求
requestBuilder.method("GET",null);
创建一个request
Request request = requestBuilder.build();
二:发送请求
同步请求用:Response response = client.newCall(request).execute();
异步请求用:
Call call = okHttpClient.newCall(request);
call.enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
Log.e("11111", "onFailure");
}
@Override
public void onResponse(Call call, Response response) throws IOException {
String str = response.body().string();
Log.e("11111", "response = " + str);
runOnUiThread(new Runnable() {
@Override
public void run() {
Log.e("11111", "异步POSE键值对请求成功");
}
});
}
});
三:与文件有关要指定文件类型
MediaType MEDIA_TYPE_PNG = MediaType.parse("image/png");