Retrofit简介
Retrofit是基于OkHttp封装的一个网络请求框架,和OKHttp同出于Square公司,Retrofit感觉比较简单,看源码也就30来个文件,而且大部分都是注解。可以看一下它的目录结构如下:
引入最新版Retrofit
引入Retrofit很简单,只要加上下面这句话
compile ‘com.squareup.retrofit2:retrofit:2.3.0’
服务器简单接口
既然是网络请求框架,就离不开网络层的接口,我用java写了个简单的Servlet测试以下数据是否成功返回
先定义一个简单的User类用来返回
package com.ph.servlet;
/**
* Created by panhao on 17-6-15.
*/
public class User {
private String userName;
private int age;
public User() {
}
public User(String userName, int age) {
this.userName = userName;
this.age = age;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
然后在Servlet接口中构造返回User对象的json串
package com.ph.servlet;
import com.google.gson.Gson;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/**
* Created by panhao on 17-6-5.
*/
@WebServlet("/RetrofitServlet")
public class RetrofitServlet extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
response.setContentType("text/html;charset=utf-8");
System.out.println("有访问");
User user = new User("张三", 21);
Gson gson = new Gson();
String json = gson.toJson(user);
response.getWriter().write(json);
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doPost(request, response);
}
}
打开浏览器测试成功拿到数据:
那么准备工作就做好了,下面只要看android 断能否成功拿到数据了。
Retrofit 对应请求的接口定义
package com.example.panhao.retrofittest;
import retrofit2.Call;
import retrofit2.http.POST;
/**
* Created by panhao on 17-6-15.
*/
public interface Api {
@POST("User/RetrofitServlet")
Call<User> getUser();
}
结果的获取
Retrofit的构建方式如下,通过建造者模式来配置url等参数
然后在点击按钮的时候,调用api的操作并且请求网络接受返回结果
package com.example.panhao.retrofittest;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.view.View;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import retrofit2.Retrofit;
import retrofit2.converter.gson.GsonConverterFactory;
public class MainActivity extends AppCompatActivity {
public static final String TAG = "PH";
private Api api;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Retrofit retrofit = new Retrofit.Builder()
.baseUrl("http://192.168.1.104:8080/")
.addConverterFactory(GsonConverterFactory.create())
.build();
api = retrofit.create(Api.class);
}
public void onClick(View view) {
Call<User> user = api.getUser();
user.enqueue(new Callback<User>() {
@Override
public void onResponse(Call<User> call, Response<User> response) {
User body = response.body();
}
@Override
public void onFailure(Call<User> call, Throwable t) {
Log.i(TAG, "onFailure: ");
}
});
}
}
这里注解的构建并不是我们以为的反射,而是通过动态代理的方式来实现的,我们可以点金去看到内部的实现:
可以看到,InvocationHandler这个类和内部的invoke()方法,就是JavaAPI提供的动态代理类。当然在使用的时候,目前是无关紧要的,但是我们学习框架还是不要简简单单的只想着使用,理解其原理能够让我们学习框架搭建者构建框架的方法和思路,这很值得我们借鉴和学习。
执行程序
一开始直接执行的时候报错了,因为我们忘了加上转换器,Retrofit默认直接只能转换ResponseBody类,可是既然提供了泛型,肯定会让我们使用自己要转换的bean,看官网文档告诉我们:
官网的意思是:Retrofit默认情况下只会泛序列化成Responsbody类,如果需要我们自己定义的,要加上json转换的转换器,不然它也不知道用哪个框架帮你来解析。
所以我们在gradle文件加上这句话
compile ‘com.squareup.retrofit2:converter-gson:2.0.2’
在Retrofit构建的时候声明转换器
Retrofit retrofit = new Retrofit.Builder()
.baseUrl("http://192.168.1.104:8080/")
.addConverterFactory(GsonConverterFactory.create())
.build();
这样,我们debug跑起来观察结果:可以在debug模式下看到,debug进入onResponse,并且成功获取User对象,和服务器发给我们的完全一致
以上就是Retrofit通过POST方式简单访问网络的案例了,感觉比OkHttp还是简单了不少的。