You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

将JSON对象反序列化为DataTable报错,如何正确转换?

JSON对象转DataTable报错处理

错误原因

你遇到的报错:

"Unexpected JSON token when reading DataTable. Expected StartArray, got StartObject. Path '', line 1, position 1."

是因为JsonConvert.DeserializeObject<DataTable>()要求传入的JSON是数组格式(用[]包裹),但你的JSON最外层是对象(用{}包裹),直接反序列化自然会失败。你的JSON里真正需要转成DataTable的是Data字段下的数组内容。

解决方法

下面提供两种可行的修改方案,任选其一即可:

方案一:定义实体类解析(类型安全)

先定义对应JSON结构的实体类:

public class RootObject
{
    public string ServiceName { get; set; }
    public string origin { get; set; }
    public List<DataItem> Data { get; set; }
}

public class DataItem
{
    public int status { get; set; }
    public string statusMessage { get; set; }
    public string url { get; set; }
}

然后修改你的业务代码:

DataTable dsAcknowledgement = new DataTable();               
int Count = 1;

// 先解析整个JSON对象
var root = JsonConvert.DeserializeObject<RootObject>(Convert.ToString(Input));
// 将Data列表转成DataTable
dsAcknowledgement = JsonConvert.DeserializeObject<DataTable>(JsonConvert.SerializeObject(root.Data));

foreach (DataRow dr in dsAcknowledgement.Rows)
{
    string encrypteddata = Convert.ToString(dr["url"]);
    string DecrypteUrl = SbntAPICrypto.Decrypt(Encrypt_AES256_Key, Encrypt_AES256_iv, encrypteddata);
    // 把解密后的值写回DataRow,否则修改不会生效
    dr["url"] = DecrypteUrl;
    Count++;
}

// 将修改后的DataTable放回原对象,再序列化
root.Data = JsonConvert.DeserializeObject<List<DataItem>>(JsonConvert.SerializeObject(dsAcknowledgement));
Input = JsonConvert.SerializeObject(root);
return ShipmateWebService(Input);

方案二:用JObject直接提取数组(无需定义类)

如果不想写实体类,可以用JObject直接操作JSON:

DataTable dsAcknowledgement = new DataTable();               
int Count = 1;

// 解析整个JSON对象
JObject jsonObj = JObject.Parse(Convert.ToString(Input));
// 提取Data字段下的数组
JArray dataArray = (JArray)jsonObj["Data"];
// 转成DataTable
dsAcknowledgement = dataArray.ToObject<DataTable>();

foreach (DataRow dr in dsAcknowledgement.Rows)
{
    string encrypteddata = Convert.ToString(dr["url"]);
    string DecrypteUrl = SbntAPICrypto.Decrypt(Encrypt_AES256_Key, Encrypt_AES256_iv, encrypteddata);
    dr["url"] = DecrypteUrl;
    Count++;
}

// 将修改后的DataTable放回原JSON对象
jsonObj["Data"] = JArray.FromObject(dsAcknowledgement);
Input = jsonObj.ToString();
return ShipmateWebService(Input);

注意点

  • 原代码中仅解密了url但未将解密后的值写回DataRow,若需要保留修改结果,必须加上dr["url"] = DecrypteUrl这行代码。
  • 如果后续需要把完整JSON传回服务,记得将修改后的DataTable重新放回原JSON结构中,而不是直接序列化DataTable。

内容的提问来源于stack exchange,提问作者keerthana

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.20 05:59:54