Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

'preserveChildrenOrder' option not working #202

Open
Kandy16 opened this issue May 9, 2015 · 7 comments
Open

'preserveChildrenOrder' option not working #202

Kandy16 opened this issue May 9, 2015 · 7 comments

Comments

@Kandy16
Copy link

Kandy16 commented May 9, 2015

The input xml is as shown
<data>
<a>A</a>
<a>A</a>
<b>B</b>
<b>B</b>
<c>C</c>
<c>C</c>
<a>A</a>
<b>B</b>
<c>C</c>
</data>

and the output is
{ data:
{ a: [ 'A', 'A', 'A' ],
b: [ 'B', 'B', 'B' ],
c: [ 'C', 'C', 'C' ] } }

I saw that it will be available from 0.4.9 version. But the latest version available is 0.4.8. But I downloaded the code and tried the above input.

This feature is very important for me. Please let me know when this will be released

Thanks In Advance

@Leonidas-from-XIV
Copy link
Owner

You can just use the git version in the meantime and let me know if it works, which would help me to make sure I'm realeasing a 0.4.9 that actually works properly.

@slippyex
Copy link

Hi there,

Unfortunately it does not work with the current git version for my use case.
I have a somewhat similar problem as Kandy16 has.

Here's an example where you can reproduce the behavior.

var fs = require('fs'),
    xml2js = require('./xml2js');
var parser = new xml2js.Parser(
{
        preserveChildrenOrder: true,
        explicitArray: false,
        explicitChildren: true, 
        charkey: "content",
        attrkey: "props",
        childkey: "content",
        emptyTag: {}
    } 
);
parser.addListener('end', function(result) {
    console.dir(JSON.stringify(result));
});
fs.readFile(__dirname + '/tmp.xml', function(err, data) {
    parser.parseString(data);
});

The corresponding "tmp.xml" file is like

<A>
  <B>B1</B>
  <C>C1</C>
  <B>B2</B>
</A>

When I now set both, "explicitChildren" AND "preserveChildrenOrder" to true, it fails with this error message:

events.js:85
      throw er; // Unhandled 'error' event
            ^
TypeError: undefined is not a function
    at Object.onclosetag (/Users/me/workspaces/xml2js-git/xml2js.js:403:41)
    at emit (/Users/me/workspaces/xml2js-git/node_modules/sax/lib/sax.js:615:33)
    at emitNode (/Users/me/workspaces/xml2js-git/node_modules/sax/lib/sax.js:620:3)
    at closeTag (/Users/me/workspaces/xml2js-git/node_modules/sax/lib/sax.js:861:5)
    at Object.write (/Users/me/workspaces/xml2js-git/node_modules/sax/lib/sax.js:1294:29)
    at Parser.exports.Parser.Parser.parseString (/Users/me/workspaces/xml2js-git/xml2js.js:478:31)
    at Parser.parseString (/Users/me/workspaces/xml2js-git/xml2js.js:6:59)
    at /Users/me/workspaces/xml2js-git/test.js:20:12
    at fs.js:336:14
    at FSReqWrap.oncomplete (fs.js:99:15)

Thanks in advance.

ds82 added a commit to ds82/node-xml2js that referenced this issue Jun 26, 2015
@ds82
Copy link

ds82 commented Jun 26, 2015

I'm working on a fix for this. Would like to hear your opinions.
ds82/node-xml2js@4179b44

I think the only reliable solution for this is to introduce an explicit index when converting xml to js(on) (at least when you use explicitChildren=false). The index will be removed when json is converted back to xml, but it will dictate the order of the xml tags.

In my project this would look like this:

<parent>
  <a>1</a>
  <b>2</b>
  <a>3</a>
</parent>

the json looks something like this (actually skipped some details to improve readability):

{
  parent: {
    a: [{
      _$: 1,
      #index: 0
    }, {
      _$: 3,
      #index: 2
    }],
    b: {
      _$: 2,
      #index: 1
    }
  }
}

Without my patch, the only way to produce this JSON would be to have an actual #index XML tag, however since a XML tag can only start with an underscore or a letter, I see no conflicts here.

@ashelley
Copy link

@ds82 Thank you +1

Just used your fork to process some SVG that was breaking without your patches.

ds82 added a commit to ds82/node-xml2js that referenced this issue Sep 3, 2015
@gvillo
Copy link

gvillo commented Jul 18, 2019

any fix for this? #index prop would be very useful for me!

@ogomez92
Copy link

ogomez92 commented Sep 3, 2021

Still waiting for a fix :(

@eMahtab
Copy link

eMahtab commented Jul 4, 2022

I switched to https://github.com/nashwaan/xml-js that worked for my requirements. It preserves the order.

Also if your input xml is deeply nested, you might find the https://marketplace.visualstudio.com/items?itemName=nidu.copy-json-path plugin useful (I guess similar plugins are available for other IDE's as well). You can easily navigate the output JSON using this plugin. This saved a lot of time for me.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
8 participants