如果其中包含特定值,则将JSON元素更新为NULL

时间:2019-03-05 07:41:08

标签: java json spring-boot jackson

我有一个看起来像JSON的

{
 "person": {
  "name":"Sam", 
  "surname":"ngonma"
 },
 "car": {
  "make":"toyota", 
  "model":"yaris"
 }
}

我通过以下几行将其写到Amazon SQS,

ObjectMapper mObjectMapper = new ObjectMapper();
sqsExtended.sendMessage(new SendMessageRequest(awsSQSUrl, mObjectMapper.writeValueAsString(claim)));

我有一个单独的值数组,如果JSON在该数组中有其值,则必须将该字段写为null

如果我的字符串数组为["Sam", "Toyota"],则我的最终JSON应该如下所示,

{
 "person": {
  "name":null, 
  "surname":"ngonma"
 },
 "car": {
  "make":null, 
  "model":"yaris"
 }
}

字符串数组已外部化。将来可能还会有其他价值。有人可以建议我一个很好的链接或想法来解决这个问题吗?

1 个答案:

答案 0 :(得分:0)

我想出的最灵活的方法是使用Jackson的JsonAnyGetter注释。它允许您为Jackson提供Map的pojo状态的表示。从Map过滤值可以以迭代方式完成。可以递归的方式从包含Map的{​​{1}}中过滤值。

这是我根据提供的问题构建的解决方案

Map

测试方法

public class Claim {
    Map<String, Object> properties = new HashMap<>();

    public Claim() {
        // may be populated from instance variables
        Map<String, String> person = new HashMap<>();
        person.put("name", "Sam");
        person.put("surname", "ngonma");
        properties.put("person", person);
        Map<String, String> car = new HashMap<>();
        car.put("make", "Toyota");
        car.put("model", "yaris");
        properties.put("car", car);
    }

    // nullify map values based on provided array
    public void filterProperties (String[] nullifyValues) {
        filterProperties(properties, nullifyValues);
    }

    // nullify map values of provided map based on provided array
    @SuppressWarnings("unchecked")
    private void filterProperties (Map<String, Object> properties, String[] nullifyValues) {
        // iterate all String-typed values
        // if value found in array arg, nullify it
        // (we iterate on keys so that we can put a new value)
        properties.keySet().stream()
            .filter(key -> properties.get(key) instanceof String)
            .filter(key -> Arrays.asList(nullifyValues).contains(properties.get(key)))
            .forEach(key -> properties.put(key, null));
        // iterate all Map-typed values
        // call this method on value
        properties.values().stream()
            .filter(value -> value instanceof Map)
            .forEach(value -> filterProperties((Map<String, Object>)value, nullifyValues));
    }

    // provide jackson with Map of all properties
    @JsonAnyGetter
    public Map<String, Object> getProperties() {
        return properties;
    }
}

输出

public static void main(String[] args) { try { ObjectMapper mapper = new ObjectMapper(); Claim claim = new Claim(); claim.filterProperties(new String[]{"Sam", "Toyota"}); System.out.println(mapper.writeValueAsString(claim)); } catch (Exception e) { e.printStackTrace(); } }