1. 程式人生 > >【我的Android進階之旅】使用Retrofit進行Post請求報錯: @Field parameters can only be used with form encoding.

【我的Android進階之旅】使用Retrofit進行Post請求報錯: @Field parameters can only be used with form encoding.

一、問題描述

今天隨手寫一個post請求的時候,報錯了,如下所示: 在這裡插入圖片描述

09-28 11:11:28.155 10547-10547/com.xtc.watch E/Fatal: {CrashHandler.saveAndPrintLog-58} 
    java.lang.IllegalStateException: Exception thrown on Scheduler.Worker thread. Add `onError` handling.
        at rx.android.schedulers.LooperScheduler$ScheduledAction.run(LooperScheduler.java:112)
        at android.os.Handler.handleCallback(Handler.java:815)
        at android.os.Handler.dispatchMessage(Handler.java:104)
        at android.os.Looper.loop(Looper.java:207)
        at android.app.ActivityThread.main(ActivityThread.java:5981)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:888)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:749)
     Caused by: rx.exceptions.OnErrorNotImplementedException: @Field parameters can only be used with form encoding. (parameter #1)
        for method WatchAccountHttpService.getByBindNumber
        at rx.internal.util.InternalObservableUtils$ErrorNotImplementedAction.call(InternalObservableUtils.java:386)
        at rx.internal.util.InternalObservableUtils$ErrorNotImplementedAction.call(InternalObservableUtils.java:383)
        at rx.internal.util.ActionSubscriber.onError(ActionSubscriber.java:44)
        at rx.observers.SafeSubscriber._onError(SafeSubscriber.java:152)
        at rx.observers.SafeSubscriber.onError(SafeSubscriber.java:115)
        at rx.exceptions.Exceptions.throwOrReport(Exceptions.java:216)
        at rx.observers.SafeSubscriber.onNext(SafeSubscriber.java:139)
        at rx.internal.operators.OperatorObserveOn$ObserveOnSubscriber.call(OperatorObserveOn.java:227)
        at rx.android.schedulers.LooperScheduler$ScheduledAction.run(LooperScheduler.java:107)
        	... 7 more
     Caused by: java.lang.IllegalArgumentException: @Field parameters can only be used with form encoding. (parameter #1)
        for method WatchAccountHttpService.getByBindNumber
        at retrofit2.ServiceMethod$Builder.methodError(ServiceMethod.java:720)
        at retrofit2.ServiceMethod$Builder.methodError(ServiceMethod.java:711)
        at retrofit2.ServiceMethod$Builder.parameterError(ServiceMethod.java:729)
        at retrofit2.ServiceMethod$Builder.parseParameterAnnotation(ServiceMethod.java:501)
        at retrofit2.ServiceMethod$Builder.parseParameter(ServiceMethod.java:333)
        at retrofit2.ServiceMethod$Builder.build(ServiceMethod.java:202)
        at retrofit2.Retrofit.loadServiceMethod(Retrofit.java:166)
        at retrofit2.Retrofit$1.invoke(Retrofit.java:145)
        at java.lang.reflect.Proxy.invoke(Proxy.java:393)
        at $Proxy42.getByBindNumber(Unknown Source)
        at com.xtc.watch.net.watch.http.account.WatchAccountHttpServiceProxy.getByBindNumber(WatchAccountHttpServiceProxy.java:44)
        at com.xtc.watch.service.account.impl.WatchServiceImpl.getWatchAccountByBindNumberAsync(WatchServiceImpl.java:258)
        at com.xtc.watch.service.account.impl.WatchServiceImpl.getBindCheckInfoByBindNumber(WatchServiceImpl.java:273)
        at com.xtc.watch.view.account.bind.utils.BindNumberHelper.loadBindNumberInfo(BindNumberHelper.java:172)
        at com.xtc.watch.view.account.bind.utils.BindNumberHelper.resolveBindNumber(BindNumberHelper.java:132)
        at com.xtc.watch.view.account.bind.utils.BindNumberHelper.resolveBindNumber(BindNumberHelper.java:114)
        at com.xtc.watch.view.account.bind.BindAlbumPreviewActivity$5.call(BindAlbumPreviewActivity.java:285)
        at com.xtc.watch.view.account.bind.BindAlbumPreviewActivity$5.call(BindAlbumPreviewActivity.java:244)
        at rx.internal.util.ActionSubscriber.onNext(ActionSubscriber.java:39)
        at rx.observers.SafeSubscriber.onNext(SafeSubscriber.java:134)
        	... 9 more

二、分析和解決問題

2.1 分析問題

根據錯誤資訊,跟蹤錯誤堆疊,然後找到對應的Retrofit介面定義之處,如下所示: 在這裡插入圖片描述

    @POST("/watchaccount/bindnumber")
    Observable<HttpResponse<NetWatchAccount>> getByBindNumber(@Field("bindNumber") String bindNumber);

在這裡插入圖片描述

哎,當POST請求時,@FormUrlEncoded和@Field簡單的表單鍵值對。兩個需要結合使用,否則會報錯。 由於寫的太快了,把@FormUrlEncoded註解忘記了。

2.2 解決問題

在 @POST註解之上,加上@FormUrlEncoded註解即可。

    @FormUrlEncoded
    @POST("/watchaccount/bindnumber")
    Observable<HttpResponse<NetWatchAccount>> getByBindNumber(@Field("bindNumber") String bindNumber);

三、Retrofit註解

在這裡插入圖片描述

  • 請求方法
註解程式碼 請求格式
@GET GET請求
@POST POST請求
@DELETE DELETE請求
@HEAD HEAD請求
@OPTIONS OPTIONS請求
@PATCH PATCH請求
  • 請求引數
註解程式碼 說明
@Headers 新增請求頭
@Path 替換路徑
@Query 替代引數值,通常是結合get請求的
@FormUrlEncoded 用表單資料提交
@Field 替換引數值,是結合post請求的
@Body 請求體,是結合post請求的

如果本文對您有所幫助,歡迎您掃碼下圖所示的支付寶和微信支付二維碼對本文進行打賞。

在這裡插入圖片描述