我使用Json.Net庫(用於.NET v3.5)來處理來自EBoss CRM API的反應的反序列化。據我所見,API文檔相當多,所以我不得不自己捅一下,看看可以引發什麼樣的反應。有條件的數組/對象反序列化與Json.Net
我想擁有一個包裝類EBossApiResponse<T>
,它將爲API返回的任何錯誤消息提供屬性,並且包含一個包含類型爲T
的反序列化數據的屬性(它將被限制爲一個抽象基類,我爲建模返回的數據而創建的任何類的基礎類型)。
我最初的戳說明了第一個問題。有效的請求可以返回一組對象,如:https://ebosscrm.com/api.php/job_type.json
這將很容易反序列化爲List<EBossJobType>
的假設T
。請注意,結果中沒有錯誤屬性。
甲惡意請求到該相同的端點然而返回不同的東西:https://ebosscrm.com/api.php/job_type.json?search[foo]=1
在這種情況下,則返回一個數組,它包含與名爲message
單個屬性單個對象。
(請注意,有呼籲將具有一個參數命名search[something]
是有效的,但foo
是從來沒有一個有效的something
)
還有要返回精確的錯誤的可能性。它看起來像API捕捉異常並格式化包含調試信息的JSON響應:https://ebosscrm.com/api.php/candidates.json?uid=114&api_key=f34js3kj
在這種情況下,返回的JSON不是數組,它是單個對象。我不知道如何迎合這些不同的響應結構。我最初的想法是有類似:
protected bool IsNonDataResponse(string response)
{
JObject o = JObject.Parse(response);
return o.SelectToken("message") != null || o.SelectToken("error") != null;
}
我可以用這個方法來然後要麼直接deserialise向右側EBossApiResponse<T>
類型(如果是真的,填充錯誤消息,但離開.Data
財產== NULL),或deserialise右邊的List<EBossEntityType>
,創建一個新的EBossApiResponse<List<EBossEntityType>>
,並設置其.Data
屬性。
然後我意識到o.SelectToken("message")
將無法正常工作,因爲o
將是一個數組,而不是一個對象。 .SelectToken()
可以採用"[0].message"
的格式來獲取第一項的消息屬性?
這個怎麼樣?
JObject o = JObject.Parse(response);
JArray arr = o as JArray;
return (arr != null && (JObject)arr[0].SelectToken("message") != null)
|| o.SelectToken("error") != null;
還是我完全找錯了樹,還有一個更優雅的解決這件事?
我想知道在地球上我怎麼可能錯過了閱讀文檔,並剛回到他們我意識到爲什麼:我正在使用.NET Framework v3.5進行項目集成,因此Json.Net 3.5,JToken.Parse()稍後被引入Json.Net。我沒有它:( –
回來進行清理。雖然它當時沒有解決問題,但現在肯定是正確的答案。 –