繁体   English   中英

从JSON转换为XML XSD有效(使用Apache Camel或Java)

[英]Convert from JSON to XML XSD-valid (with Apache Camel or Java)

我有一条骆驼路线,可将文档从JSON转换为XML; 对于在XSD中定义的架构,XML必须有效。 目前,转换是使用camel-xmljson完成的 (并且我对列表类型进行了一些自定义的Java处理)。

唯一不匹配架构的是元素顺序,因为转换将顺序更改为字母顺序,因为每个定义的JSON都不关心顺序。 由于需要转换多个可能更改的文档类型,因此转换和后续处理应尽可能通用是很重要的(我希望它仅适用于XSD文件,而不适用于从XSD生成的类)。

因此,我正在寻找一种从JSON和XSD转换为有效XML的方法,或者一种更改XML元素顺序以匹配XSD定义的方法。 有人可以指出吗?

JSON并不关心对象(键-值对)中的顺序,但它关注数组中的顺序,因此也许您应该在顺序重要的地方使用JSON数组。 无论如何,您可以使用标准XSLT 3.0进行这种JSON / XML转换,该标准引入了JSON到XML和XML到JSON转换的功能。 在Java中, SAXON XSLT库从v9.7开始支持它们 (包括免费版本在内的所有版本)。

这是XSLT样式表的摘录,其中应用了从JSON输入( 链接到完整XSLT )的转换:

<xsl:stylesheet version="3.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xpath-default-namespace="http://www.w3.org/2005/xpath-functions" expand-text="yes"
    xmlns:my-prefix="urn:the:namespace:of:my:xsd">
    <!-- Reference example for JSON to XML transformation: https://www.saxonica.com/papers/xmlprague-2016mhk.pdf -->
    <!-- expand-text option allows to use text value templates in XSLT 3.0 -->
    <xsl:output encoding="UTF-8" indent="yes" method="xml" />

    <xsl:template name="xsl:initial-template">
        <xsl:apply-templates select="json-to-xml(.)" />
    </xsl:template>

<!-- This is just an example of applying a template when matching some key from JSON. --> 
    <xsl:template match="map[@key='key_of_something_to_change']">
        <!-- Fill in whith whatever transformation you want to apply in this case. Plenty of examples to change order of XML elements, such as:
         https://stackoverflow.com/questions/37442799/xslt-change-element-order
          -->
        ...
    </xsl:template>
...

</xsl:stylesheet>

然后,使用一些示例代码从Java使用该XSLT,假设您的类路径上是SAXON XSLT> = 9.7(此示例将输入JSON作为字符串并将结果输出到System.out,仅用于测试,但是您可以适应于处理其他类型SAXON API轻松实现输入/输出):

import net.sf.saxon.s9api.Processor;
import net.sf.saxon.s9api.SaxonApiException;
import net.sf.saxon.s9api.XdmAtomicValue;
import net.sf.saxon.s9api.Xslt30Transformer;
import net.sf.saxon.s9api.XsltExecutable;
import net.sf.saxon.trace.XSLTTraceListener;

...

    private static final XsltExecutable JSON_TO_XML_XSLT_EXEC;
    static
    {
        try
        {
            final Processor xsltProc = new Processor(false);
            JSON_TO_XML_XSLT_EXEC = xsltProc.newXsltCompiler().compile(new StreamSource(new File("/path/to/my/xslt/stylesheet/file"));
        }
        catch (final SaxonApiException e)
        {
            throw new RuntimeException("Cannot create XSLT processor for my stylesheet", e);
        }
   }

   private static void convertJsonToXml(final String inputJson, final Path outXmlFile)
    {
        final Xslt30Transformer xslt = JSON_TO_XML_XSLT_EXEC.load30();
        /*
         * Line below is useful for debugging, esp. to see what the output from the json-to-xml function looks like before further processing. Else remove it.
         */
        xslt.setTraceListener(new XSLTTraceListener());

        try
        {
            xslt.setGlobalContextItem(new XdmAtomicValue(inputJson));
            /*
             * Call default template "xsl:initial-template"
             */
            xslt.callTemplate(null, xslt.newSerializer(System.out));
        }
        catch (final SaxonApiException e)
        {
            throw new RuntimeException("Failed to apply XSLT", e);
        }
   }

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM