Java 如何使用XSLT/XSL将基于属性的xml转换为json并忽略特定元素的属性

Java 如何使用XSLT/XSL将基于属性的xml转换为json并忽略特定元素的属性,java,xml,xslt,dom,xls,Java,Xml,Xslt,Dom,Xls,我相信我的问题提供了一个很好的想法,我正在尝试做什么。顺便说一句,在下面找到传入的xml和所需的json输出 我在这里找到了一个关于如何从xml转换为json的极好答案,但我的xml有点不同。请注意,下面的值是属性的一部分。另外,我想忽略c:item中的属性。换句话说,必须忽略cod和包装。我知道如何将这种基于属性的xml转换为基于元素值的另一种xml,然后将这种新xml转换为json格式,但在我看来,第一步(从xml转换为另一种xml)有点奇怪,因为我只需要json。我知道从xml到xml,多

我相信我的问题提供了一个很好的想法,我正在尝试做什么。顺便说一句,在下面找到传入的xml和所需的json输出

我在这里找到了一个关于如何从xml转换为json的极好答案,但我的xml有点不同。请注意,下面的值是属性的一部分。另外,我想忽略c:item中的属性。换句话说,必须忽略cod和包装。我知道如何将这种基于属性的xml转换为基于元素值的另一种xml,然后将这种新xml转换为json格式,但在我看来,第一步(从xml转换为另一种xml)有点奇怪,因为我只需要json。我知道从xml到xml,多亏了这里提供的优秀答案

传入xml

<c:product xmlns:c="myapp">
       <c:item cod="789">
              <c:aa name="024" value="123"/>
              <c:bbb name="0105" value="123456"/>
              <c:bbb name="0122" value="T"/>
              <c:aa name="071" value="00000001"/>
       </c:item>
       <c:item package="123" cod="11111">
              <c:aa name="002" value="753"/>
              <c:aa name="003" value="456"/>
              <c:bbb name="0146" value="147852"/>
       </c:item>
</c:product>
****7月31日编辑

基于Michael Kay答案的输出:

"aa" : {"024":"123"}"bbb" : {"0105":"123456"}"bbb" : {"0122":"T"}"aa" : {"071":"00000001"}"aa" : {"002":"753"}"aa" : {"003":"456"}"bbb" : {"0146":"147852"}
XLS基于Michael Kay答案使用,并生成上述结果

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:c="myapp" exclude-result-prefixes="c">
<xsl:output method="xml" omit-xml-declaration="yes" version="1.0" encoding="utf-8" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="c:item/*">
  <xsl:text>"</xsl:text>
  <xsl:value-of select="local-name()"/>
  <xsl:text>" : {"</xsl:text>
  <xsl:value-of select="@name"/>
  <xsl:text>":"</xsl:text>
  <xsl:value-of select="@value"/>
  <xsl:text>"}</xsl:text>
</xsl:template>
</xsl:stylesheet>

"
" : {"
":"
"}

<c:aa name="024" value="123"/>
完全是琐碎的:只是

<xsl:template match="c:item/*">
  <xsl:text>"</xsl:text>
  <xsl:value-of select="local-name()"/>
  <xsl:text>" : {"</xsl:text>
  <xsl:value-of select="@name"/>
  <xsl:text>":"</xsl:text>
  <xsl:value-of select="@value"/>
  <xsl:text>"}</xsl:text>
</xsl:template>

"
" : {"
":"
"}

我不太明白您为什么会遇到问题。

您显示的XSLT是正确的,但是您缺少一些东西

  • 没有处理
    c:item
    自身的模板来包装
    {}
  • 不向单独的对象输出逗号和换行符
  • 不处理根元素
    c:product
    来创建子数组(因此您拥有有效的JSON)
  • 试试这个XSLT

    <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"  version="1.0" 
                    xmlns:c="myapp" exclude-result-prefixes="c">
    <xsl:output method="text"/>
    <xsl:strip-space elements="*"/>
    
    <xsl:template match="*[c:item]">
        <xsl:text>[&#10;</xsl:text>
        <xsl:apply-templates select="c:item"/>
        <xsl:text>]&#10;</xsl:text>
    </xsl:template>
    
    <xsl:template match="c:item">
        <xsl:text>  {&#10;</xsl:text>
            <xsl:apply-templates />
        <xsl:text>  }</xsl:text>
        <xsl:if test="following-sibling::c:item">
            <xsl:text>,</xsl:text>
        </xsl:if>
        <xsl:text>&#10;</xsl:text>
    </xsl:template>
    
    <xsl:template match="c:item/*">
            <xsl:text>    "</xsl:text>
            <xsl:value-of select="local-name()" />
            <xsl:text>" : {"</xsl:text>
            <xsl:value-of select="@name" />
            <xsl:text>":"</xsl:text><xsl:value-of select="@value" />
            <xsl:text>"}</xsl:text>
            <xsl:if test="following-sibling::*">
                <xsl:text>,</xsl:text>
            </xsl:if>
            <xsl:text>&#10;</xsl:text>
    </xsl:template>
    </xsl:stylesheet>
    
    这实际上与问题中所需的输出不匹配,但显示的输出实际上不是有效的JSON


    请参见

    “我相信我的问题提供了一个我正在尝试做的好主意。”-这取决于读者的判断。请注意,您实际上并没有问任何问题(除了标题…之类的)。你还可以在拼写、语法、标点和一般可读性方面做得更好。(依我看,别再胡说八道了,为什么你认为你的问题是个好问题,集中精力把它变成一个好问题。)斯蒂芬,如果我在标题中问了一个问题,那么我确实问了一个问题。我已经在这里读过好几次了,有人开始和我的问题类似,这是我第一次看到有人抱怨。我在哪里告诉你我做了一个好问题?我告诉别人,有人给了我上一个问题一个很好的答案(完全符合你的意思)。关于拼写和语法,不幸的是英语不是我的母语,我总是尽我最大的努力避免英语错误,但我不知道你们说的是哪个错误。最后,我的问题到底出了什么问题?任何浪费>>读者期望的“JSON”的问题,从两个大括号开始
    {{
    根本不是有效的JSON。正确,这是一个输入错误。Michael,谢谢你的回答,但我肯定错过了你回答的任何部分,或者你希望我已经知道的xls的一些基本想法。请注意,我尝试了你的建议,但首先,我没有得到有效的JSON,其次我是“混合”请复制我的输入xml并根据您的xls建议运行,您将看到我无法区分是“aa”还是“bbb”属于第一项,哪个属于最后一项。我想在转换过程中删除cod和package属性,但我自然不想让第一项与第二项混淆,因为您仍然将XSL拼写为“xls”你对这门语言非常陌生,很难知道如何回答初学者提出的问题,因为我们不知道你知道多少。用教程回答一个问题是不可能或不合适的,在我看来,给出一个复杂的工作解决方案也是不合适的,因为我认为你你需要自己解决这个问题:一个好的SO问题的关键是它集中在一个你被卡住的关键领域,很难从你的问题中看出你的拦截器在哪里。迈克尔,我对这个话题很谦虚,我很感谢你帮助我的努力。蒂姆C,你完美地回答了我的疑问。我只想做一点小小的调整在这个xsl中,wans最初并没有要求这样做。因为,在我的现实世界中,我发现aa总是两位数代码(例如99),bbb总是三位数代码(例如999)。我知道我可以拥有一个没有“aa”和“bbb”的有效json文件。我该怎么做?我在这里提出了一个新问题,带着这个特定的疑问
    <c:aa name="024" value="123"/>
    
    "aa" : {"024":"123"}
    
    <xsl:template match="c:item/*">
      <xsl:text>"</xsl:text>
      <xsl:value-of select="local-name()"/>
      <xsl:text>" : {"</xsl:text>
      <xsl:value-of select="@name"/>
      <xsl:text>":"</xsl:text>
      <xsl:value-of select="@value"/>
      <xsl:text>"}</xsl:text>
    </xsl:template>
    
    <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"  version="1.0" 
                    xmlns:c="myapp" exclude-result-prefixes="c">
    <xsl:output method="text"/>
    <xsl:strip-space elements="*"/>
    
    <xsl:template match="*[c:item]">
        <xsl:text>[&#10;</xsl:text>
        <xsl:apply-templates select="c:item"/>
        <xsl:text>]&#10;</xsl:text>
    </xsl:template>
    
    <xsl:template match="c:item">
        <xsl:text>  {&#10;</xsl:text>
            <xsl:apply-templates />
        <xsl:text>  }</xsl:text>
        <xsl:if test="following-sibling::c:item">
            <xsl:text>,</xsl:text>
        </xsl:if>
        <xsl:text>&#10;</xsl:text>
    </xsl:template>
    
    <xsl:template match="c:item/*">
            <xsl:text>    "</xsl:text>
            <xsl:value-of select="local-name()" />
            <xsl:text>" : {"</xsl:text>
            <xsl:value-of select="@name" />
            <xsl:text>":"</xsl:text><xsl:value-of select="@value" />
            <xsl:text>"}</xsl:text>
            <xsl:if test="following-sibling::*">
                <xsl:text>,</xsl:text>
            </xsl:if>
            <xsl:text>&#10;</xsl:text>
    </xsl:template>
    </xsl:stylesheet>
    
    <c:product xmlns:c="myapp">
           <c:item cod="789">
                  <c:aa name="024" value="123"/>
                  <c:bbb name="0105" value="123456"/>
                  <c:bbb name="0122" value="T"/>
                  <c:aa name="071" value="00000001"/>
           </c:item>
           <c:item package="123" cod="11111">
                  <c:aa name="002" value="753"/>
                  <c:aa name="003" value="456"/>
                  <c:bbb name="0146" value="147852"/>
           </c:item>
    </c:product>
    
    [
      {
        "aa" : {"024":"123"},
        "bbb" : {"0105":"123456"},
        "bbb" : {"0122":"T"},
        "aa" : {"071":"00000001"}
      },
      {
        "aa" : {"002":"753"},
        "aa" : {"003":"456"},
        "bbb" : {"0146":"147852"}
      }
    ]