如何创建通用模型反序列化Kucoin与Binance的API订单簿响应
解决Kucoin与Binance API响应通用反序列化问题
针对两个交易所API响应结构差异的问题,以下是三种实用解决方案:
方案1:自定义JsonConverter统一处理两种结构
通过自定义JsonConverter,让现有OrderBookResponse模型自动适配两种响应格式:
using System.Text.Json; using System.Text.Json.Serialization; // 保留原有模型结构 public class OrderBookResponse { public OrderBookData Data { get; set; } } public class OrderBookData { public List<List<string>> Bids { get; set; } public List<List<string>> Asks { get; set; } } // 自定义转换器实现兼容逻辑 public class OrderBookResponseConverter : JsonConverter<OrderBookResponse> { public override OrderBookResponse Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { using var doc = JsonDocument.ParseValue(ref reader); var root = doc.RootElement; OrderBookData data; // 识别Kucoin结构(包含data字段) if (root.TryGetProperty("data", out var dataElement)) { data = JsonSerializer.Deserialize<OrderBookData>(dataElement.GetRawText(), options); } // 识别Binance结构(根节点直接包含bids/asks) else { data = JsonSerializer.Deserialize<OrderBookData>(root.GetRawText(), options); } return new OrderBookResponse { Data = data }; } public override void Write(Utf8JsonWriter writer, OrderBookResponse value, JsonSerializerOptions options) { // 若无需序列化响应,此处可留空或按需实现 JsonSerializer.Serialize(writer, value.Data, options); } }
修改两个服务的反序列化逻辑,添加转换器:
// KucoinService和BinanceService中替换反序列化代码 var options = new JsonSerializerOptions(); options.Converters.Add(new OrderBookResponseConverter()); OrderBookResponse deserializedResponse = response.Content.ReadFromJsonAsync<OrderBookResponse>(options).Result;
方案2:通用接口+适配模型
定义通用接口,为每个交易所创建专属响应模型,实现接口统一调用:
// 通用数据接口 public interface IOrderBookData { List<List<string>> Bids { get; } List<List<string>> Asks { get; } } // Kucoin专属模型 public class KucoinOrderBookResponse { public KucoinOrderBookData Data { get; set; } } public class KucoinOrderBookData : IOrderBookData { public List<List<string>> Bids { get; set; } public List<List<string>> Asks { get; set; } } // Binance专属模型 public class BinanceOrderBookResponse : IOrderBookData { public List<List<string>> Bids { get; set; } public List<List<string>> Asks { get; set; } // Binance其他冗余字段可忽略,无需定义 }
修改服务代码,分别反序列化为对应模型:
KucoinService
KucoinOrderBookResponse deserializedResponse = response.Content.ReadFromJsonAsync<KucoinOrderBookResponse>().Result; ExchangeRate exchangeRate = new ExchangeRate() { ExchangeName = "Kucoin", Rate = PriceHelper.GetAveragePrice(deserializedResponse.Data) };
BinanceService
BinanceOrderBookResponse deserializedResponse = response.Content.ReadFromJsonAsync<BinanceOrderBookResponse>().Result; ExchangeRate exchangeRate = new ExchangeRate() { ExchangeName = "Binance", Rate = PriceHelper.GetAveragePrice(deserializedResponse) };
同时更新PriceHelper.GetAveragePrice的参数类型:
public static decimal GetAveragePrice(IOrderBookData orderBookData) { // 原有逻辑直接使用orderBookData.Bids和orderBookData.Asks即可 }
方案3:直接用JObject提取字段(轻量方案)
无需修改模型,直接解析JSON提取目标字段:
KucoinService
using System.Text.Json; var jsonString = response.Content.ReadAsStringAsync().Result; var doc = JsonDocument.Parse(jsonString); var dataElement = doc.RootElement.GetProperty("data"); var orderBookData = new OrderBookData { Bids = JsonSerializer.Deserialize<List<List<string>>>(dataElement.GetProperty("bids").GetRawText()), Asks = JsonSerializer.Deserialize<List<List<string>>>(dataElement.GetProperty("asks").GetRawText()) };
BinanceService
using System.Text.Json; var jsonString = response.Content.ReadAsStringAsync().Result; var doc = JsonDocument.Parse(jsonString); var orderBookData = new OrderBookData { Bids = JsonSerializer.Deserialize<List<List<string>>>(doc.RootElement.GetProperty("bids").GetRawText()), Asks = JsonSerializer.Deserialize<List<List<string>>>(doc.RootElement.GetProperty("asks").GetRawText()) };
后续逻辑保持不变,直接使用orderBookData计算汇率即可。
内容的提问来源于stack exchange,提问作者fuxxxcy
相关产品推荐
相关产品推荐

