如何在Meteor后端解析XML?

yim*_*mmy 5 xml parsing backend meteor

我正在尝试在后端使用HTTP调用解析XML,其中主体是XML.问题是我们不能在后端使用Jquery或DOMParser来解析.我们试图先在前端解析它,然后将它作为变量发送到meteor方法(在后端),但它太大(超过最大堆栈).我们还尝试添加节点模块来执行此操作,但它无法正常工作.

我们怎样才能在Meteor的后端获得解析的XML对象?

Wra*_*ing 10

首先,您需要安装几个软件包.

  1. HTTP,因此您可以"获取"外部XML
  2. xml2js,因此您可以在XML出现后解析它

像这样安装并重启服务器:

meteor add http peerlibrary:xml2js && meteor
Run Code Online (Sandbox Code Playgroud)

其次,构建服务器端功能.它不一定是Meteor方法,但是对于这个例子,我会将它放在一个中,这样我们就可以轻松地解决它.使用HTTP.call()或HTTP.get()发出请求.然后是URL; 我将使用示例XML文件.然后是后URL参数; 就我而言,没有.然后是回调函数.

Meteor.methods({
    'xmlDemo':function(){
        HTTP.call('GET',
            'http://www.xmlfiles.com/examples/plant_catalog.xml',
            {},
            function(callError,callResponse){
                console.log('xml',callResponse);
            }
        );
    }
});
Run Code Online (Sandbox Code Playgroud)

如果您是Meteor的新手,请首先在回调函数中特别注意"error"参数.

第三,尝试该方法.这就像一场电话游戏.

  1. 客户端调用流星服务器. Meteor.call('xmlDemo');
  2. 流星服务器调用外部URL.

如果一切顺利,该方法将读取文件内容,并在服务器的控制台上显示输出.(即看看你运行"流星"的终端)

{ statusCode: 200,
content: '<?xml version="1.0" encoding="ISO8859-1" ?>\r\n<CATALOG>\r\n
(et cetera...)
(et cetera...)
(et cetera...)',
headers:
 { 'content-type': 'text/xml',
   'last-modified': 'Tue, 24 Apr 2012 21:06:45 GMT',
   'accept-ranges': 'bytes',
   etag: '"80a095275e22cd1:0"',
   server: 'Microsoft-IIS/7.5',
   'x-powered-by': 'ASP.NET',
   date: 'Mon, 30 Nov 2015 19:17:26 GMT',
   'content-length': '8167' },
data: null }
Run Code Online (Sandbox Code Playgroud)

这里看到的最重要的事情是来自HTTP.call的响应是一个对象."content"字段保存实际数据.(这是我个人被绊倒的地方.)

第四,尝试将XML字符串传递给xml2js.

Meteor.methods({
    'xmlDemo':function(){
        HTTP.call('GET',
            'http://www.xmlfiles.com/examples/plant_catalog.xml',
            {},
            function(callError,callResponse){
                //console.log('xml',callResponse);
                xml2js.parseString(callResponse.content, function (jsError, jsResult) {
                    console.error('errors',jsError);
                    console.log('xml to js',jsResult);
                });
            }
        );
    }
});
Run Code Online (Sandbox Code Playgroud)

再一次,运气好的话,你会看到植物作为终端打印出来的物体.您现在要做的就是获取对象数组,遍历它,并将内容存储到集合中.Underscore让它变得简单(它内置于Meteor)

_.each(jsResult.CATALOG.PLANT,function(plant){
    Plants.insert(plant);
}
Run Code Online (Sandbox Code Playgroud)

最后,您将添加几个故障保险箱来报告错误.另外xml2js开箱即用并不一定能很好地收集集合的工作方式.您需要设置一些选项.

  • explicitArray:false(默认情况下,<this>example</this>会变成一个标签{this:["example"]}.在Mongo中,这被认为是一个嵌入式文档,你会遇到麻烦.)
  • emptyTag:undefined(默认情况下,<this/>会变成一个空标签{this:''}.就个人而言,我觉得让空的东西不存在更容易,检查它们是否存在,而不是检查它们是否存在并且实际上有内容)

清理完我自己的一些代码后,这是最后一个例子

在/lib/file.js上...

Plants = new Mongo.Collection('plants');
Run Code Online (Sandbox Code Playgroud)

在/server/file.js上...

Meteor.methods({
    'xmlDemo':function(){
        HTTP.get('http://www.xmlfiles.com/examples/plant_catalog.xml',{},
            function(xmlError,xmlResponse){
                if(xmlError){
                    console.error('xmlError',xmlError);
                }else{
                    xml2js.parseString(xmlResponse.content, {explicitArray:false, emptyTag:undefined}, function (jsError, jsResult) {
                    if(jsError){
                        console.error('xml2js error',jsError);
                    }else{
                        _.each(jsResult.CATALOG.PLANT,function(plant){
                            Plants.insert(plant);
                        }
                    }
                });
            }
        );
    }
});
Run Code Online (Sandbox Code Playgroud)


kjh*_*hes 1

我们尝试添加一个节点模块来执行此操作,但它无法正常工作。

您可能因不兼容的依赖关系而陷入困境。

尝试node-xml2js,它只需要sax.js,它只需要 JavaScript。