首页 > 解决方案 > 过滤解析的 JSON 对象

问题描述

我正在拨打休息电话并收到以下 JSON 响应:

{
    "issues": [{
            "id": "250271",
            "self": "KeyUrl1",
            "key": "Key-8622",
            "fields": {
                "attachment": [{
                        "self": "AttachmentUrl1",
                        "id": "106198",
                        "filename": "export.htm"
                    }
                ],
                "customfield_11041": "Test"
            }
        },
        {
            "id": "250272",
            "self": "KeyUrl2",
            "key": "Key-8621",
            "fields": {
                "attachment": [{
                        "self": "AttachmentUrl2",
                        "id": "106199",
                        "filename": "lmn.htm"
                    }
                ],
                "customfield_11041": "Test"
            }
        },
    ]
}

我使用 NewtonSoft Json 将它解析为 JObject。

var jObject = JObject.Parse(response);

此外,我正在尝试过滤缺少附件或没有附件包含“导出”之类的文件名的此类记录。

以下是我编写的代码,理想情况下它应该只在记录对象中产生 1 条记录,但是它返回两个对象。

var issues = jObject["issues"] as JArray;
var records = issues.Where(x => !x["fields"]["attachment"].Any() || !x["fields"]["attachment"].Any(y => y["filename"].Contains("export")));

需要帮助找出问题所在。

这是小提琴链接 - https://dotnetfiddle.net/AVyIHr

标签: c#.netjson

解决方案


问题是您调用Contains("export")的结果y["filename"]不是字符串,而是JToken. 您需要先转换为字符串,才能使用Contains您期望的形式。

此外,您可以摆脱第一个条件 -没有附件的问题无论如何都没有任何带有“导出”文件名的附件。

剩下的就是:

var records = issues
    .Where(x => !x["fields"]["attachment"].Any(y => ((string) y["filename"]).Contains("export")))
    .ToList();

但是,您可能会发现反序列化为一个类更简单 - 这将降低拼写错误的风险此类转换错误的风险。如果您反序列化为 aList<Issue>您将有以下条件:

x => !x.Fields.Attachments.Any(y => y.Filename.Contains("export"))

......我认为这是相当干净的。


推荐阅读