Android中使用MockWebServer測(cè)試API

文/ZYRzyr
原文鏈接:http://www.itdecent.cn/p/e906f7ee2a04

本文適合這幾類同學(xué)閱讀:熟悉使用Junit4、okhttpretrofit的,閑著無聊的。
??Android中有關(guān)網(wǎng)絡(luò)的開發(fā)通常伴隨著整個(gè)應(yīng)用的開發(fā)過程,而在這個(gè)過程中,大多數(shù)都是采用的手動(dòng)測(cè)試,即運(yùn)行在真機(jī)或模擬器中進(jìn)行真實(shí)的網(wǎng)絡(luò)連接測(cè)試,這樣做難免會(huì)浪費(fèi)一些時(shí)間。但若應(yīng)用中使用的是okhttp,則有一個(gè)非常方便省時(shí)的辦法,即使用MockWebServer進(jìn)行單元測(cè)試。
??本文將使用MockWebServer并結(jié)合retrofit,介紹Android中網(wǎng)絡(luò)部分的單元測(cè)試。

一.準(zhǔn)備

在此,默認(rèn)已在工程中使用了okhttpretrofit,接下來,在Modulebuild.gradle中引入MockWebServer:

dependencies {
    testCompile 'com.squareup.okhttp3:mockwebserver:3.8.1'  //本文編寫時(shí)的最新版本
}

二.開始測(cè)試

1.新建測(cè)試文件WebTest.java:
@RunWith(JUnit4.class)
public class WebTest {

}
2.聲明并實(shí)例化MockWebServer:
@RunWith(JUnit4.class)
public class WebTest {
    @Rule
    public final MockWebServer mockWebServer = new MockWebServer();
}

若不使用@Rule標(biāo)記MockWebServer,則需在@Before@After中分別調(diào)用其start()shutdown()方法。

3.聲明retrofitservice,此處分別測(cè)試MockWebServer的兩種請(qǐng)求響應(yīng)策略:隊(duì)列與轉(zhuǎn)發(fā)器
private interface Service {
        @FormUrlEncoded
        @POST("modify")
        Call<Person> modifyPerson(@Field("name") String name);

        @GET("person/{id}")
        Call<Person> fetchPersonById(@Path("id") int id);  
}

其中的實(shí)體類將在文末給出,實(shí)際開發(fā)中可使用真實(shí)地址,此處僅為假設(shè)。

4.實(shí)例化Service:
@Before
public void setup() {
    service = new Retrofit.Builder()
            .baseUrl(mockWebServer.url("/"))  //實(shí)際項(xiàng)目中可使用真實(shí)url
            .addConverterFactory(FastJsonConverterFactory.create())
            .build()
            .create(Service.class);
}

此處使用fastjson解析返回的json數(shù)據(jù),其中若要使用FastJsonConverterFactory請(qǐng)?zhí)砑尤缦乱蕾嚕?br> 在build.gradle中添加:

allprojects {
    repositories {
        maven { url "https://jitpack.io" }
    }
}

modulebuild.gradle中添加:

dependencies {
    compile 'com.github.ZYRzyr:FastJsonConverter:v1.3-beta'
}
5.隊(duì)列響應(yīng)

調(diào)用MockWebServerenqueue(MockResponse response)方法即可模擬一次請(qǐng)求響應(yīng):

@Test
public void testPOST() throws Exception {
    //模擬服務(wù)器的response
    mockWebServer.enqueue(new MockResponse().setBody("{\"name\": \"Tom\",\"age\": 100}"));

    Call<Person> call = service.modifyPerson("Tom");
    Person person = call.execute().body();

    assertNotNull(person);
    assertEquals("Tom", person.getName());
    assertEquals(100, person.getAge());
    assertEquals("POST", mockWebServer.takeRequest().getMethod());
}
6.轉(zhuǎn)發(fā)器響應(yīng)

需要手動(dòng)編寫Dispatcher并設(shè)置給MockWebServer:

@Test
public void testGET_WithParam() throws Exception {
    mockWebServer.setDispatcher(dispatcher);   //dispatcher見下文
    Call<Person> call = service.fetchPersonById(5);
    Person person = call.execute().body();

    assertNotNull(person);
    assertEquals("A", person.getName());
    assertEquals(11, person.getAge());
    assertEquals("GET", mockWebServer.takeRequest().getMethod());
}

dispatcher:

//dispatcher即為上文中的 mockWebServer.setDispatcher(dispatcher); 
private final Dispatcher dispatcher = new Dispatcher() {
    @Override
    public MockResponse dispatch(RecordedRequest request) throws InterruptedException {
        switch (request.getPath()) {
            case "/person/5":           //5即為GET請(qǐng)求fetchPersonById(@Path("id") int id)中的請(qǐng)求參數(shù)
                return new MockResponse().setResponseCode(200).setBody("{\"name\": \"A\",\"age\": 11}");
            default:
                return new MockResponse().setResponseCode(404);
        }
    }
};

上文中的實(shí)體類Person.java

public class Person {
    private String name;
    private int age;

    public Person() {
    }

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }
...省略getter、setter方法
}

最后

使用了MockWebServer進(jìn)行API測(cè)試,直接省了很多編譯、運(yùn)行的時(shí)間,心情都要好了很多。若想了解更多的關(guān)于MockWebServer本身的東西,可以直接去它老巢查看。

原文作者/ZYRzyr
原文鏈接:http://www.itdecent.cn/p/e906f7ee2a04

請(qǐng)進(jìn)入這里獲取授權(quán):https://101709080007647.bqy.mobi

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • Android 自定義View的各種姿勢(shì)1 Activity的顯示之ViewRootImpl詳解 Activity...
    passiontim閱讀 178,733評(píng)論 25 709
  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,506評(píng)論 19 139
  • 框架:提供一定能力的小段程序 http://www.cnblogs.com/jincheng-yangchaofa...
    姑娘請(qǐng)別為難小僧閱讀 7,789評(píng)論 0 132
  • 自由 是來自遠(yuǎn)方的呼喚 還是內(nèi)心的吶喊 沖破枷鎖 讓每一片靈魂在風(fēng)中飄揚(yáng) 日出時(shí) 我是東海邊的一粒沙 日落時(shí) 我是...
    星無塵懿閱讀 261評(píng)論 0 1
  • 天上一輪似桃李,疑是渭濱畫彩云。獨(dú)愛一澤與晚霞,馬鞭曉楓閱春秋。
    一葦之杭閱讀 499評(píng)論 0 2

友情鏈接更多精彩內(nèi)容