Java/Android - проверка строки JSON по строковой схеме - программирование
Подтвердить что ты не робот

Java/Android - проверка строки JSON по строковой схеме

У меня возникли проблемы с поиском самого простого способа проверки строки JSON для данной строки JSON-схемы (для справки, это в Java, работающей в приложении для Android).

В идеале, я бы хотел просто передать строку JSON String и строку JSON-схемы, и он возвращает логическое значение относительно того, проходит ли он проверку. Через поиск я нашел следующие 2 многообещающие библиотеки для этого:

http://jsontools.berlios.de/

https://github.com/fge/json-schema-validator

Однако первый из них выглядит довольно устаревшим с плохой поддержкой. Я реализовал библиотеку в своем проекте и даже с помощью своих JavaDocs, я не смог сказать, как правильно построить объект "Validator" для проверки.

Аналогичная история со вторым, которая, кажется, актуальна с хорошим тестовым кодом. Однако для того, что я хочу сделать, что очень просто, кажется немного сложным и запутанным в том, как конкретно выполнить то, что я хочу (даже после просмотра ValidateServlet.java).

Любопытно, есть ли у кого-нибудь другие предложения по хорошему способу выполнить это (от того, что кажется), простая задача, которая нужна, или если мне, возможно, придется придерживаться второго варианта сверху? Спасибо заранее!

4b9b3361

Ответ 1

Это, по сути, то, с чем вы связались с сервлетами, поэтому он не может быть однострочным, но он все же является выразительным.

useV4 и useId, как указано на сервлете, предназначены для указания опции проверки для Default to draft v4 и Use id for addressing.

Вы можете увидеть его онлайн: http://json-schema-validator.herokuapp.com/

public boolean validate(String jsonData, String jsonSchema, boolean useV4, boolean useId) throws Exception {
   // create the Json nodes for schema and data
   JsonNode schemaNode = JsonLoader.fromString(jsonSchema); // throws JsonProcessingException if error
   JsonNode data = JsonLoader.fromString(jsonData);         // same here

   JsonSchemaFactory factory = JsonSchemaFactories.withOptions(useV4, useId);
   // load the schema and validate
   JsonSchema schema = factory.fromSchema(schemaNode);
   ValidationReport report = schema.validate(data);

   return report.isSuccess();
}

Ответ 2

Благодарю вас за Дугласа Крокфорда и Фрэнсиса Галиге за то, что он написал java-схему java-схемы! И он-лайн тестер на http://json-schema-validator.herokuapp.com/index.jsp является потрясающим! Мне очень нравятся полезные сообщения об ошибках (я нашел только один пример, в котором они не выполнялись), хотя строка и столбец и/или контекст будут еще лучше (прямо сейчас вы получаете информацию о строках и столбцах во время ошибок формата JSON (любезно предоставлено Jackson ) Наконец, я хотел бы поблагодарить Майкла Дроттбума за его большой учебник (даже если он только покрыл Python, Ruby и C, в то же время игнорируя лучший язык всех: -)).

Для тех, кто пропустил это (как и раньше), есть примеры в github.com/fge/json-schema-processor-examples. Хотя эти примеры очень впечатляют, они не являются простыми примерами проверки json, которые первоначально запрашивались (и которые я тоже искал). Простые примеры приведены на странице github.com/fge/json-schema-validator/blob/master/src/main/java/com/github/fge/jsonschema/examples/Example1.java

Код Alex выше не работал у меня, но был очень полезным; мой pom вытаскивает последний стабильный релиз версии 2.0.1 со следующей зависимостью, вставленной в мой файл maven pom.xml:

<dependency>
    <groupId>com.github.fge</groupId>
    <artifactId>json-schema-validator</artifactId>
    <version>2.0.1</version>
</dependency>

Тогда следующий код java отлично работает для меня:

import java.io.IOException;
import java.util.Iterator;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.JsonNode;
import com.github.fge.jsonschema.exceptions.ProcessingException;
import com.github.fge.jsonschema.main.JsonSchema;
import com.github.fge.jsonschema.main.JsonSchemaFactory;
import com.github.fge.jsonschema.report.ProcessingMessage;
import com.github.fge.jsonschema.report.ProcessingReport;
import com.github.fge.jsonschema.util.JsonLoader;


public class JsonValidationExample  
{

public boolean validate(String jsonData, String jsonSchema) {
    ProcessingReport report = null;
    boolean result = false;
    try {
        System.out.println("Applying schema: @<@<"+jsonSchema+">@>@ to data: #<#<"+jsonData+">#>#");
        JsonNode schemaNode = JsonLoader.fromString(jsonSchema);
        JsonNode data = JsonLoader.fromString(jsonData);         
        JsonSchemaFactory factory = JsonSchemaFactory.byDefault(); 
        JsonSchema schema = factory.getJsonSchema(schemaNode);
        report = schema.validate(data);
    } catch (JsonParseException jpex) {
        System.out.println("Error. Something went wrong trying to parse json data: #<#<"+jsonData+
                ">#># or json schema: @<@<"+jsonSchema+">@>@. Are the double quotes included? "+jpex.getMessage());
        //jpex.printStackTrace();
    } catch (ProcessingException pex) {  
        System.out.println("Error. Something went wrong trying to process json data: #<#<"+jsonData+
                ">#># with json schema: @<@<"+jsonSchema+">@>@ "+pex.getMessage());
        //pex.printStackTrace();
    } catch (IOException e) {
        System.out.println("Error. Something went wrong trying to read json data: #<#<"+jsonData+
                ">#># or json schema: @<@<"+jsonSchema+">@>@");
        //e.printStackTrace();
    }
    if (report != null) {
        Iterator<ProcessingMessage> iter = report.iterator();
        while (iter.hasNext()) {
            ProcessingMessage pm = iter.next();
            System.out.println("Processing Message: "+pm.getMessage());
        }
        result = report.isSuccess();
    }
    System.out.println(" Result=" +result);
    return result;
}

public static void main(String[] args)
{
    System.out.println( "Starting Json Validation." );
    JsonValidationExample app = new JsonValidationExample();
    String jsonData = "\"Redemption\"";
    String jsonSchema = "{ \"type\": \"string\", \"minLength\": 2, \"maxLength\": 11}";
    app.validate(jsonData, jsonSchema);
    jsonData = "Agony";  // Quotes not included
    app.validate(jsonData, jsonSchema);
    jsonData = "42";
    app.validate(jsonData, jsonSchema);
    jsonData = "\"A\"";
    app.validate(jsonData, jsonSchema);
    jsonData = "\"The pity of Bilbo may rule the fate of many.\"";
    app.validate(jsonData, jsonSchema);
}

}

Мой результат из приведенного выше кода:

Starting Json Validation.
Applying schema: @<@<{ "type": "string", "minLength": 2, "maxLength": 11}>@>@ to data: #<#<"Redemption">#>#
 Result=true
Applying schema: @<@<{ "type": "string", "minLength": 2, "maxLength": 11}>@>@ to data: #<#<Agony>#>#
Error. Something went wrong trying to parse json data: #<#<Agony>#># or json schema: @<@<{ "type": "string", "minLength": 2, "maxLength": 11}>@>@. Are the double quotes included?
 Result=false
Applying schema: @<@<{ "type": "string", "minLength": 2, "maxLength": 11}>@>@ to data: #<#<42>#>#
Processing Message: instance type does not match any allowed primitive type
 Result=false
Applying schema: @<@<{ "type": "string", "minLength": 2, "maxLength": 11}>@>@ to data: #<#<"A">#>#
Processing Message: string is too short
 Result=false
Applying schema: @<@<{ "type": "string", "minLength": 2, "maxLength": 11}>@>@ to data: #<#<"The pity of Bilbo may rule the fate of many.">#>#
Processing Message: string is too long
 Result=false

Наслаждайтесь!

Ответ 3

Ответ на

@Alex работал у меня на Android, но мне потребовалось Multi-dex и добавить:

    packagingOptions {
        pickFirst 'META-INF/ASL-2.0.txt'
        pickFirst 'draftv4/schema'
        pickFirst 'draftv3/schema'
        pickFirst 'META-INF/LICENSE'
        pickFirst 'META-INF/LGPL-3.0.txt'
    }

на мой build.gradle