How to iterate through an Json array with same keys, but different values using Faster xml

半城伤御伤魂 提交于 2020-01-15 09:03:29

问题


  1. I am trying to parse the json array with same key value which looks something like:
Back End Response:"Countries":[{"state":"Queens Land "state":"Tasmania"}].

2.I have created classes to read back end response and mapping the values with faster XML, but only the last value in the array is getting copied, instead of entire array. This is how I created my Data Transfer Object classes.

Now the Test object contains Countries array, but only one of the State value is read. i.e

"Countries":["States":"Tasmania"].

Please excuse me for typos. can some one help, can some one suggest whats wrong with the bellow code..

private Class Test{
  List<Countries> countries;
}

private class Countries{        
  private String States;
}

private class Mapper {

}

In my Mapper class reading the value using faster XML


回答1:


Assume that your JSON payload is:

{
  "Countries": [
    {
      "state": "Queens Land",
      "state": "Tasmania"
    }
  ]
}

According to RFC7159:

An object structure is represented as a pair of curly brackets surrounding zero or more name/value pairs (or members). A name is a string. A single colon comes after each name, separating the name from the value. A single comma separates a value from a following name. The names within an object SHOULD be unique.

In your example, you have not unique names and most JSON parsers would skip repeated values and would take only one. So, if you can change backend response, just change it to:

{
  "Countries": [
    {
      "state": "Queens Land"
    },
    {
      "state": "Tasmania"
    }
  ]
}

or

{
  "Countries": [
    "Queens Land",
    "Tasmania"
  ]
}

But if you can not do that, you need to use Streaming API and implement your custom deserialiser. See below example:

import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.core.JsonToken;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonDeserializer;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

public class JsonPathApp {

    public static void main(String[] args) throws Exception {
        File jsonFile = new File("./resource/test.json").getAbsoluteFile();

        ObjectMapper mapper = new ObjectMapper();
        Test test = mapper.readValue(jsonFile, Test.class);
        System.out.println(test);
    }
}

class CountriesJsonDeserializer extends JsonDeserializer<Countries> {

    @Override
    public Countries deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
        List<String> states = new ArrayList<>();
        while (p.nextToken() != JsonToken.END_OBJECT) {
            if (p.currentToken() == JsonToken.FIELD_NAME) {
                if ("state".equalsIgnoreCase(p.getText())) {
                    p.nextToken();
                    states.add(p.getText());
                }
            }
        }

        Countries countries = new Countries();
        countries.setStates(states);
        return countries;
    }
}

class Test {

    @JsonProperty("Countries")
    private List<Countries> countries;

    public List<Countries> getCountries() {
        return countries;
    }

    public void setCountries(List<Countries> countries) {
        this.countries = countries;
    }

    @Override
    public String toString() {
        return "Test{" +
                "countries=" + countries +
                '}';
    }
}

@JsonDeserialize(using = CountriesJsonDeserializer.class)
class Countries {
    private List<String> states;

    public List<String> getStates() {
        return states;
    }

    public void setStates(List<String> states) {
        this.states = states;
    }

    @Override
    public String toString() {
        return "Countries{" +
                "states=" + states +
                '}';
    }
}

Above example prints:

Test{countries=[Countries{states=[Queens Land, Tasmania]}]}

See also:

  • Intro to the Jackson ObjectMapper


来源:https://stackoverflow.com/questions/58151124/how-to-iterate-through-an-json-array-with-same-keys-but-different-values-using

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!