Kotlin 改造错误 "Expected BEGIN_ARRAY but was BEGIN_OBJECT"

Kotlin Retrofit Error "Expected BEGIN_ARRAY but was BEGIN_OBJECT"

我已通读 Whosebug 上的多篇文章,但尚未找到适合我的问题的解决方案。你能帮我解决这个 Retrofit 错误吗?

JSON 回复:

{
"products": [
    {
        "barcode_number": "8000040000802",
        "barcode_type": "EAN",
        "barcode_formats": "EAN 8000040000802",
        "mpn": "",
        "model": "",
        "asin": "",
        "product_name": "Campari Bitter 25% Vol. 1 L",
        "title": "",
        "category": "Food, Beverages & Tobacco > Beverages > Alcoholic Beverages > Bitters",
        "manufacturer": "Campari",
        "brand": "Campari",
        "label": "",
        "author": "",
        "publisher": "",
        "artist": "",
        "actor": "",
        "director": "",
        "studio": "",
        "genre": "",
        "audience_rating": "",
        "ingredients": "",
        "nutrition_facts": "",
        "color": "",
        "format": "",
        "package_quantity": "",
        "size": "",
        "length": "",
        "width": "",
        "height": "",
        "weight": "",
        "release_date": "",
        "description": "",
        "features": [],
        "images": [
            "https://images.barcodelookup.com/19631/196313718-1.jpg"
        ],
        "stores": [
            {
                "store_name": "Rakuten Deutschland GmbH",
                "store_price": "16.50",
                "product_url": "https://www.rakuten.de/produkt/campari-bitter-25-vol-1-l-1826679605",
                "currency_code": "EUR",
                "currency_symbol": "€"
            }
        ],
        "reviews": []
    }
]
}

Kotlin 插件 JSON 创建的数据 类:

data class BaseResponse(
   val products: List<Product>
)

产品:

data class Product(
    val actor: String,
    val artist: String,
    val asin: String,
    val audience_rating: String,
    ...
)

商店:

data class Store(
    val currency_code: String,
    val currency_symbol: String,
    val product_url: String,
    val store_name: String,
    val store_price: String
)

服务:

interface BarcodeLookupApiService {
    @GET("products")
    suspend fun getArticleData(@Query("barcode") barcode: String,
                               @Query("key") key: String): List<BaseResponse>
}

改造生成器:

object RetrofitBuilder {
    private const val BASE_URL = "https://api.barcodelookup.com/v2/"

    private fun getRetrofit(): Retrofit {
        return Retrofit.Builder()
            .baseUrl(BASE_URL)
            .addConverterFactory(GsonConverterFactory.create())
            .build()
    }

    val apiService: BarcodeLookupApiService =
        getRetrofit().create(BarcodeLookupApiService::class.java)
}

难道插件创建的数据类不对?或者我的服务不应该 return 列表?我试过 returning 一个简单的 BaseResponse 对象,但这也不起作用。

更改您的界面,如下所示:

interface BarcodeLookupApiService {
    @GET("products")
    suspend fun getArticleData(@Query("barcode") barcode: String,
                               @Query("key") key: String): BaseResponse
}

要获取产品列表,请执行以下操作:

baseRespose.ProductsList

这将解决您的问题。响应是一个对象,对象内部有一个数组。因此你得到了错误。

在我的例子中,我使用 Laravel 框架来构建我的 Web 服务或 Rest Api with Sanctum。好的,问题在这里:

{
    "result": {
        "message": "Registrado correctamente",
        "success": true,
        "status": 200,
        "error": null
    }
}

brackets的GsonConverter查询是的看这里注意:

{
    "result": [
        {
            "message": "Registrado correctamente",
            "success": true,
            "status": 200,
            "error": null
        }
    ]

我更新我的后端 Api:

   $result = [
            'message' => 'Registrado correctamente',
            'success' => true,
            'status' => 200,
            'error' => null         
           ];
         
           return response()->json([
               'result' => $result,
           ], 200);

  return response()->json([
               'result' => [$result],
           ], 200);

请注意我在'result'中添加了括号[ ]。这解决了我的问题。

我的两个数据class是这样的:

@Parcelize
data class RegisterResponseObj(
    val message: String,
    val success: Boolean,
    val status: Int = -1,
    val error: String?,
) : Parcelable

data class RegisterResponse(val result: List<RegisterResponseObj>)

网络服务:

interface WebService {
        
    @FormUrlEncoded
    @Headers("Accept: application/json")
    @POST("register")
    suspend fun registerUser(@Field("name") name: String,
                            @Field("email") email: String,
                            @Field("password")password: String): RegisterResponse

}

干杯!