OKHttp是一款高效的HTTP客户端,支持连接同一地址的链接共享同一个socket,通过连接池来减小响应延迟,还有透明的GZIP压缩,请求缓存等优势,其核心主要有路由、连接协议、拦截器、代理、安全性认证、连接池以及网络适配,拦截器主要是指添加,移除或者转换请求或者回应的头部信息。
这个库也是square开源的一个网络请求库(okhttp内部依赖okio),现在已被Google使用在Android源码上。
官网地址:http://square.github.io/okhttp/
Github Wiki:https://github.com/square/okhttp/wiki
Wiki 翻译:http://blog.csdn.net/jackingzheng/article/details/51778793OKHttp的功能:
- 联网请求文本数据
- 大文件下载
- 大文件上传
- 请求图片
compile 'com.squareup.okhttp3:okhttp:3.7.0'
添加网络权限;
使用http://square.github.io/okhttp/中示例get方法,该方法请求url地址只能在子线程中运行;
/**
* get请求,要求在子线程运行
* @param url
* @return
* @throws IOException
*/
private String get(String url) throws IOException {
Request request = new Request.Builder()
.url(url)
.build();
Response response = client.newCall(request).execute();
return response.body().string();
}
开辟子线程get方式请求数据;
case R.id.button:
new Thread(){
@Override
public void run() {
super.run();
try {
String result = get("http://gank.io/api/data/Android/2/1");
Message msg = Message.obtain();
msg.what = GET;
msg.obj = result;
mHandler.sendMessage(msg);
} catch (IOException e) {
e.printStackTrace();
}
}
}.start();
break;
通过handler更新ui,显示请求结果。
case GET:
mTextView2.setText((String) msg.obj);
break;
官网示例post方法,也需要在子线程中运行;
/**
* post请求
* @param url
* @param json 上传时需要json
* @return
* @throws IOException
*/
private String post(String url, String json) throws IOException {
RequestBody body = RequestBody.create(JSON, json);
Request request = new Request.Builder()
.url(url)
.post(body)
.build();
Response response = client.newCall(request).execute();
return response.body().string();
}
开辟子线程psot请求数据;
new Thread(){
@Override
public void run() {
super.run();
try {
String result = post("http://api.m.mtime.cn/PageSubArea/TrailerList.api", null);
Message msg = Message.obtain();
msg.what = POST;
msg.obj = result;
mHandler.sendMessage(msg);
} catch (IOException e) {
e.printStackTrace();
}
}
}.start();
我们使用原生的OKHttp时,需要自己去开辟子线程请求网络数据,然后通过Handler去更新UI,很麻烦,需要我们想法设法可以再次封装,方便我们的使用。
使用OkhttpUtils进行get请求;
/**
* 使用OkhttpUtils进行get请求
* @param url url地址
* @param id 请求ID号
*/
private void getByOkhttpUtils(String url, int id) {
OkHttpUtils.get().url(url).id(id).build().execute(new StringCallback() {
@Override
public void onError(Call call, Exception e, int id) {
e.printStackTrace();
mTextView2.setText(e.getMessage());
}
@Override
public void onResponse(String response, int id) {
mTextView2.setText(response);
switch (id){
case 100:
Toast.makeText(getApplicationContext(), "100请求成功", Toast.LENGTH_SHORT).show();
break;
}
}
});
}
使用OkhttpUtils进行post请求;
/**
* 使用OkhttpUtils进行post请求
* @param url
* @param id
*/
private void postByOkhttpUtils(String url, int id) {
OkHttpUtils.post().url(url).id(id).build().execute(mStringCallback);
}
........
//封装回调
private StringCallback mStringCallback = new StringCallback() {
@Override
public void onError(Call call, Exception e, int id) {
e.printStackTrace();
mTextView2.setText(e.getMessage());
}
@Override
public void onResponse(String response, int id) {
mTextView2.setText(response);
switch (id) {
case 100:
Toast.makeText(getApplicationContext(), "100get请求成功", Toast.LENGTH_SHORT).show();
break;
case 101:
Toast.makeText(getApplicationContext(), "101post请求成功", Toast.LENGTH_SHORT).show();
break;
}
}
};
下载文件,添加WRITE_EXTERNAL_STORAGE权限,设置回调并进行下载;
//参数包含保存路径和保存文件名
private FileCallBack mFileCallBack = new FileCallBack(Environment.getExternalStorageDirectory().getAbsolutePath(), "test.mp4") {
@Override
public void onError(Call call, Exception e, int id) {
e.printStackTrace();
mTextView2.setText(e.getMessage());
}
@Override
public void inProgress(float progress, long total, int id) {
super.inProgress(progress, total, id);
mProgressBar.setProgress((int) (100 * progress));
mTextView2.setText("下载进度:" + (int) (100 * progress) + "/%");
}
@Override
public void onResponse(File response, int id) {
}
};
......
/**
* 使用OkhttpUtils进行下载大文件
* @param url
*/
private void downloadFileByOkhttpUtils(String url){
OkHttpUtils.get().url(url).build().execute(mFileCallBack);
}
文件上传;
文件服务器搭建:下载链接,我的测试链接: http://192.168.1.102/FileUpload/index.jsp;
/**
* 单文件或多文件上传
* @param url url地址
* @param id 请求id
* @param username 用户名参数
* @param files 文件集合
*/
private void uploadFilesByOkhttpUtils(String url, int id, String username, List files) {
for (File file : files) {
if (!file.exists()) {
Toast.makeText(getApplicationContext(), "文件" + file.getName() + "不存在", Toast.LENGTH_SHORT).show();
return;
}
}
Map params = new HashMap<>();
params.put("username", username);
PostFormBuilder builder = OkHttpUtils.post();
for (File file : files) {
builder = builder.addFile(username, "server" + file.getName(), file);
}
builder.url(url).id(id).params(params).build().execute(mStringCallback);
}
......
@OnClick(R.id.button3)
public void onViewClicked() {
List files = new ArrayList<>();
files.add(new File(Environment.getExternalStorageDirectory().getAbsolutePath(), "QQ_8.9.2.20760_setup.exe"));
files.add(new File(Environment.getExternalStorageDirectory().getAbsolutePath(), "test.mp4"));
uploadFilesByOkhttpUtils("http://192.168.1.102/FileUpload/FileUploadServlet", 102, "Mr.sorrow", files);
}
请求图片;
private BitmapCallback mBitmapCallback = new BitmapCallback() {
@Override
public void onError(Call call, Exception e, int id) {
e.printStackTrace();
mTextView2.setText(e.getMessage());
}
@Override
public void onResponse(Bitmap response, int id) {
mImageView.setImageBitmap(response);
}
};
.......
/**
* 请求单张图片
* @param url
* @param id
*/
private void getPicByOkhttpUtils(String url, int id) {
OkHttpUtils
.get()
.url(url)
.tag(this)
.id(id)
.build()
.connTimeOut(20000) //设置连接超时、读取超时、写入超时
.readTimeOut(20000)
.writeTimeOut(20000)
.execute(mBitmapCallback);
}
Activity:
public class ThirdActivity extends AppCompatActivity {
private List picsUrl;
@BindView(R.id.listview)
ListView mListview;
@BindView(R.id.progressBar)
ProgressBar mProgressBar;
@BindView(R.id.textView)
TextView mTextView;
private StringCallback mStringCallback = new StringCallback() {
@Override
public void onError(Call call, Exception e, int id) {
e.printStackTrace();
mTextView.setVisibility(View.VISIBLE);
mProgressBar.setVisibility(View.GONE);
}
@Override
public void onResponse(String response, int id) {
mTextView.setVisibility(View.GONE);
switch (id) {
case 100:
Toast.makeText(getApplicationContext(), "请求成功", Toast.LENGTH_SHORT).show();
break;
}
if (response != null) {
Meizi meizi1 = processData(response);
if (meizi1 != null) {
List beanList = meizi1.getResults();
if (!beanList.isEmpty()) {
for (Meizi.ResultsBean resultsBean : beanList) {
picsUrl.add(resultsBean.getUrl());
Log.i("xxxxx", resultsBean.getUrl());
}
}
}
}
mListview.setAdapter(new MyAdapter(picsUrl, ThirdActivity.this));
mProgressBar.setVisibility(View.GONE);
}
@Override
public void inProgress(float progress, long total, int id) {
super.inProgress(progress, total, id);
}
};
/**
* 解析json数据
*
* @param json
*/
private Meizi processData(String json) {
Gson gson = new Gson();
return gson.fromJson(json, Meizi.class);
}
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_third);
ButterKnife.bind(this);
picsUrl = new ArrayList<>();
getDataByOkhttpUtils("http://gank.io/api/data/%E7%A6%8F%E5%88%A9/20/1", 100);
}
/**
* get请求json数据
*
* @param url
* @param id
*/
private void getDataByOkhttpUtils(String url, int id) {
OkHttpUtils.get().url(url).id(id).build().execute(mStringCallback);
}
}
Adapter:
public class MyAdapter extends BaseAdapter {
private List data;
private Context mContext;
public MyAdapter(List data, Context context) {
this.data = data;
mContext = context;
}
@Override
public int getCount() {
return data.size();
}
@Override
public String getItem(int position) {
return data.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder = null;
if (convertView == null) {
convertView = View.inflate(mContext, R.layout.items, null);
holder = new ViewHolder(convertView);
convertView.setTag(holder);
} else {
holder = (ViewHolder) convertView.getTag();
}
holder.mTvName.setText(getItem(position));
holder.mTvDesc.setText(getItem(position));
final ViewHolder finalHolder = holder;
OkHttpUtils
.get()
.url(getItem(position))
.tag(this)
.build()
.connTimeOut(20000) //设置连接超时、读取超时、写入超时
.readTimeOut(20000)
.writeTimeOut(20000)
.execute(new BitmapCallback() {
@Override
public void onError(Call call, Exception e, int id) {
}
@Override
public void onResponse(Bitmap response, int id) {
finalHolder.mIvIcon.setImageBitmap(response);
}
});
return convertView;
}
static class ViewHolder {
@BindView(R.id.iv_icon)
ImageView mIvIcon;
@BindView(R.id.tv_name)
TextView mTvName;
@BindView(R.id.tv_desc)
TextView mTvDesc;
ViewHolder(View view) {
ButterKnife.bind(this, view);
}
}
}
GsonFormat生成的实体Bean:
public class Meizi {
private boolean error;
private List results;
public boolean isError() {
return error;
}
public void setError(boolean error) {
this.error = error;
}
public List getResults() {
return results;
}
public void setResults(List results) {
this.results = results;
}
public static class ResultsBean {
private String _id;
private String createdAt;
private String desc;
private String publishedAt;
private String source;
private String type;
private String url;
private boolean used;
private String who;
public String get_id() {
return _id;
}
public void set_id(String _id) {
this._id = _id;
}
public String getCreatedAt() {
return createdAt;
}
public void setCreatedAt(String createdAt) {
this.createdAt = createdAt;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
public String getPublishedAt() {
return publishedAt;
}
public void setPublishedAt(String publishedAt) {
this.publishedAt = publishedAt;
}
public String getSource() {
return source;
}
public void setSource(String source) {
this.source = source;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
public boolean isUsed() {
return used;
}
public void setUsed(boolean used) {
this.used = used;
}
public String getWho() {
return who;
}
public void setWho(String who) {
this.who = who;
}
}
}
演示视频
下载地址