将文件夹中的多个 JSON 文件读取到地图中

Read multiple JSON files from a folder into a map

对于给定的文件夹路径,我想 load/transform 该文件夹中的所有 JSON 文件在一个映射中。

InputStream input = new ClassPathResource(jsonFile).getInputStream();
jsonMap = new ObjectMapper().readValue(input,
    new TypeReference<Map<String, MappedContacts>>() {});

我已经设法对单个文件执行此操作,但我不确定如何才能有效地对多个文件执行此操作。

您可以使用 @JsonMerge 注释告诉杰克逊您的 属性 值应该使用 "merging" 方法。

...其中首先访问当前值(使用 getter 或字段)然后修改 是否有传入数据:如果没有,则分配发生时不考虑当前状态

让我们看看例子, 假设您有 2 个(或更多)json 个文件:

contacts1.json

{
  "person1": {
    "contacts": [1,2]
  },
  "person2": {
    "contacts": []
  }
}

和contacts2.json

{
  "person1": {
    "contacts": [3,4]
  },
  "person2": {
    "contacts": [100]
  }
}

和你的MappedContacts

class MappedContacts {
        @JsonMerge
        List<Integer> contacts;

        public List<Integer> getContacts() {
            return contacts;
        }

        public void setContacts(List<Integer> contacts) {
            this.contacts = contacts;
        }

        @Override
        public String toString() {
            return contacts.toString();
        }
    }

然后测试它是否有效,只需简单的 hello jackson merge :

public static void main(String[] args) throws IOException {
    TypeReference<Map<String, MappedContacts>> type = new TypeReference<Map<String, MappedContacts>>() {};
    InputStream input = new ClassPathResource("contacts1.json").getInputStream();
    InputStream input2 = new ClassPathResource("contacts2.json").getInputStream();
    ObjectMapper mapper = new ObjectMapper();
    Object contacts = mapper.readValue(input, type);
    mapper.readerFor(type)
            .withValueToUpdate(contacts)
            .readValues(input2);

        System.out.println(contacts);
    }

输出

{a=[1, 2, 3, 4], b=[100]}

由于我使用的是 Spring,因此在使用 ObjectMapper 将每个资源转换为地图之前,使用 PathMatchingResourcePatternResolver 从文件夹中检索所有资源非常容易:

PathMatchingResourcePatternResolver resolver = new PathMatchingResourcePatternResolver(ConfigMapping.class.getClassLoader());

Resource[] resources = resolver.getResources("classpath*:/META-INF/resources/mapper/*");

for (Resource resource: resources) {
 InputStream input = resource.getInputStream();
 Map < String, MappedContacts> jsonMap = new ObjectMapper().readValue(input, new TypeReference < Map < String, MappedContacts>> () {});
 mapping.putAll(jsonMap);
}