Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Invalid XSD schema using libxmljs with nodejs

I've posted an issue on libxmljs repository and it was closed because they think that this isn't a problem at the level of the lib. So I post it here.

I'm trying to validate a XLIFF file with a XML schema provided by OASIS but I keep receiving an error with the XSD.

Error: Invalid XSD schema at Document.validate (/Users/fluxb0x/Tests/xliff_parser/node_modules/libxmljs/lib/document.js:73:17) at Request._callback (/Users/fluxb0x/Tests/xliff_parser/main.js:25:21) at Request.self.callback (/Users/fluxb0x/Tests/xliff_parser/node_modules/request/request.js:199:22) at Request.emit (events.js:98:17) at Request. (/Users/fluxb0x/Tests/xliff_parser/node_modules/request/request.js:1160:14) at Request.emit (events.js:117:20) at IncomingMessage. (/Users/fluxb0x/Tests/xliff_parser/node_modules/request/request.js:1111:12) at IncomingMessage.emit (events.js:117:20) at _stream_readable.js:938:16 at process._tickCallback (node.js:419:13)

I've use Oxygen XML editor to test the validation and it goes without problem.

This is the XLIFF file exported by me : en.xliff

This is the XSD file provided by OASIS : xliff_schema.xsd

Pretty big file.

Thank you for the help.

like image 525
Ismael Avatar asked Jul 17 '26 15:07

Ismael


2 Answers

If the XSD schema contains xsd:import elements with filesystem-relative schemaLocation attributes, the libxmljs.parseXml() function accepts a baseUrl option that can be used to set the location of these.

const xsdDocument = libxmljs.parseXml(xsdString, { baseUrl: "/path/to/xsd/" });

This avoids the need to temporarily change working directory. Watch out for the trailing slash too.

like image 178
Lovell Fuller Avatar answered Jul 19 '26 05:07

Lovell Fuller


As you noted on the libxmljs bug tracker, libxmljs throws an error when validating an XML with a schema file which imports another.

<xsd:import namespace="http://www.w3.org/XML/1998/namespace" schemaLocation="./xml.xsd"/>

This happens because the relative path in schemaLocation is calculated on the process current working directory. A workaround is changing the directory before validating:

fs.readFile(schemaPath, { encoding: 'utf8' }, function (err, xsd) {
    if (err) cb (err);

    var cwd = process.cwd();
    process.chdir(path.dirname(schemaPath));

    var xsdDoc = libxml.parseXml(xsd);
    var xmlDoc = libxml.parseXml(content);

    var output = xmlDoc.validate(xsdDoc);
    process.chdir(cwd);

    cb(undefined, xmlDoc.validationErrors);
});

I'm not sure how libxml handles this though: maybe the referenced file is loaded synchronously and I suppose this is suboptimal.

This workaround is only for local files, I don't know how to resolve in case of a remote schemaLocation, like in your example (schemaLocation="http://www.w3.org/2001/xml.xsd"/>)

Even if it's not a real solution I think this might help.

like image 23
Matteo Nardi Avatar answered Jul 19 '26 05:07

Matteo Nardi



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!