2014-10-01 90 views
1

我有一个XML架构 -XML到JSON转换的问题

<?xml version="1.0" encoding="UTF-8"?> 

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns="http://www.tibco.com/schemas/RegTestingStub/SharedResources/SchemaDefinitions/CommonXSD/Schema.xsd2" 
    targetNamespace="http://www.tibco.com/schemas/RegTestingStub/SharedResources/SchemaDefinitions/CommonXSD/Schema.xsd2" 
    elementFormDefault="qualified" 
    attributeFormDefault="unqualified"> 
    <xs:element name="AccumulateResponse" type="AccumulateResponse"/> 
    <xs:complexType name="AccumulateResponse"> 
     <xs:sequence> 
      <xs:element name="TestCase" minOccurs="0" maxOccurs="unbounded"> 
       <xs:complexType> 
        <xs:sequence> 
         <xs:element name="Transactionid" type="xs:string"/> 
         <xs:element name="TransactionType" type="xs:string"/> 
         <xs:element name="Status" type="xs:string"/> 
        </xs:sequence> 
       </xs:complexType> 
      </xs:element> 
     </xs:sequence> 
    </xs:complexType> 
</xs:schema> 

我做这种转换我下面的步骤 - 1)生成Java从XML架构使用XJC 2类)编译使用Java类编译器API 3)通过JAXB解组类实例

但它们都是繁重的IO操作。有没有办法在内存中做到这一点?

回答

0

终于破解这件事 -

FOR XML到JSON的转换 -

  1. 解析XML架构(JAXB)和创建可被存储在存储器

  2. 对象验证XML相对于该架构对象创建

  3. 创建XML字符串WRT的实例对象的架构类

  4. 使用该实例来创建json字符串。

这样json字符串将具有数据类型,如架构规定的。例如。 - 在模式中定义的特定元素将作为json数组出现,即使它在xml中出现1(它不会被转换为json对象)。如果在模式中明确定义并且未隐式转换为整数,则值为123的元素将被解释为字符串。

如果有人想要它的代码联系我。

1

您可以使用http://www.xsd2xml.com/从xsd生成示例xml,然后您可以使用站点:http://www.utilities-online.info/xmltojson/将xml转换为json。

为了您的XSD,我得到了示例XML:

<?xml version="1.0" encoding="utf-8"?> 
<AccumulateResponse> 
    <TestCase> 
    <Transactionid>str1234</Transactionid> 
    <TransactionType>str1234</TransactionType> 
    <Status>str1234</Status> 
    </TestCase> 
    <TestCase> 
    <Transactionid>str5678</Transactionid> 
    <TransactionType>str5678</TransactionType> 
    <Status>str5678</Status> 
    </TestCase> 
</AccumulateResponse> 

而且使用我的第二个站点:

{ 
"AccumulateResponse": { 
    "TestCase": [ 
    { 
    "Transactionid": "str1234", 
    "TransactionType": "str1234", 
    "Status": "str1234" 
    }, 
    { 
    "Transactionid": "str5678", 
    "TransactionType": "str5678", 
    "Status": "str5678" 
    } 
    ] 
} 
} 
+0

尝试输入1234作为xsd中任何元素的值。您会注意到该元素的转换后的json变成了一个整数,并不是一个字符串。无论如何,我的要求是,我以编程的方式执行此操作...所以希望您可以指出我正确的方向! – 2014-10-02 13:05:05

+0

如果你想通过java编码,我建议使用库:gson [link](https://code.google.com/p/google-gson/)和JAXB。 gson可以帮助你将java obejcts转换成json。 JAXB将帮助您将XML更改为java obecjts(unmarshall)。 – Piotr 2014-10-03 07:20:59

+0

我想将xml转换为与模式相关的json,以便数据类型和JSON对象和数组与元素定义一致。请帮忙 – 2014-10-09 12:23:39

1

免责声明:我的Jsonix的作者,schema-驱动用于XML的JavaScript库< - > JS转换。

Jsonix似乎做你想要什么:

  • 您可以生成您的模式
  • 使用这种映射(JS)映射到您的JSON解组的XML到JSON
  • 名帅成XML

而且,正如你想的那样,Jsonix是型感知模式感知

类型感知意味着你会得到一个JSON字符串,你有xs:string和一个数字,你有xs:decimal等Jsonix支持几乎所有内置的XML模式类型(以及你自己的简单类型派生自内置-in类型)。

架构感知意味着您的JSON结构将严格基于您的XML架构的结构。你会得到阵列,你有一个可重复的元素,等等。

适用于浏览器以及Node.js,兼容AMD以及CJS环境。


好的,足够的话,让代码说话。

我们采取以下模式(我命名文件ar.xsd):

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns="urn:test" 
    targetNamespace="urn:test" 
    elementFormDefault="qualified" 
    attributeFormDefault="unqualified"> 
    <xs:element name="AccumulateResponse" type="AccumulateResponse"/> 
    <xs:complexType name="AccumulateResponse"> 
     <xs:sequence> 
      <xs:element name="TestCase" minOccurs="0" maxOccurs="unbounded"> 
       <xs:complexType> 
        <xs:sequence> 
         <xs:element name="TransactionId" type="xs:string"/> 
         <xs:element name="TransactionType" type="xs:string"/> 
         <xs:element name="Status" type="xs:string"/> 
        </xs:sequence> 
       </xs:complexType> 
      </xs:element> 
     </xs:sequence> 
    </xs:complexType> 
</xs:schema> 

(我只是修改一个元素名称和命名空间。)

我们首先使用Jsonix架构编译器生成的映射文件:

java -jar jsonix-schema-compiler-full.jar ar.xsd -p AR

我们从这个得到的是被称为AR.js映射文件定义XML-JSON映射。这是映射定义的样子:(有你在哪里得到非常短的名称,如en而不是elementName也是一个紧凑模式)

{ 
    name: 'AR', 
    defaultElementNamespaceURI: 'urn:test', 
    typeInfos: [{ 
     localName: 'AccumulateResponse', 
     propertyInfos: [{ 
      name: 'testCase', 
      collection: true, 
      elementName: 'TestCase', 
      typeInfo: '.AccumulateResponse.TestCase' 
      }] 
     }, { 
     localName: 'AccumulateResponse.TestCase', 
     propertyInfos: [{ 
      name: 'transactionId', 
      elementName: 'TransactionId' 
      }, { 
      name: 'transactionType', 
      elementName: 'TransactionType' 
      }, { 
      name: 'status', 
      elementName: 'Status' 
      }] 
     }], 
    elementInfos: [{ 
     elementName: 'AccumulateResponse', 
     typeInfo: '.AccumulateResponse' 
     }] 
    } 

下一页这里是一个XML样品测试(sample01.xml):

<?xml version="1.0" encoding="utf-8"?> 
<AccumulateResponse xmlns="urn:test"> 
    <TestCase> 
    <Transactionid>1234</Transactionid> 
    <TransactionType>5678</TransactionType> 
    <Status>Status01</Status> 
    </TestCase> 
    <TestCase> 
    <Transactionid>true</Transactionid> 
    <TransactionType>false</TransactionType> 
    <Status>Status02</Status> 
    </TestCase> 
</AccumulateResponse> 

下面是一个解组测试用例(ar-tests.js):

var Jsonix = require('jsonix').Jsonix; 
    var AR = require('../AR').AR; 

    // Create Jsonix context 
    var context = new Jsonix.Context([ AR ]); 

    // Create unmarshaller 
    var unmarshaller = context.createUnmarshaller(); 

    // Unmarshal the XML file 
    unmarshaller.unmarshalFile('tests/sample01.xml', 
     function(element) { 
      console.log(element.value); 
      test.equal('Status01', element.value.testCase[0].status); 
      test.done(); 
    }); 

而且这是你在控制台中看到:

{ TYPE_NAME: 'AR.AccumulateResponse', 
    testCase: 
    [ { TYPE_NAME: 'AR.AccumulateResponse.TestCase', 
     transactionType: '5678', 
     status: 'Status01' }, 
    { TYPE_NAME: 'AR.AccumulateResponse.TestCase', 
     transactionType: 'false', 
     status: 'Status02' } ] } 

编组站的工作方式相同。

该示例的完整代码可用here。它使用Node.js/nodeunit实现,但Jsonix也可以在浏览器中使用。 (你没有unarshalFile功能,但你可以做unmarshalStringunmarshalDocument等)

我会在稍后发布一个JSFiddle的例子。

几个环节: