映射嵌套JSON时如何检查NULL? [英] How to check for NULL when mapping nested JSON?

查看:140
本文介绍了映射嵌套JSON时如何检查NULL?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试将嵌套的JSON映射到模型对象,问题是当它返回null时,它将破坏所有代码,我想检查null是否可以执行某些操作但不破坏应用程序.

JSON文件:

[
    {
        "id": 53,
        "date": "2018-12-28T08:51:11",
        "title": {
            "rendered": "this is for featured"
        },
        "content": {
            "rendered": "\n<p><g class=\"gr_ gr_3 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling\" id=\"3\" data-gr-id=\"3\">sdafkj</g> <g class=\"gr_ gr_10 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling ins-del multiReplace\" id=\"10\" data-gr-id=\"10\">kj</g> <g class=\"gr_ gr_16 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling ins-del multiReplace\" id=\"16\" data-gr-id=\"16\">asd</g> <g class=\"gr_ gr_18 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling\" id=\"18\" data-gr-id=\"18\">kadjsfk</g> kljadfklj sd</p>\n",
            "protected": false
        },
        "excerpt": {
            "rendered": "<p>sdafkj kj asd kadjsfk kljadfklj sd</p>\n",
            "protected": false
        },
        "author": 1,
        "featured_media": 54,
        "_links": {
            "self": [
                {
                    "href": "https://client.kurd.app/wp-json/wp/v2/posts/53"
                }
            ],

        },
        "_embedded": {
            "author": [
                {
                    "id": 1,
                    "name": "hooshyar",

                }
            ],
            "wp:featuredmedia": [
                {
                    "id": 54,

                    "source_url": "https://client.kurd.app/wp-content/uploads/2018/12/icannotknow_22_12_2018_18_48_11_430.jpg",
                    }
                    ]
}
]

映射到对象的代码:

  featuredMediaUrl = map ["_embedded"]["wp:featuredmedia"][0]["source_url"];

方法'map'在null上被调用. 接收方:null [0],有时返回null;

解决方案

在我的评论之后,我建议您使用代码生成库将JSON解析为JSON Models.

阅读本文,向您说明如何使用(例如) json_serializable 包. >

此类库承担生成所有样板代码的所有繁琐工作来创建您的Model类,并且它们将null值视为强制值.

例如,如果您对一个类Person进行注释,则:

@JsonSerializable(nullable: true)
class Person {
  final String firstName;
  final String lastName;
  final DateTime dateOfBirth;
  Person({this.firstName, this.lastName, this.dateOfBirth});
  factory Person.fromJson(Map<String, dynamic> json) => _$PersonFromJson(json);
  Map<String, dynamic> toJson() => _$PersonToJson(this);
}

使用(nullable: true)模型的dart类将跳过空值字段.

更新

由于我渴望技术,因此我尝试了 quicktype 工具(由Christoph Lachenicht建议)例子.

我已经准备了模拟api 和文件example.json提供您发布的JSON.我只用了一个元素,而不是数组.您可以在这里 example.json .

在安装QuickType后,我已经为此json生成了模型类:

quicktype --lang dart --all-properties-optional example.json -o example.dart

这里请注意cli参数--all-properties-optional,该参数会为缺少的字段创建空检查.

Map<String, dynamic> toJson() => {
    "id": id == null ? null : id,
    "date": date == null ? null : date,
    "title": title == null ? null : title.toJson(),
    "content": content == null ? null : content.toJson(),
    "excerpt": excerpt == null ? null : excerpt.toJson(),
    "author": author == null ? null : author,
    "featured_media": featuredMedia == null ? null : featuredMedia,
    "_links": links == null ? null : links.toJson(),
    "_embedded": embedded == null ? null : embedded.toJson(),
};

然后我在example.dart

中使用了Example类

var jsonExampleResponse =
    await http.get('https://www.shadowsheep.it/so/53962129/testjson.php');
print(jsonExampleResponse.body);

var exampleClass = exampleFromJson(jsonExampleResponse.body);
print(exampleClass.toJson());

一切都很好.

N.B. 当然,当您使用此类时,必须在使用它们之前检查其字段是否为空:

print(exampleClass.embedded?.wpFeaturedmedia?.toString());

仅此而已.我希望能使您处于正确的方向.

I'm trying to map a nested JSON to the model object, the problem is when it returns null, it will break all the code, I want to check if null do something but not break the app.

THE JSON FILE:

[
    {
        "id": 53,
        "date": "2018-12-28T08:51:11",
        "title": {
            "rendered": "this is for featured"
        },
        "content": {
            "rendered": "\n<p><g class=\"gr_ gr_3 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling\" id=\"3\" data-gr-id=\"3\">sdafkj</g> <g class=\"gr_ gr_10 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling ins-del multiReplace\" id=\"10\" data-gr-id=\"10\">kj</g> <g class=\"gr_ gr_16 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling ins-del multiReplace\" id=\"16\" data-gr-id=\"16\">asd</g> <g class=\"gr_ gr_18 gr-alert gr_spell gr_inline_cards gr_run_anim ContextualSpelling\" id=\"18\" data-gr-id=\"18\">kadjsfk</g> kljadfklj sd</p>\n",
            "protected": false
        },
        "excerpt": {
            "rendered": "<p>sdafkj kj asd kadjsfk kljadfklj sd</p>\n",
            "protected": false
        },
        "author": 1,
        "featured_media": 54,
        "_links": {
            "self": [
                {
                    "href": "https://client.kurd.app/wp-json/wp/v2/posts/53"
                }
            ],

        },
        "_embedded": {
            "author": [
                {
                    "id": 1,
                    "name": "hooshyar",

                }
            ],
            "wp:featuredmedia": [
                {
                    "id": 54,

                    "source_url": "https://client.kurd.app/wp-content/uploads/2018/12/icannotknow_22_12_2018_18_48_11_430.jpg",
                    }
                    ]
}
]

CODE FOR MAPPING TO OBJECT:

  featuredMediaUrl = map ["_embedded"]["wp:featuredmedia"][0]["source_url"];

The method 'map' was called on null. Receiver: null [0] which sometimes returns null ;

解决方案

Following my comment I suggest you to use a code generation library to parse JSON to JSON Models.

Read this article that explain you how to use (for example) the json_serializable package.

Such libraries takes all the dirty job of generate all the boilerplate code to create your Model classes and they take care of null values as mandatory or not.

For example if you annotate a class Person like that:

@JsonSerializable(nullable: true)
class Person {
  final String firstName;
  final String lastName;
  final DateTime dateOfBirth;
  Person({this.firstName, this.lastName, this.dateOfBirth});
  factory Person.fromJson(Map<String, dynamic> json) => _$PersonFromJson(json);
  Map<String, dynamic> toJson() => _$PersonToJson(this);
}

with (nullable: true) the dart class of your model will skip the null value fields.

UPDATE

Because I'm eager of technology I've given quicktype tool (suggested by Christoph Lachenicht) a try with your example.

I've prepared a mock api and a file example.json providing the JSON you've posted. I've taken only one element, not the array. And you can have a look here example.json.

After installin QuickType I've generate the model class for this json:

quicktype --lang dart --all-properties-optional example.json -o example.dart

Pay attention here to tha cli parameter --all-properties-optional that create null checks for missing fields.

Map<String, dynamic> toJson() => {
    "id": id == null ? null : id,
    "date": date == null ? null : date,
    "title": title == null ? null : title.toJson(),
    "content": content == null ? null : content.toJson(),
    "excerpt": excerpt == null ? null : excerpt.toJson(),
    "author": author == null ? null : author,
    "featured_media": featuredMedia == null ? null : featuredMedia,
    "_links": links == null ? null : links.toJson(),
    "_embedded": embedded == null ? null : embedded.toJson(),
};

Then I've used the Example class in example.dart

var jsonExampleResponse =
    await http.get('https://www.shadowsheep.it/so/53962129/testjson.php');
print(jsonExampleResponse.body);

var exampleClass = exampleFromJson(jsonExampleResponse.body);
print(exampleClass.toJson());

And all went fine.

N.B. Of course when you use this class you have to check if its fields are empty before using them:

print(exampleClass.embedded?.wpFeaturedmedia?.toString());

That's all. I hope to have put you in the rigth direction.

这篇关于映射嵌套JSON时如何检查NULL?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆