本篇文章已授權微信公眾號 guolin_blog (郭霖)獨家釋出
原文連結:模擬伺服器返回資料
背景
模擬伺服器返回的資料,在以下場景具有實際意義:
和伺服器開發協商好開發介面,但伺服器API尚未部署,想介面定義好就進行開發;
伺服器已部署,返回的資料不能測試到各種情況,希望返回期待資料測試邊界情況;
如果客戶端開發人員能不走伺服器,通過模擬資料返回,能提升開發效率和程式質量。
實現思路
本文主要講解兩種實現方式:
使用網路分析工具攔截客戶端請求,並返回偽造資料。
優點:無需改變客戶端程式碼;不依賴客戶端平臺,android和ios都通用;
缺點:依賴網路分析工具;除錯相對不靈活;使用客戶端網路框架攔截請求並返回。
優點:返回資料由客戶端程式碼決定,靈活易於除錯;
缺點:需要改變客戶端程式碼;需要根據客戶端網路框架進行響應處理,不同的網路框架處理不一樣;
對於方案一,主要使用網路分析工具Charles進行攔截並返回,對於方案二,主要講解使用OkHttp作為網路框架,利用攔截器機制實現模擬返回。
使用Charles模擬資料
準備條件
- 客戶端需要連線到和電腦同一個網路(手機連線電腦發出的wifi)
- 官網下載安裝
配置
配置方法參考Charles:移動端裝置網路抓包
完成配置後,可以在Charles中檢測到手機的網路請求和響應。
轉接伺服器地址
轉接伺服器地址是指,當客戶端請求地址B時,本應該向指定的伺服器請求資料,但Charles可攔截此ip地址,使不向伺服器地址請求,並且返回另外一臺伺服器模擬的資料。
首先,我們來生成模擬返回資料的api介面;
開啟mocky網址,輸入想偽造Body資料,點選Generate my HTTP Response按鈕生成http的url地址。
如圖,當點選www.mocky.io/v2/58592298… 時,返回json格式的資料。
有了模擬資料的api地址,接著設定需要模擬的api介面。經過配置後,Charles可檢測手機的網路請求,選擇需要模擬返回資料的網路請求介面,右鍵選擇Map Remote...
Map From為需要攔截的介面,Map To為模擬的api介面,此處我們填入www.mocky.io/v2/58592298…,如下圖:
選擇標題欄Tool工具圖示,取消選擇Map Remote,再勾選Map Remote,讓設定的ip地址生效。此時,當客戶端請求原地址時,都會返回模擬ip地址的資料,效果圖如下:
小結
以上,使用Mocky網路和Charles工具實現模擬資料返回,無需改變客戶端原有程式碼,但是,當需要改變客戶端返回的資料時,則需要重新生成http模擬地址,再次設定Charles Map to內容。
自定義OkHttp Interceptor模擬返回
以下內容假設使用者掌握OkHttp的簡單使用,重點講解自定義OkHttpInterceptor模擬返回資料。
OkHttp攔截器
如圖,OkHttp可在Request和Response中設定任意個數的Intercepor(圖中用圓圈標識),對請求體和響應體進行處理。藉助OkHttp Interceptor機制,建立一個MockIntercepor,模擬返回一個Response,虛線部分為模擬的Response。
程式碼實現
MockInterceptor程式碼如下:
public class MockInterceptor implements Interceptor{
@Override
public Response intercept(Chain chain) throws IOException {
Gson gson = new Gson();
Response response = null;
Response.Builder responseBuilder = new Response.Builder()
.code(200)
.message("")
.request(chain.request())
.protocol(Protocol.HTTP_1_0)
.addHeader("content-type", "application/json");
Request request = chain.request();
if(request.url().equals("http://url_whitch_need_to_mock")) { //攔截指定地址
String responseString = "{\n" + //模擬資料返回body
"\t\"code\": 200,\n" +
"\t\"message\": \"success\",\n" +
"\t\"data\": {}\n" +
"}";
responseBuilder.body(ResponseBody.create(MediaType.parse("application/json"), responseString.getBytes()));//將資料設定到body中
response = responseBuilder.build(); //builder模式構建response
}else{
response = chain.proceed(request);
}
return response;
}
}複製程式碼
在debug模式下,將此Interceptor新增到網路請求的OkHttp中,即可對指定的api地址進行攔截,並且返回特定的資料。
小結
使用OkHttp的攔截機制,可實現改變部分程式碼則可模擬返回資料,返回的資料可在程式碼中設定,可使用工廠模式將模擬資料的生成變動程式碼放到Factory中。依賴網路請求框架,若原專案使用OkHttp或Retrofit作為網路框架,可輕易實現模擬介面。
引用
Charles:移動端裝置網路抓包
利用charles模擬Http請求和響應
Hack Retrofit (2) 之 Mock Server
OkHttp Interceptor