总有些时候,后端给你的数据是比较特殊的,不能轻易的把返回json转换成对象,比如以下数据
{
"code": 200,
"message": "成功",
"data": {
"income": "667.06",
"statement_data": {
"2023-11": {
"income": "542.00",
"expend": "0.00"
},
"2023-12": {
"income": "125.06",
"expend": "0.00"
}
}
}
}
因为key的名称是不确定的,所以不能让retrofit 转。我们需要获取原数据。
把返回数据改成ResponseBody
如
sealed interface StatementCalls {
@FormUrlEncoded
@POST("/api/{user}/statement")
fun getStatement(
@Path("user") user: String,
@FieldMap map: Map<String, String>
):Call<ResponseBody>
}
异步返回之后,调用 responeBody.string()方法,解析json。在本例中,遍历statement_data的keys,
如
val statementData=JSONObject(json)
.getJSONObject("data")
.getJSONArray("statement_data")
val dataList = mutableListOf<TenementStatementRecyclerData>()
for (index in 0 until statementData.length()) {
val jsonObject = statementData.getJSONObject(index)
val incomeMoney = jsonObject.getString("income")
val paidMoney = jsonObject.getString("expend")
val tenementStatementBean = TenementStatementRecyclerData(
income = incomeMoney,
expend = paidMoney
)
dataList.add(tenementStatementBean)
}
如果json又臭又长,那么强烈建议,构建jsonObject的时候就获取data字段,不然很容易在茫茫的Java代码中迷失……
val dataJson=JSONObject(json).getJSONObject("data")
responeBody.string()只返回一次响应体字符串,需要注意订阅等一些操作,比如,在多个地方订阅这个body,需要把string储存起来,否则会返回空值。
viewModel.statement.filterNotNull().collect{
val response=it.string()
...
}
//在另一处
viewModel.statement.filterNotNull().collect{
val response=it.string()//不要这么做.后收集会返回空值
...
}