Отображение объекта на подкласс с помощью JacksonXML - PullRequest
0 голосов
/ 25 декабря 2018

У меня проблемы с отображением объекта строки JSON на подкласс в Java.У меня есть класс Message, который содержит MessageType и String с содержанием сообщения.

public class Message {
    protected MessageType messageType;
    protected String content;

    public MessageType getMessageType() {
        return messageType;
    }

    public String getContent() {
        return content;
    }

    public void setMessageType(MessageType messageType) {
        this.messageType = messageType;
    }

    public void setContent(String content) {
        this.content = content;
    }
}

Существует также специальный вид сообщения, это сообщение содержит дополнительную переменную.Я сделал это сообщение подклассом Message класса:

public class QuestionMessage extends Message {

    private Question question;

    public QuestionMessage() {

    }

    public Question getQuestion() {
        return question;
    }

    public void setQuestion(Question question) {
        this.question = question;
    }
}

Где класс вопроса определяется как:

public class Question {
    private String question;
    private String answerA;
    private String answerB;
    private String answerC;
    private String correctAnswer;

    //Getters and setters down here.
}

Где-то еще в моем коде я получаю строку JSON иЯ использую ObjectMapper Джексона для сопоставления этой строки с классом Message:

objectMapper.readValue(jsonString, Message.class);

Теперь иногда строка JSON является обычным сообщением, например:

{"messageType":"NORMAL","content":"Content string"}

Эта строка JSONуспешно сопоставляется с классом Message и возвращает объект Message.Однако, когда мой код получает специальное сообщение, такое как:

{"messageType":"NEW_QUESTION", "content":"Content String","question":{"question":"123","answerA":"123","answerB":"123","answerC":"123"}}

К сожалению, мой код не может отобразить последнее сообщение json в класс QuestionMessage.Возможно ли с помощью JacksonXML отобразить на подкласс (QuestionMessage) класса (Message.class), который вы передаете объектному картографу?

Или это невозможно, и мне сначала нужно найти входящий jsonстрока для узла «вопрос», а затем специально вызывать:

objectMapper.readValue(jsonString, QuestionMessage.class);

вместо

objectMapper.readValue(jsonString, Message.class);

1 Ответ

0 голосов
/ 25 декабря 2018

Вы можете настроить Deserializer, который проверяет, существует ли question узел или нет.

Для примера:

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.deser.std.StdDeserializer;

import java.io.IOException;

public class MessageDeserializer extends StdDeserializer<Message> {

    public MessageDeserializer() {
        this(null);
    }

    public MessageDeserializer(Class<?> vc) {
        super(vc);
    }

    @Override
    public Message deserialize(JsonParser jp, DeserializationContext ctxt)
            throws IOException, JsonProcessingException {
        JsonNode node = jp.getCodec().readTree(jp);
        JsonNode questionNode = node.findValue("question");

        if (questionNode != null) {
            Question questionMessage = new Question();
                ...
            return questionMessage;
        } else {
            Message message = new Message();
                ...
            return message;
        }
    }
}

И использовать его:

ObjectMapper mapper = new ObjectMapper();
SimpleModule module = new SimpleModule();
module.addDeserializer(Message.class, new MessageDeserializer());
mapper.registerModule(module);

Message readValue = mapper.readValue(json, Message.class);

Проверьте здесь для более подробной информации.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...