使用MOXy将JSON字符串解组为某些“对象”

时间:2015-01-12 16:17:43

标签: java json unmarshalling moxy

我正在尝试使用MOXy编写一个方法来打印JSON字符串。所以我想要的是拥有这样的方法

public String formatJson(String input) { ... }

我认为要采用的方法是将String解析为通用Object(类似于SAX-Document或类似的东西),然后使用一些格式化属性将此Object封送回JSON(这不是问题: - ))。

问题是,在读取JSON-String-Input时,我没有要解组的类(因为我希望方法尽可能通用)。

[已编辑] 删除了GSON和Jackson示例,因为只有MOXy才是问题。

我试过了:

public static String toFormattedJson(final String jsonString) {
    String formatted;
    try {
        JAXBContext jaxbContext = JAXBContextFactory.createContext(new Class[] { JAXBElement.class }, null);
        Unmarshaller unmarshaller = jaxbContext.createUnmarshaller();
        unmarshaller.setProperty(MEDIA_TYPE, MediaType.APPLICATION_JSON);
        unmarshaller.setProperty(JSON_INCLUDE_ROOT, true);
        StringReader reader = new StringReader(jsonString);
        Object element = unmarshaller.unmarshal(reader); // Exception is thrown here
        formatted = toFormattedJson(element);
    } catch (final JAXBException e) {
        formatted = jsonString;
    }
    return formatted;
}

但我得到了这个例外

javax.xml.bind.UnmarshalException   - 链接异常: [java.lang.ClassCastException:org.eclipse.persistence.internal.oxm.record.SAXUnmarshallerHandler无法强制转换为org.eclipse.persistence.internal.oxm.record.UnmarshalRecord]

那么,如果我没有针对该特定字符串的任何类,那么如何将任意JSON字符串读入Java对象?

更新: 这是用于将Object格式化为JSON字符串的方法:

private static String toFormattedJson(Object obj) {
    String result;
    try (StringWriter writer = new StringWriter()) {
        final JAXBContext jaxbContext = JAXBContextFactory.createContext(new Class[] { obj.getClass() }, null);
        final Marshaller marshaller = jaxbContext.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
        marshaller.setProperty(JAXBContextProperties.MEDIA_TYPE, MediaType.APPLICATION_JSON);
        marshaller.setProperty(MarshallerProperties.JSON_REDUCE_ANY_ARRAYS, false);
        marshaller.setProperty(MarshallerProperties.JSON_MARSHAL_EMPTY_COLLECTIONS, false);
        marshaller.setProperty(JAXBContextProperties.JSON_WRAPPER_AS_ARRAY_NAME, false);
        marshaller.setProperty(JAXBContextProperties.JSON_INCLUDE_ROOT, true);
        marshaller.marshal(obj, writer);
        writer.flush();
        result = writer.toString();
    } catch (JAXBException | IOException e) {
        result = obj.toString();
    }
    return result;
}

当我尝试格式化

时,现在使用下面的代码(Martin Vojtek)
String jsonString = "{\"p\" : [ 1, 2, 3]}";

我明白了:

{
   "p" : "1"
}

1 个答案:

答案 0 :(得分:2)

您可以将String指定为unmarshal目标:

public static void main(String[] args) {
        System.out.println(toFormattedJson("[{\"test\":true}, \"ok\", [\"inner\",1]]"));
}

public static String toFormattedJson(final String jsonString) {
    String formatted;
    try {
        JAXBContext jaxbContext = JAXBContextFactory.createContext(new Class[] { JAXBElement.class }, null);
        System.out.println("jaxbContext="+jaxbContext);
        Unmarshaller unmarshaller = jaxbContext.createUnmarshaller();
        unmarshaller.setProperty(JAXBContextProperties.MEDIA_TYPE, MediaType.APPLICATION_JSON);
        unmarshaller.setProperty(JAXBContextProperties.JSON_INCLUDE_ROOT, true);
        StringReader reader = new StringReader(jsonString);
        Object element = unmarshaller.unmarshal(new StreamSource(reader), String.class);
        formatted = toFormattedJsonElement(element);
    } catch (final JAXBException e) {
        e.printStackTrace();
        formatted = jsonString;
    }
    return formatted;
}

private static String toFormattedJsonElement(Object element) {
    return "formatted: " + element;
}