1. 程式人生 > >retrofit 2.3.0 接入和使用

retrofit 2.3.0 接入和使用

前言

開門見山,本文記錄瞭如何接入並使用square出品的retrofit網路框架。

一、準備工作

  • 新增retrofit 的依賴(或直接使用jar包)

這邊並不能直接連線網路,所以直接下載jar包並使用了

  • 新增okio依賴或引用jar包

新增jar包之後,還要新增okio的jar包,不然會報錯

java.lang.NoClassFoundError:okio.Buffer

這裡寫圖片描述

  • 新增converter-gson的依賴或引用jar包

由於程式碼中要解析資料到實體類裡,retrofit是預設用的Gson來轉換的,而且官方也給了一個轉換的包,使用也很簡單,直接用GsonConverterFactory.create()就能直接轉換:

         Retrofit retrofit = new Retrofit.Builder().baseUrl(THost.Host)
            .addConverterFactory(GsonConverterFactory.create())
            .build();
  • 新增okhttp的依賴或引用jar包

這裡直接下載的最新版的okhttp的jar包,版本為okhttp-3.8.0,如果不加,則會報錯:

這裡寫圖片描述

  • 新增Gson的依賴

這裡有個坑,就是gson版本不能太低,這邊原本使用的是gson 2.2.4,結果請求是正常的,但是解析會出錯,無法得到想要的資料,在onFailure方法裡打的log如下:

這裡寫圖片描述

請求是正常的,抓包顯示返回正常,但是方法裡跑不到onResponse,而是進了onFailure,log顯示java.lang.NoSuchMethodError: com.google.gson.Gson.newJsonReader

解決方法是用最新的gson包就行了。這邊使用的是gson 2.8.0

總結下,新增的依賴就是這些了:

這裡寫圖片描述

二、開始使用

以一個簡單的登入為例,需求如下:

請求地址為http://app.test.com/testapp.php

請求方式為POST,引數有username和pwd,以及一個action,通過表單傳送到伺服器

我們先定義一個介面類,裡面有一個login方法

public interface TestApiService {

    @FormUrlEncoded
    @POST("http://app.test.com/testapp.php")
    Call<TPHPResult<TLogin>> login ( @Field("username") String username,
                                     @Field("pwd") String pwd,
                                     @Field("action") String aciton ) ;
} 

這裡用註解表明了login方法的引數形式

  • @Field註解代表引數為表單格式,key為username,value在呼叫的時候傳入。
  • @POST註解裡面放的是請求的url地址。

由於引數以表單形式提交,所以方法上還要加@FormUrlEncoded註解

然後再在MainActivity裡使用這個方法來實現登入:

public class MainActivity extends AppCompatActivity {

    private String token ;
    private int uid ;

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

        Retrofit retrofit = new Retrofit.Builder().baseUrl("http://app.test.com/testapp.php/")
                .addConverterFactory(GsonConverterFactory.create())
                .build();

        TestApiService service = retrofit.create(TestApiService.class);

        Call<TPHPResult<TLogin>> loginCall = service.login("Naruto", "123456","login");

        //enqueue是非同步的,所以可以直接在主執行緒請求網路
        loginCall.enqueue(new Callback<TPHPResult<TLogin>>() {
                @Override
                public void onResponse(Call<TPHPResult<TLogin>> call, Response<TPHPResult<TLogin>> response) {

                    if (response.code() == 200) {
                        TLogin loginInfo = response.body().getData() ;

                        token = loginInfo.getToken() ;
                        uid = loginInfo.getUid() ;

                        getUserInfo();
                    }
                }

                @Override
                public void onFailure(Call<TPHPResult<TLogin>> call, Throwable throwable) {
                    Toast.makeText(MainActivity.this,"登入錯誤: " + throwable.toString(),Toast.LENGTH_SHORT).show(); ;
                }
            });
    }
}

在上面可以看到,我們的請求地址末尾是不帶”/”的,直接請求帶”/”的url會報錯404 Not Found,但是程式碼裡的baseUrl裡的url為何又有”/”呢?

這是因為,在retrofit2.0以後,規定baseUrl裡面的url,必須以”/”結尾,不然會報錯:

這裡寫圖片描述

這裡要打個岔,說明下伺服器介面的定義方式了。

一般來說,很多後臺開發人員,都會把呼叫的方法名字直接放到請求url的後面,比如:
http://app.test.com/testapp.php/login
針對這種定義方式,在請求時,就很簡單,只需在baseUrl裡放http://app.test.com/testapp.php/

Retrofit retrofit = new Retrofit.Builder().baseUrl("http://app.test.com/testapp.php/")
//略...

,然後在login方法的@POST註解裡面放上login

@FormUrlEncoded
@POST("login")
Call<TPHPResult<TLogin>> login(...) //略......

就可以拼接成
http://app.test.com/testapp.php/login

然而,也有的後臺人員,定義介面時,讓客戶端把方法名字當做表單引數傳過來,如上面的action欄位,裡面的值為login,就是我們要請求的介面名字。

請求url永遠是一樣的,通過action來區別各個介面。

這種情況下,如果伺服器不做相容,那麼請求的url只能是不帶”/”的,不然就會404 Not Found。 但是由於retrofit 2.0的限制,baseUrl裡只能是帶”/”的url (http://app.test.com/testapp.php/),這樣是訪問不到伺服器的。怎麼辦呢?

我們可以在@POST裡面放真正的請求地址,這樣就能覆蓋掉baseUrl裡面的url了。那麼,為什麼不把.baseUrl("")去掉,只在@POST裡寫url呢?這是因為不寫會報錯呀 :(

這裡寫圖片描述

總結下使用方法:

首先定義請求的介面類(TestApiService),根據介面引數的格式(表單/鍵值對/body/etc),請求的格式(POST/GET/etc),以及返回結果T(TPHPResult),來宣告一個返回值為Call<T>的login方法

然後定義Retrofit 例項retrofig,通過retrofit例項的create方法建立一個介面類的例項service,呼叫service例項的login方法生成Call物件,然後再enqueue非同步將請求發出去,得到結果並在回撥中解析。

可以看得出來,實際上retrofit的使用還是很簡單的,當然,這也僅僅是入門而已,真正要用到實際業務上,就要考慮架構和封裝了。

相關推薦

retrofit 2.3.0 接入使用

前言 開門見山,本文記錄瞭如何接入並使用square出品的retrofit網路框架。 一、準備工作 新增retrofit 的依賴(或直接使用jar包) 這邊並不能直接連線網路,所以直接下載jar包並使用了 新增okio依賴或引用jar包

solr-5.4.1 mmseg4j-2.3.0版本的配置

配置solr伺服器   1.登入solr的官方網站下載最新版本,目前是5.5.0。http://lucene.apache.org/solr/downloads.html  2.linux下載tgz型別,windows系統下載solr-5.5.0.zip  3.解壓

Spark Release 2.3.0 版本釋出新特性優化

Apache Spark 2.3.0是2.x系列中的第四個版本。此版本增加了對結構化流中的連續處理以及全新的Kubernetes Scheduler後端的支援。其他主要更新包括新的DataSource和結構化Streaming v2 API,以及一些PySpark效能增強。此

未能加載文件或程序集“System.Web.Mvc, Version=5.2.3.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35”或它的某一個依賴項

程序集 版本 獲取 web .net 依賴 net class ima 在發布網站時遇到如題錯誤。 錯誤消息詳細信息:未能加載文件或程序集“System.Web.Mvc, Version=5.2.3.0, Culture=neutral, PublicKeyToken=31

hive 2.3.0的web UI 的配置

color 關於 nbsp href web span 更新 組件 issues 用過hive的都知道,hive可以通過 web 來訪問,只需在hive-site.xml配置即可,但是我在配置的時候根本沒有看到很多博客中所提到的: 關於hwi的ip和port的配置項。最後去

求1+2!+3!+...+20!的

image nbsp png src mage bsp img ima 技術 結果 求1+2!+3!+...+20!的和

編譯的 Ruby 2.3.0 缺少 openssl 支持的解決方法 (已解決)

gpo 重新 and 技術 body figure 編譯 class failed 我的系統是centos 7.5,已離線安裝ruby-2.3.0,openssl-1.0.2l,rubygems-2.7.4 如下圖: 但是在 gem sources -a http:/

selenium-ide-2.3.0 組件在foxfire45.0無法安裝的問題

附件 rfi 頁面 成功 安裝 log install ins 瀏覽器 樓主在安裝selenium-ide組件時,嘗試了下面兩種方式都無法安裝: 1.在forfire瀏覽器進行拖拽安裝,頁面無任何跳轉。拖拽後回車安裝,也沒任何效果 2.附件組件-從文件安裝添加組件,添加了組

kylin_異常_01_java.io.FileNotFoundException: /developer/apache-kylin-2.3.0-bin/tomcat/conf/.keystore

hadoop bstr store iat path ioe .proto https class 一、異常現象 kylin安裝完,啟動後,控制正常,kylin後臺也能正常訪問。但是去看kylin的日誌,卻發現報錯了: SEVERE: Failed to load

【Python3練習題 020】 求1+2!+3!+...+20!的

sum div spa port ons fun plus 函數 UNC 方法一 import functools sum = 0 for i in range(1,21): sum = sum + functools.reduce(lambda x,y: x

python 求階乘之和。求1+2!+3!+...+20!的

blank HR IV sharp ML 術語 lis get 功能 階乘:也是數學裏的一種術語;階乘指從1乘以2乘以3乘以4一直乘到所要求的數;在表達階乘時,就使用“!”來表示。如h階乘,就表示為h!;階乘一般很難計算,因為積都很大。 分析:1、階乘的計算就是比較麻煩的一

Could not load file or assembly 'System.Web.Mvc, Version=5.2.3.0...

3.0 view version img strong pre views str system 一、在Mvc 發布時出現如下錯誤: Could not load file or assembly ‘System.Web.Mvc, Version=5.2.3.0...

java 求 1!+2!+3!+....+10!的

com args println ++ system ack main 輸出 初始 package com.xuyigang1234.chp01; //1!+2!+3!+....+10!的和 public class Demo5 { public static v

ruby升級到2.3.0 cocoapods用不了 怎麼解決?

1.rvm list 你已安裝了哪些版本 2.rvm remove 2.3.0 直接把2.3移除 3.rvm 2.2.2 --default 4.sudo gem uninstall cocoapods 解除安裝cocoapods

【翻譯】OpenTSDB 2.3-- 資料查詢讀取

查詢或讀取資料 OpenTSDB提供了許多提取,操作和分析資料的方法。可以通過CLI工具、HTTP API查詢資料,可以通過GnuPlot圖來檢視資料。有的開源工具,如Grafana和 Bosun也可以訪問TSDB資料以展示資料。OpenTSDB基於標籤的系統在查詢上可能有點棘手,因此請

Apache CouchDB 2.3.0 釋出,文件資料庫

   Apache CouchDB 2.3.0 已釋出,Apache CouchDB 是一個面向文件的資料庫管理系統。它提供以 JSON 作為資料格式的 REST 介面來對其進行操作,並可以通過檢視來操縱文件的組織和呈現。CouchDB 是 Apache 基金會的頂級開源專案。

使用遞迴函式,計算1+2+3+……+n的

#for迴圈 n = int(input('請輸入一個正整數:')) sum = 0 for i in range(n + 1): sum += i print(sum) #遞迴呼叫 n = int(input('請輸入一個正整數:')) def Sum(n): if n

程式基本演算法習題解析 用遞迴函式求 s=1+2+3+...+n 的

附上程式碼: // Chapter6_2.cpp : Defines the entry point for the application. // 用遞迴函式求 s=1+2+3+...+n 的和 #include "stdafx.h" #include<iostream> usi

vue-cli 3.0安裝使用

Vue CLI介紹 Vue CLI 是一個基於 Vue.js 進行快速開發的完整系統,提供: 通過 @vue/cli 搭建互動式的專案腳手架。 通過 @vue/cli + @vue/cli-servic

輸出1!+2!+3!+······+10!的

階乘 package practice; public class Main{ public static void main(String[] args) { int x=1; int sum=0;; for(int i=1;i<=10;i++) {