Проверить JSON на соответствие схеме с Джексоном против внешнего файла схемы
Я хотел бы использовать библиотеку Джексона (https://github.com/FasterXML/jackson ) для работы с файлами JSON в Java, которые описываются файлом схемы JSON.
Теперь я хотел бы проверить, соответствует ли разбираемый JSON файлу схемы JSON, который разбирается сам по себе.
Существует модуль схемы JSON для Jackson (https://github.com/FasterXML/jackson-module-jsonSchema ). однако мне кажется, что его основное внимание сосредоточено на создании JSON файл схемы из Java.
Какой хороший способ проверки схемы JSON в Java? - желательно использовать Джексона, но я также открыт для других решений.
2 ответов:
Насколько я знаю, Джексон может только создавать схемы для заданных типов,но не выполнять проверку. Существует json-schema-validator, но он больше не поддерживается.
1.) Добавить зависимость пом.xml: -
<dependency> <groupId>com.github.fge</groupId> <artifactId>json-schema-validator</artifactId> <version>2.2.6</version> </dependency>2.) NoSqlEntity-это метаданные для сущности, которая может находиться в базе данных no-sql.
Инициализированный NoSqlEntity с файлом схемы.
Public static final nosqlentity entity = new NoSqlEntity ("PAYOUT_ENTITY","DB_", " /schema/payout_entity.json");
public class NoSqlEntity { private static final Map<String, NoSqlEntity> STORE = new HashMap<>(); private final AtomicLong seq = new AtomicLong(System.currentTimeMillis()); private IdentityGenerator identityGenerator; private String entity; private String collectionName; private String jsonSchema; private String idColumn = "id"; private String database; public NoSqlEntity(String entity, String idColumn, String collectionPrefix, String jsonSchema) { this.entity = entity; this.idColumn = idColumn; this.collectionName = collectionPrefix + "_" + entity; this.jsonSchema = jsonSchema; STORE.put(entity, this); } public NoSqlEntity(String collectionName, String jsonSchema) { this.collectionName = collectionName; this.jsonSchema = jsonSchema; } public static NoSqlEntity valueOf(String entityType) { return STORE.get(entityType); } public boolean isNotNullSchema() { return jsonSchema != null; } ... // Other Getter/Setter properties and methods. }3.) Пример формата файла схемы валидации payout_entity.json -
{ "properties":{ "txId":{"type":"string"} } "required" :["txId","currency"] }4.) JsonSchemaManager-проверяет входящую схему JSON и кэшируйте также и схему.
[5]}5.) NoSqlRepository, которые сохраняют метаданные в базе данных NoSql.public class JsonSchemaManager { private final static Logger LOGGER = LoggerFactory.getLogger(JsonSchemaManager.class); protected final static String LS = StandardSystemProperty.LINE_SEPARATOR.value(); private final JsonValidator validator = JsonSchemaFactory.byDefault().getValidator(); private final Map<NoSqlEntity, JsonNode> schemaMap = new HashMap<>(); public JsonNode load(NoSqlEntity noSqlEntity) throws IOException { final JsonNode schema = JsonLoader.fromURL(this.getClass().getResource(noSqlEntity.getJsonSchema())); schemaMap.put(noSqlEntity, schema); return schema; } public void validateSchema(NoSqlEntity noSqlEntity, JsonNode toBeValidated, Consumer<ProcessingReport> consumer) { try { JsonNode schema = schemaMap.get(noSqlEntity); if (schema == null) { schema = load(noSqlEntity); } final ProcessingReport report = validator.validate(schema, toBeValidated); if (!report.isSuccess()) { consumer.accept(report); } } catch (IOException ex) { //NOSONAR throw new InvalidRequestException(ex.toString()); } catch (ProcessingException ex) { //NOSONAR throw new InvalidRequestException(ex.toString()); } } public synchronized boolean synchronizedCheck(NoSqlEntity noSqlEntity, JsonNode toBeValidated, Consumer<Map<String, Object>> messageConsumers) { boolean flags = CommonUtils.unchecked(() -> { validateSchema(noSqlEntity, toBeValidated, report -> { report.forEach(processingMessage -> messageConsumers.accept(JsonConverter.jsonAsMapObject(processingMessage.asJson()))); }); return true; }, ex -> { throw new RuntimeException(ex.toString()); //NOSONAR }); return flags; } }@Component public class NoSqlRepository { private static final Logger LOGGER = LoggerFactory.getLogger(NoSqlRepository.class); private final DocumentFormat documentFormat = DocumentFormat.JSON; private static final String SEPARATOR = ","; private static final ThreadLocal<MyLocalVariable> THREAD_LOCAL_VARIABLES = ThreadLocal.withInitial(() -> new MyLocalVariable()); static class MyLocalVariable { private JsonSchemaManager schemaManager = new JsonSchemaManager(); private BasicBSONDecoder bsonDecoder = new BasicBSONDecoder(); public JsonSchemaManager getSchemaManager() { return schemaManager; } public BasicBSONDecoder getBsonDecoder() { return bsonDecoder; } } private void checkSchemaIfAny(NoSqlEntity noSqlEntity, JsonNode entity) { if (noSqlEntity.isNotNullSchema()) { THREAD_LOCAL_VARIABLES.get().getSchemaManager().check(noSqlEntity, entity); } } public String saveEntity(NoSqlEntity noSqlEntity, JsonNode entity){ // Before persisting payload into noSQL, validate payload against schema. this.checkSchemaIfAny(noSqlEntity,entity); } // Other CURD methods here... }
Comments