Android 网络框架学习之Retrofit,androidretrofit
2016-01-18 10:34
525 查看
概述:
前文,我们比对了Volley、Retrofit、OKHttp。 抉择:AndroidHTTP请求库用Retrofit即可,有图片的加上Android-Universal-Image-Loader(或者Picasso),如果有Retrofit不能满足你的要求的话再用okhttp。一般情况下,前两个已经能很好解决大部分问题了,且用起来都比Volley简单多了。 依次学习使用Retrofit、OKHttp和GSONRetrofit: A type-safe REST client for Android
and Java Retrofit简化了从Web API下载数据,解析成普通的Java对象(POJO)。例如,要从Github 上下载用户仓库的信息,你只需要编写下面的几行:
@GET("/users/{user}/repos") List listRepos(@Path("user") String user);
okHttp: OKHttp是Android版Http客户端。非常高效,支持SPDY、连接池、GZIP和
HTTP 缓存。默认情况下,OKHttp会自动处理常见的网络问题,像二次连接、SSL的握手问题。如果你的应用程序中集成了OKHttp,Retrofit默认会使用OKHttp处理其他网络层请求。 Gson:GSON是将JSON解析成POJO的Java库。GSON也可以将POJO解析成JSON。Retrofit使用GSON解析JSON数据。
使用jsonschema2pojo来创建POJO
1、通过网站http://www.jsonschema2pojo.org/在线创建:选择源代码类型为Json,注解类型是Gson,然后点击preview. 2、通过命令行工具:jsonschema2pojo.bat-a GSON -T JSON --source jsonaddress --target java-gen
Retrofit
官网:http://square.github.io/retrofit/
1) POJO或模型实体类 : 从服务器获取的JSON数据将被填充到这种类的实例中。
2) 接口 : 我们需要创建一个接口来管理像GET,POST...等请求的URL,这是一个服务类。
3) RestAdapter类 : 这是一个REST客户端(RestClient)类,retrofit中默认用的是Gson来解析JSON数据,你也可以设置自己的JSON解析器,比如jackson
安装:
Maven方式:<dependency> <groupId>com.squareup.retrofit</groupId> <artifactId>retrofit</artifactId> <version>1.9.0</version> </dependency>
Gradle方式:
compile 'com.squareup.retrofit:retrofit:1.9.0'
使用
Retrofit将RestAPI转变为java接口:public interface GitHubService { @GET("/users/{user}/repos") List<Repo> listRepos(@Path("user") String user); }
RestAdapter创建HTTP连接并用于创建GitHubService的实现:
RestAdapter restAdapter = new RestAdapter.Builder() .setEndpoint("https://api.github.com") .build(); GitHubService service = restAdapter.create(GitHubService.class);
每次调用GitHubService中的方法都会创建一个HTTP请求到服务端:
List<Repo> repos = service.listRepos("octocat");
以上使用注解描述HTTP请求的好处:
URL parameter replacement and query parameter support
Object conversion to request body (e.g., JSON, protocol buffers)
Multipart request body and file upload
API注解
所有请求都需要一个请求方法注解并以相对URL路径作为参数。内建了5个注解:GET, POST, PUT, DELETE, and HEAD@GET("/users/list")
你也可以指定查询参数: @GET("/users/list?sort=desc")
URL操作
所有请求URL可以动态改变,通过如下形式:@GET("/group/{id}/users") List<User> groupList(@Path("id") int groupId);
其中参数用@Path注解修饰,@Path("id")对应于{id} 还可以通过这种形式添加查询:@Query
@GET("/group/{id}/users") List<User> groupList(@Path("id") int groupId, @Query("sort") String sort);
对于添加更复杂的查询可以采用map形式:
@GET("/group/{id}/users") List<User> groupList(@Path("id") int groupId, @QueryMap Map<String, String> options);
REQUEST BODY请求体
@POST("/users/new") void createUser(@Body User user, Callback<User> cb);
注意采用一个POJO作为请求体,它会被RestAdapter进行转换。同时POST方式可以传入回调。
FORM ENCODED AND MULTIPART表单域与文件上传
@FormUrlEncoded修饰表单域,每个表单域子件key-value采用@Field修饰@FormUrlEncoded @POST("/user/edit") User updateUser(@Field("first_name") String first, @Field("last_name") String last);
@Multipart修饰用于文件上传,每个Part元素用@Part修饰:
@Multipart @PUT("/user/photo") User updateUser(@Part("photo") TypedFile photo, @Part("description") TypedString description);
处理Header:
@Headers("Cache-Control: max-age=640000") @GET("/widget/list") List<Widget> widgetList();
@Headers({ "Accept: application/vnd.github.v3.full+json", "User-Agent: Retrofit-Sample-App" }) @GET("/users/{username}") User getUser(@Path("username") String username);
@GET("/user") void getUser(@Header("Authorization") String authorization, Callback<User> callback)
如果想给所有的请求添加同一个Header,那么可以采取RequestIntercepor形式:
RequestInterceptor requestInterceptor = new RequestInterceptor() { @Override public void intercept(RequestFacade request) { request.addHeader("User-Agent", "Retrofit-Sample-App"); } }; RestAdapter restAdapter = new RestAdapter.Builder() .setEndpoint("https://api.github.com") .setRequestInterceptor(requestInterceptor) .build();
同步、异步、可观察
以下方式为同步的:A method with a return type will be executed synchronously.@GET("/user/{id}/photo") Photo getUserPhoto(@Path("id") int id);
以下为异步的:Asynchronous execution requires the last parameter of the method be a Callback.
@GET("/user/{id}/photo") void getUserPhoto(@Path("id") int id, Callback<Photo> cb);
但是需要注意的是在Android中,Callback是在主线程中调用执行的。 总之,带返回值形式为同步,带Callback参数形式为异步请求。
返回观察:
@GET("/user/{id}/photo") Observable<Photo> getUserPhoto(@Path("id") int id);
Observable requests are subscribed asynchronously and observed on the same thread that executed the HTTP request. To observe on a different thread (e.g. Android's
main thread) call observeOn(Scheduler) on the returned Observable.
RESPONSE OBJECT TYPE
注意:Retrofit所有的JSON与Object转换工作由RestAdapter完成@GET("/users/list") List<User> userList(); @GET("/users/list") void userList(Callback<List<User>> cb); @GET("/users/list") Observable<List<User>> userList();
如果你想访问原始HTTP响应:
@GET("/users/list") Response userList(); @GET("/users/list") void userList(Callback<Response> cb); @GET("/users/list") Observable<Response> userList();
RestAdaper配置
JSON转换:Retrofit默认采用Gson.如果你想定制Gson转换(e.g. naming policies, date formats, custom types)可以在RestAdapter构建的时候提供一个Gson对象。
Gson gson = new GsonBuilder() .setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES) .registerTypeAdapter(Date.class, new DateTypeAdapter()) .create(); RestAdapter restAdapter = new RestAdapter.Builder() .setEndpoint("https://api.github.com") .setConverter(new GsonConverter(gson)) .build(); GitHubService service = restAdapter.create(GitHubService.class);
处理XML转换:
RestAdapter restAdapter = new RestAdapter.Builder() .setEndpoint("https://api.soundcloud.com") .setConverter(new SimpleXMLConverter()) .build(); SoundCloudService service = restAdapter.create(SoundCloudService.class);
错误处理
class MyErrorHandler implements ErrorHandler { @Override public Throwable handleError(RetrofitError cause) { Response r = cause.getResponse(); if (r != null && r.getStatus() == 401) { return new UnauthorizedException(cause); } return cause; } } RestAdapter restAdapter = new RestAdapter.Builder() .setEndpoint("https://api.github.com") .setErrorHandler(new MyErrorHandler()) .build();
日志处理:
RestAdapter restAdapter = new RestAdapter.Builder() .setLogLevel(RestAdapter.LogLevel.FULL) .setEndpoint("https://api.github.com") .build();
集成okHttp
Retrofit一旦在项目中发现okHttp,会自动集成okHttp
Proguard:
-dontwarn retrofit.** -keep class retrofit.** { *; } -keepattributes Signature -keepattributes Exceptions
参考: http://stackoverflow.com/questions/27960801/should-i-use-okhttp-with-volley-library http://stackoverflow.com/questions/16902716/comparison-of-android-networking-libraries-okhttp-retrofit-volley/ http://blog.jobbole.com/65170/ https://www.v2ex.com/t/180575 https://github.com/bboyfeiyu/android-tech-frontier/tree/master/issue-7/Retrofit%E5%BC%80%E5%8F%91%E6%8C%87%E5%8D%97 http://www.cnblogs.com/ct2011/p/3997368.html?utm_source=tuicool
相关文章推荐
- https双向认证(基于程序访问,j2ee和android上皆可用)
- linux下使用libmodbus库实现modbusTCP与modbusRTU功能
- 配置https双向认证过程实战(tomcat和浏览器交互)
- vmware下centos克隆功能对网络的设置
- vmware下centos克隆功能对网络的设置
- flex HTTPService浅析
- Android访问网络,使用HttpURLConnection还是HttpClient?
- 说说ToolBar以及仿QQ没网络提示的实现
- iOS 网络请求 时 出现 <null> 与 (null) 的 问题的处理方法
- 别说我懂社交网络: 关于社交网络分析的一头雾水
- 常用的网络驱动收包方式
- Sokcet方式请求HTTP/HTTPS的封装类HttpHelper
- centos 7 网络配置 ssd mysql nginx
- 2016年1月全国网络媒体技术联盟第七届年会的几个关键词
- tcpdump笔记
- nefu495最长k可重区间集问题【最大权不相交路径】网络流24题
- VMware中三种网络连接的区别
- Micheal Nielsen's神经网络学习之三:过拟合与规范化
- ubuntu15.10下Snort安装及配置
- 网络爬虫入门(二)模拟提交以及HttpClient修正