当前位置:龙哥网 > 网络技术 > Jackson2的JsonSchema实现java实体类生成json方式_java

Jackson2的JsonSchema实现java实体类生成json方式_java

longge3个月前 (03-01)网络技术41
目录
  • 核心工具类
  • 怎么使用
    • 测试用的实体类
  • 用法
    • 转换结果

      除Swagger等文档插件,全网首发,同时支持Json和Xml

      核心工具类

      Json2Utils.java

      package com.xxx.demo.common.util;
      import java.io.IOException;
      import java.util.Arrays;
      import java.util.Iterator;
      import java.util.Map;
      import java.util.Map.Entry;
      import com.fasterxml.jackson.annotation.JsonInclude.Include;
      import com.fasterxml.jackson.core.JsonGenerator;
      import com.fasterxml.jackson.core.JsonProcessingException;
      import com.fasterxml.jackson.core.type.TypeReference;
      import com.fasterxml.jackson.databind.JavaType;
      import com.fasterxml.jackson.databind.JsonNode;
      import com.fasterxml.jackson.databind.JsonSerializer;
      import com.fasterxml.jackson.databind.ObjectMapper;
      import com.fasterxml.jackson.databind.SerializerProvider;
      import com.fasterxml.jackson.databind.node.ArrayNode;
      import com.fasterxml.jackson.databind.node.NullNode;
      import com.fasterxml.jackson.databind.node.ObjectNode;
      import com.fasterxml.jackson.dataformat.xml.XmlMapper;
      import com.fasterxml.jackson.dataformat.xml.ser.XmlSerializerProvider;
      import com.fasterxml.jackson.dataformat.xml.util.XmlRootNameLookup;
      import com.kjetland.jackson.jsonSchema.JsonSchemaConfig;
      import com.kjetland.jackson.jsonSchema.JsonSchemaGenerator;
      public final class Json2Utils {
       
       //数组或List的循环次数
       private static final int ARRAY_LOOP = 1; 
       //Map的循环次数
       private static final int MAP_LOOP = 1; 
       //Map的key的前缀
       private static final String MAP_KEY_PREFIX = "KEY_"; 
       private static final ObjectMapper innerMapper = new ObjectMapper(); 
       private static final XmlSerializerProvider provider = new XmlSerializerProvider(new XmlRootNameLookup()); 
       static {
        provider.setNullValueSerializer(new JsonSerializer<Object> () {   
         @Override
         public void serialize(Object value, JsonGenerator gen, SerializerProvider serializers)
           throws IOException {
          gen.writeString("");
         }   
        });
       }
       
       /**
        * 普通java类转json字符串
        * @param <T>
        * @param mapper
        * @param clazz
        * @return
        */
       public static <T> String clazz2Json(ObjectMapper mapper, Class<T> clazz) {
        JavaType javaType = mapper.getTypeFactory().constructType(clazz);
        return javaType2Json(mapper, javaType);
       }
       
       /**
        * 泛型java类转json字符串
        * @param <T>
        * @param mapper
        * @param reference
        * @return
        */
       public static <T> String clazz2Json(ObjectMapper mapper, TypeReference<T> reference) {
        JavaType javaType = mapper.getTypeFactory().constructType(reference);
        return javaType2Json(mapper, javaType);
       }
       private static String javaType2Json(ObjectMapper mapperSource, JavaType javaType) {
        ObjectMapper mapper = mapperSource.copy();
        ObjectMapper innerMapper = Json2Utils.innerMapper;
        JsonSchemaConfig config = JsonSchemaConfig.vanillaJsonSchemaDraft4();
        JsonSchemaGenerator schemaGenerator = new JsonSchemaGenerator(innerMapper, config);
        JsonNode jsonNode = schemaGenerator.generateJsonSchema(javaType);
        JsonNode normalize = normalize(innerMapper, jsonNode);
        Object value = innerMapper.convertValue(normalize, javaType);
        mapper.setDefaultPropertyInclusion(Include.ALWAYS);
        if (mapper instanceof XmlMapper) {
         mapper.setSerializerProvider(provider);
        }
        try {
         return mapper.writerWithDefaultPrettyPrinter().writeValueAsString(value);
        } catch (JsonProcessingException e) {
         return null;
        }
       }
       
       private static JsonNode normalize(ObjectMapper mapper, JsonNode source) {
        if (shouldArray(source)) {
         ArrayNode arrayNode = mapper.createArrayNode();
         fillJsonNode(mapper, source, source, arrayNode);
         return arrayNode;
        } else if (shouldObject(source)) {
         ObjectNode objectNode = mapper.createObjectNode();
         fillJsonNode(mapper, source, source, objectNode);
         return objectNode;
        }
        return NullNode.getInstance();  
       }
       
       private static void fillJsonNode(ObjectMapper mapper, JsonNode sourceRoot, JsonNode source, JsonNode target) {
        if (isArray(source)) {
         for (int i = 0; i < ARRAY_LOOP; i++) {
          fillArrayNode(mapper, sourceRoot, source, target);
         }
        } else if (shouldObject(source)) {
         fillObjectNode(mapper, sourceRoot, source, target);
        }
       }
       private static void fillArrayNode(ObjectMapper mapper, JsonNode sourceRoot, JsonNode source, JsonNode target) {
        JsonNode arrayItems = getArrayItems(source);
        if (isArray(arrayItems)) {
         ArrayNode arrayNode = mapper.createArrayNode();
         ((ArrayNode) target).add(arrayNode);
         fillJsonNode(mapper, sourceRoot, arrayItems, arrayNode);
        } else if (isMap(arrayItems)) {
         JsonNode propertiesNode = arrayItems.get("additionalProperties");
         if (isPojoPlain(propertiesNode)) {
          ObjectNode objectNode = mapper.createObjectNode();
          ((ArrayNode) target).add(objectNode);
          fillJsonNode(mapper, sourceRoot, arrayItems, objectNode);
         } else {
          ((ArrayNode) target).add(NullNode.getInstance());
         }
        } else if (isPojoPlain(arrayItems)) {
         JsonNode jsonNode = sourceRoot.at(arrayItems.get("$ref").asText().substring(1));
         ObjectNode objectNode = mapper.createObjectNode();
         ((ArrayNode) target).add(objectNode);
         fillJsonNode(mapper, sourceRoot, jsonNode, objectNode);
        } else {
         ((ArrayNode) target).add(NullNode.getInstance());
        }
       }
       private static void fillObjectNode(ObjectMapper mapper, JsonNode sourceRoot, JsonNode source, JsonNode target) {
        if (isMap(source)) {
         for (int i = 0; i < MAP_LOOP; i++) {
          fillMapNode(mapper, sourceRoot, source, target, i);
         }
        } else if (source.has("properties")) {
         Iterator<Entry<String, JsonNode>> iterator = source.get("properties").fields();
         while (iterator.hasNext()) {
          Map.Entry<String, JsonNode> entry = iterator.next();
          JsonNode jsonNode = entry.getValue();
          if (shouldArray(jsonNode)) {
           ArrayNode arrayNode = mapper.createArrayNode();
           ((ObjectNode) target).set(entry.getKey(), arrayNode);
           fillJsonNode(mapper, sourceRoot, jsonNode, arrayNode);
          } else if (shouldObject(jsonNode)) {
           ObjectNode objectNode = mapper.createObjectNode();
           ((ObjectNode) target).set(entry.getKey(), objectNode);
           fillJsonNode(mapper, sourceRoot, jsonNode, objectNode);
          } else {
           ((ObjectNode) target).set(entry.getKey(), NullNode.getInstance());
          }    
         }
        }
       }
       
       private static void fillMapNode(ObjectMapper mapper, JsonNode sourceRoot, JsonNode source, JsonNode target, int i) {
        String keyName = MAP_KEY_PREFIX + i;
        JsonNode propertiesNode = source.get("additionalProperties");
        if (isArray(propertiesNode)) {
         ArrayNode arrayNode = mapper.createArrayNode();
         ((ObjectNode) target).set(keyName, arrayNode);
         fillJsonNode(mapper, sourceRoot, propertiesNode, arrayNode);
        } else if (isMap(propertiesNode)) {
         ObjectNode objectNode = mapper.createObjectNode();
         ((ObjectNode) target).set(keyName, objectNode);
         fillJsonNode(mapper, sourceRoot, propertiesNode, objectNode);
        } else if (isPojoPlain(propertiesNode)) {
         JsonNode jsonNode = sourceRoot.at(propertiesNode.get("$ref").asText().substring(1));
         ObjectNode objectNode = mapper.createObjectNode();
         ((ObjectNode) target).set(keyName, objectNode);
         fillJsonNode(mapper, sourceRoot, jsonNode, objectNode);
        } else {
         ((ObjectNode) target).set(keyName, NullNode.getInstance());
        }
       }
       private static boolean isArray(JsonNode jsonNode) {
        if (!jsonNode.has("type")) {
         return false;
        }
        return "array".equals(jsonNode.get("type").asText());
       }
       
       private static boolean isMap(JsonNode jsonNode) {
        if (!jsonNode.has("type")) {
         return false;
        }
        return "object".equals(jsonNode.get("type").asText()) && !jsonNode.get("additionalProperties").isBoolean();
       }
       
       private static boolean isPojoRoot(JsonNode jsonNode) {
        return "object".equals(jsonNode.get("type").asText()) && jsonNode.get("additionalProperties").isBoolean()
          && !Arrays.asList("Local Date Time", "Local Date", "Local Time", "Offset Date Time").contains(jsonNode.get("title").asText());
       }
       
       private static boolean isPojoPlain(JsonNode jsonNode) {
        if (jsonNode.has("properties")) {
         return true;
        }
        if (!jsonNode.has("$ref")) {
         return false;
        }
        String ref = jsonNode.get("$ref").asText();
        return !ref.endsWith("LocalDateTime") && !ref.endsWith("LocalDate") && !ref.endsWith("LocalTime") && !ref.endsWith("OffsetDateTime");
       }
       
       private static boolean shouldArray(JsonNode jsonNode) {
        return isArray(jsonNode);
       }
       
       private static boolean shouldObject(JsonNode jsonNode) {
        if (isMap(jsonNode)) {
         return true;
        }
        if (jsonNode.has("title") && isPojoRoot(jsonNode)) {
         return true;
        }
        if (!jsonNode.has("title") && isPojoPlain(jsonNode)) {
         return true;
        }
        return false;
       }
       
       private static JsonNode getArrayItems(JsonNode source) {
        return source.get("items");
       }
      }
      

      怎么使用

      测试用的实体类

      Base.java

      package com.xxx.demo.common.jsontest;
      import java.util.Arrays;
      public class Base<T> {
       private String address; 
       private T[] listDt; 
       public String getAddress() {
        return address;
       }
       public void setAddress(String address) {
        this.address = address;
       }
       public T[] getListDt() {
        return listDt;
       }
       public void setListDt(T[] listDt) {
        this.listDt = listDt;
       }
       @Override
       public String toString() {
        return "Base [address=" + address + ", listDt=" + Arrays.toString(listDt) + "]";
       }
      }
      

      BaseDt.java

      package com.xxx.demo.common.jsontest;
      import java.math.BigInteger;
      import java.time.LocalDate;
      import java.util.Date;
      import java.util.List;
      
      public class BaseDt {
       private Integer bst; 
       private Date dt; 
       private BigInteger bg; 
       private int nt; 
       private Short sht;
       private Long lng; 
       private Byte bt;
       
       @JacksonXmlCData
       private char chr; 
       private boolean bln; 
       private float flt; 
       private double dbl; 
       private LocalDate ld; 
       private List<String> testStr; 
       private Score score;
       public Integer getBst() {
        return bst;
       }
       public void setBst(Integer bst) {
        this.bst = bst;
       }
       public Date getDt() {
        return dt;
       }
       public void setDt(Date dt) {
        this.dt = dt;
       }
       public BigInteger getBg() {
        return bg;
       }
       public void setBg(BigInteger bg) {
        this.bg = bg;
       }
       public int getNt() {
        return nt;
       }
       public void setNt(int nt) {
        this.nt = nt;
       }
       public Short getSht() {
        return sht;
       }
       public void setSht(Short sht) {
        this.sht = sht;
       }
       public Long getLng() {
        return lng;
       }
       public void setLng(Long lng) {
        this.lng = lng;
       }
       public Byte getBt() {
        return bt;
       }
       public void setBt(Byte bt) {
        this.bt = bt;
       }
       public char getChr() {
        return chr;
       }
       public void setChr(char chr) {
        this.chr = chr;
       }
       public boolean isBln() {
        return bln;
       }
       public void setBln(boolean bln) {
        this.bln = bln;
       }
       public float getFlt() {
        return flt;
       }
       public void setFlt(float flt) {
        this.flt = flt;
       }
       public double getDbl() {
        return dbl;
       }
       public void setDbl(double dbl) {
        this.dbl = dbl;
       }
       public LocalDate getLd() {
        return ld;
       }
       public void setLd(LocalDate ld) {
        this.ld = ld;
       }
       public List<String> getTestStr() {
        return testStr;
       }
       public void setTestStr(List<String> testStr) {
        this.testStr = testStr;
       }
       public Score getScore() {
        return score;
       }
       public void setScore(Score score) {
        this.score = score;
       }
       @Override
       public String toString() {
        return "BaseDt [bst=" + bst + ", dt=" + dt + ", bg=" + bg + ", nt=" + nt + ", sht=" + sht + ", lng=" + lng
          + ", bt=" + bt + ", chr=" + chr + ", bln=" + bln + ", flt=" + flt + ", dbl=" + dbl + ", ld=" + ld
          + ", testStr=" + testStr + ", score=" + score + "]";
       } 
      }

      Score.java

      package com.xxx.demo.common.jsontest;
      import java.math.BigDecimal;
      public class Score {
       private BigDecimal langue; 
       private BigDecimal math; 
       private BigDecimal english;
       public BigDecimal getLangue() {
        return langue;
       }
       public void setLangue(BigDecimal langue) {
        this.langue = langue;
       }
       public BigDecimal getMath() {
        return math;
       }
       public void setMath(BigDecimal math) {
        this.math = math;
       }
       public BigDecimal getEnglish() {
        return english;
       }
       public void setEnglish(BigDecimal english) {
        this.english = english;
       }
       @Override
       public String toString() {
        return "Score [langue=" + langue + ", math=" + math + ", english=" + english + "]";
       }
      }
      

      TestMap.java

      package com.xxx.demo.common.jsontest;
      import java.util.List;
      public class TestMap {
       private List<String> mapList;
       public List<String> getMapList() {
        return mapList;
       }
       public void setMapList(List<String> mapList) {
        this.mapList = mapList;
       }
       @Override
       public String toString() {
        return "TestMap [mapList=" + mapList + "]";
       }
      }
      

      Student.java

      package com.xxx.demo.common.jsontest;
      import java.time.LocalDateTime;
      import java.time.LocalTime;
      import java.util.List;
      import java.util.Map;
      
      public class Student<T, E> extends Base<BaseDt> {
       private String userName;
       private Integer age;
       private String phone; 
       private LocalDateTime accessTime; 
       private LocalTime localTime; 
       private Score score; 
       private List<T> grades; 
       private Map<String, E> mapLt; 
       private Map<String, String> mapStr; 
       private Map<String, LocalDateTime> mapLocal; 
       private List<Map<String, Score>> lscoreList1; 
       private List<List<Map<String, Score>>> lscoreList2; 
       private Map<String, Map<String, Map<String, Score>>> mapScore; 
       private Map<String, List<Score>> mapList;
       public String getUserName() {
        return userName;
       }
       public void setUserName(String userName) {
        this.userName = userName;
       }
       public Integer getage() {
        return age;
       }
       public void setAge(Integer age) {
        this.age = age;
       }
       public String getPhone() {
        return phone;
       }
       public void setPhone(String phone) {
        this.phone = phone;
       }
       public LocalDateTime getAccessTime() {
        return accessTime;
       }
       public void setAccessTime(LocalDateTime accessTime) {
        this.accessTime = accessTime;
       }
       public List<T> getGrades() {
        return grades;
       }
       public void setGrades(List<T> grades) {
        this.grades = grades;
       }
       public Map<String, E> getMapLt() {
        return mapLt;
       }
       public void setMapLt(Map<String, E> mapLt) {
        this.mapLt = mapLt;
       }
       public Map<String, String> getMapStr() {
        return mapStr;
       }
       public void setMapStr(Map<String, String> mapStr) {
        this.mapStr = mapStr;
       }
       public Map<String, LocalDateTime> getMapLocal() {
        return mapLocal;
       }
       public void setMapLocal(Map<String, LocalDateTime> mapLocal) {
        this.mapLocal = mapLocal;
       }
       public LocalTime getLocalTime() {
        return localTime;
       }
       public void setLocalTime(LocalTime localTime) {
        this.localTime = localTime;
       }
       public Score getScore() {
        return score;
       }
       public void setScore(Score score) {
        this.score = score;
       }
       public List<Map<String, Score>> getLscoreList1() {
        return lscoreList1;
       }
       public void setLscoreList1(List<Map<String, Score>> lscoreList1) {
        this.lscoreList1 = lscoreList1;
       }
       public List<List<Map<String, Score>>> getLscoreList2() {
        return lscoreList2;
       }
       public void setLscoreList2(List<List<Map<String, Score>>> lscoreList2) {
        this.lscoreList2 = lscoreList2;
       }
       public Map<String, Map<String, Map<String, Score>>> getMapScore() {
        return mapScore;
       }
       public void setMapScore(Map<String, Map<String, Map<String, Score>>> mapScore) {
        this.mapScore = mapScore;
       }
       public Map<String, List<Score>> getMapList() {
        return mapList;
       }
       public void setMapList(Map<String, List<Score>> mapList) {
        this.mapList = mapList;
       }
       @Override
       public String toString() {
        return "Student [userName=" + userName + ", age=" + age + ", phone=" + phone + ", accessTime=" + accessTime
          + ", localTime=" + localTime + ", score=" + score + ", grades=" + grades + ", mapLt=" + mapLt
          + ", mapStr=" + mapStr + ", mapLocal=" + mapLocal + ", lscoreList1=" + lscoreList1 + ", lscoreList2="
          + lscoreList2 + ", mapScore=" + mapScore + ", mapList=" + mapList + "]";
       } 
      }
      

      用法

      JsonUtils类转Springboot2以代码的方式统一配置Jackson->Jackson工具类

      package com.xxx.demo.common.jsontest;
      import java.util.List;
      import com.fasterxml.jackson.core.type.TypeReference;
      import com.fasterxml.jackson.databind.ObjectMapper;
      import com.xxx.demo.common.util.Json2Utils;
      import com.xxx.demo.common.util.JsonUtils;
      import com.xxx.demo.common.util.XmlUtils;
      public class Json2Test { 
       public static void main(String[] args) {
        ObjectMapper mapper1 = JsonUtils.getObjectMapper();
        String json = Json2Utils.clazz2Json(mapper1, new TypeReference<List<List<Student<Score, TestMap>>>>() {});
        System.out.println(json);
        ObjectMapper mapper2 = XmlUtils.getObjectMapper();
        String xml = Json2Utils.clazz2Json(mapper2, new TypeReference<Student<Score, TestMap>>() {});
        System.out.println(xml);
       }
      }
      

      转换结果

      [ [ {
      "address" : null,
      "listDt" : [ {
      "bst" : null,
      "dt" : null,
      "bg" : null,
      "nt" : 0,
      "sht" : null,
      "lng" : null,
      "bt" : null,
      "chr" : "\u0000",
      "bln" : false,
      "flt" : 0.0,
      "dbl" : 0.0,
      "ld" : null,
      "testStr" : [ null ],
      "score" : {
      "langue" : null,
      "math" : null,
      "english" : null
      }
      } ],
      "userName" : null,
      "age" : null,
      "phone" : null,
      "accessTime" : null,
      "localTime" : null,
      "score" : {
      "langue" : null,
      "math" : null,
      "english" : null
      },
      "mapLt" : {
      "KEY_0" : {
      "mapList" : [ null ]
      }
      },
      "mapStr" : {
      "KEY_0" : null
      },
      "mapLocal" : {
      "KEY_0" : null
      },
      "lscoreList1" : [ {
      "KEY_0" : {
      "langue" : null,
      "math" : null,
      "english" : null
      }
      } ],
      "lscoreList2" : [ [ {
      "KEY_0" : {
      "langue" : null,
      "math" : null,
      "english" : null
      }
      } ] ],
      "mapScore" : {
      "KEY_0" : {
      "KEY_0" : {
      "KEY_0" : {
      "langue" : null,
      "math" : null,
      "english" : null
      }
      }
      }
      },
      "mapList" : {
      "KEY_0" : [ {
      "langue" : null,
      "math" : null,
      "english" : null
      } ]
      },
      "gg" : [ {
      "langue" : null,
      "math" : null,
      "english" : null
      } ]
      } ] ]

      <Student>
        <address></address>
        <listDt>
          <listDt>
            <bst></bst>
            <dt></dt>
            <bg></bg>
            <nt>0</nt>
            <sht></sht>
            <lng></lng>
            <bt></bt>
            <chr><![CDATA[ ]]></chr>
            <bln>false</bln>
            <flt>0.0</flt>
            <dbl>0.0</dbl>
            <ld></ld>
            <testStr>
              <testStr></testStr>
            </testStr>
            <score>
              <langue></langue>
              <math></math>
              <english></english>
            </score>
          </listDt>
        </listDt>
        <userName></userName>
        <age></age>
        <phone></phone>
        <accessTime></accessTime>
        <localTime></localTime>
        <score>
          <langue></langue>
          <math></math>
          <english></english>
        </score>
        <mapLt>
          <KEY_0>
            <mapList>
              <mapList></mapList>
            </mapList>
          </KEY_0>
        </mapLt>
        <mapStr>
          <KEY_0></KEY_0>
        </mapStr>
        <mapLocal>
          <KEY_0></KEY_0>
        </mapLocal>
        <lscoreList1>
          <lscoreList1>
            <KEY_0>
              <langue></langue>
              <math></math>
              <english></english>
            </KEY_0>
          </lscoreList1>
        </lscoreList1>
        <lscoreList2>
          <lscoreList2>
            <KEY_0>
              <langue></langue>
              <math></math>
              <english></english>
            </KEY_0>
          </lscoreList2>
        </lscoreList2>
        <mapScore>
          <KEY_0>
            <KEY_0>
              <KEY_0>
                <langue></langue>
                <math></math>
                <english></english>
              </KEY_0>
            </KEY_0>
          </KEY_0>
        </mapScore>
        <mapList>
          <KEY_0>
            <langue></langue>
            <math></math>
            <english></english>
          </KEY_0>
        </mapList>
        <gg>
          <gg>
            <langue></langue>
            <math></math>
            <english></english>
          </gg>
        </gg>
      </Student>
      免责声明
      本站部分资源来源于互联网 如有侵权 请联系站长删除
      龙哥网是优质的互联网科技创业资源_行业项目分享_网络知识引流变现方法的平台为广大网友提供学习互联网相关知识_内容变现的方法。#转载请注明出处!