处理来自 JsonReader 的空指针

Handling Null Pointers from JsonReader

我正在使用 JsonReader 从网站获取大量数据并保存到数据库。顺便说一下,只要 reader 没有找到对象项的值,它就会失败并停止执行。

这是我的错误;

System.err﹕ java.lang.IllegalStateException: Expected a string but was NULL at line 1 column 359337 path $[19].date

即使指定的值不可用,在遇到错误之前加载的所有对象似乎也丢失了并且没有保存到数据库中。有没有办法处理这些错误并保留到目前为止已加载的对象?我已将 JsonReader 设置为宽松。

这是方法中解析数据的部分:

private Post read(JsonReader reader) throws Exception {
            reader.beginObject();

            while (reader.hasNext()) {
                String name = reader.nextName();

                switch (name) {
                    case TITLE:
                        mTitle = new StringBuilder();
                        mTitle.append(reader.nextString());
                        break;
                    case AUTHOR:
                        if (reader.hasNext()) {
                            JsonToken peek = reader.peek();

                            if (peek == JsonToken.NULL) {
                                reader.skipValue();
                            } else {
                                reader.beginObject();

                                while (reader.hasNext()) {
                                    String enclosedName = reader.nextName();

                                    switch (enclosedName) {
                                        case NAME:
                                            mAuthor = new StringBuilder();
                                            mAuthor.append(reader.nextString());
                                            break;
                                        case AVATAR:
                                            mAvatar = new StringBuilder();
                                            mAvatar.append(reader.nextString());
                                            break;
                                        default:
                                            reader.skipValue();
                                            break;
                                    }
                                }

                                reader.endObject();
                            }
                        }
                        break;
                    case CONTENT:
                        mDescription = new StringBuilder();
                        mDescription.append(reader.nextString());
                        break;
                    case URL:
                        mEntryLink = new StringBuilder();
                        mEntryLink.append(reader.nextString());
                        break;
                    case DATE:
                        mDateStringBuilder = new StringBuilder();
                        mDateStringBuilder.append(reader.nextString());
                        break;
                    case GUID:
                        mGuid = new StringBuilder();
                        mGuid.append(reader.nextString());
                        break;
                    case FEATURED_IMAGE:
                        if (reader.hasNext()) {
                            JsonToken look = reader.peek();

                            if (look == JsonToken.NULL) {
                                reader.skipValue();
                            } else {
                                mFeaturedImage = new StringBuilder();
                                reader.beginObject();

                                while (reader.hasNext()) {
                                    String itemToLookFor = reader.nextName();

                                    switch (itemToLookFor) {
                                        case SOURCE:
                                            mFeaturedImage.append(reader.nextString());
                                            break;
                                        default:
                                            reader.skipValue();
                                            break;
                                    }
                                }

                                reader.endObject();
                            }
                        }
                        break;
                    case TERMS:
                        if (reader.hasNext()) {
                            JsonToken check = reader.peek();

                            if (check == JsonToken.NULL) {
                                reader.skipValue();
                            } else {
                                reader.beginObject();

                                while (reader.hasNext()) {
                                    String stuff = reader.nextName();

                                    switch (stuff) {
                                        case CATEGORIES:
                                            reader.beginArray();

                                            itemCategory = new StringBuilder();

                                            while (reader.hasNext()) {
                                                reader.beginObject();

                                                while (reader.hasNext()) {
                                                    String item = reader.nextName();

                                                    switch (item) {
                                                        case NAME:
                                                            itemCategory.append(reader.nextString()).append(",");
                                                            break;
                                                        default:
                                                            reader.skipValue();
                                                            break;
                                                    }
                                                }

                                                reader.endObject();
                                            }
                                            reader.endArray();
                                            break;
                                        case TAGS:
                                            reader.beginArray();

                                            itemTags = new StringBuilder();

                                            while (reader.hasNext()) {
                                                reader.beginObject();

                                                while (reader.hasNext()) {
                                                    String item = reader.nextName();

                                                    switch (item) {
                                                        case NAME:
                                                            itemTags.append(reader.nextString()).append(",");
                                                            break;
                                                        default:
                                                            reader.skipValue();
                                                            break;
                                                    }
                                                }

                                                reader.endObject();
                                            }
                                            reader.endArray();
                                            break;
                                        default:
                                            reader.skipValue();
                                            break;
                                    }
                                }

                                reader.endObject();
                            }
                        }
                        break;
                    default:
                        reader.skipValue();
                        break;
                }
            }

            reader.endObject();

            return new Post(mAuthor.toString(), mAvatar.toString(), mDateStringBuilder.toString(), mTitle.toString(), mEntryLink.toString(), mDescription.toString(), mGuid.toString(), mFeaturedImage.toString(), itemTags.toString(), itemCategory.toString());
        }

我认为您可能没有检查 NULL 元素,情况似乎是这样。

您曾经使用过:

JsonToken check = reader.peek();

if (check == JsonToken.NULL) {

没错。但是,在其他地方,您只需获得 String:

mDescription.append(reader.nextString());

在所有得到 String 的地方,您需要检查是否确实存在意外类型(例如 NULL)。在这种情况下,您需要应用适当的错误遏制代码。

顺便说一句,您真的不需要创建所有这些 StringBuilder。因为每次初始化后您只将一个 String 放入其中。只需使用 String 即可节省大量时间。如果你打算把每个类型的所有内容写入一个StringBuilder,那么你需要在开始循环之前初始化它们。