使用RestTemplate進行http調用格式轉換問題

之前http調用都是自己封裝的HttpClients,比較麻煩。最近發現有新的API:RestTemplate可以直接調用接口,非常方便,省得自己封裝請求了。

開始使用:

String url = targetInfoUrl +"?userId={userId}";
Map<String,Object> paramMap = new HashMap(1);
paramMap.put("userId",userId);
Response response = new RestTemplate().getForObject(url, Response.class, paramMap);

被請求接口的返回值是Response類,結構如下:

public class Response<T> {

    public String code;

    public String msg;

    @JsonInclude(value = JsonInclude.Include.NON_NULL)
    public T data;
}

其中data具體的值是一個List<MemberInfoAndTargetInfo>。這個MemberInfoAndTargetInfo類的屬性又有一個List<TargetInfoBean>

public class MemberInfoAndTargetInfo {

    private String userId;

    /**
     * 用戶目標信息
     */
    private List<TargetInfoBean> targetInfos;
}

我在獲取到Response時,進行強制轉換失敗,編譯不會報錯,運行期報錯

List<MemberInfoAndTargetInfo> data1 = (List<MemberInfoAndTargetInfo>) response.getData();

報錯原因是Map不能被強制轉換爲List。這才發現自己忘記反序列化了,被getForObject方法:

	@Override
	@Nullable
	public <T> T getForObject(String url, Class<T> responseType, Map<String, ?> uriVariables) throws RestClientException {
		RequestCallback requestCallback = acceptHeaderRequestCallback(responseType);
		HttpMessageConverterExtractor<T> responseExtractor =
				new HttpMessageConverterExtractor<>(responseType, getMessageConverters(), logger);
		return execute(url, HttpMethod.GET, requestCallback, responseExtractor, uriVariables);
	}

的第二個參數迷惑了,自以爲它會幫我反序列化。其實返回的是Response類型的json格式數據,需要我自己再反序列化。查看源碼,這個responseType也僅表示類的名稱等類型信息。於是自己就反序列化一下:

String stringObject = new RestTemplate().getForObject(url, String.class, paramMap);
Object data = JSONObject.parseObject(stringObject).get(ConstantConfig.DATA);
List<MemberInfoAndTargetInfo> targetInfos = JSONArray.parseArray(data.toString(), MemberInfoAndTargetInfo.class);

轉化的過程,又發現MemberInfoAndTargetInfo類的屬性有一個List<TargetInfoBean>無法反序列化,報錯說缺少構造方法。我查看代碼,發現MemberInfoAndTargetInfo類有方法:

public void setTargetInfos(List<TargetInfoBean> targetInfos) {
    this.targetInfos = targetInfos;
}

於是查看TargetInfoBean類,發現它少了一個無參的構造方法,補上後,成功。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章