var XmlDocument = require('../').XmlDocument
var t = require('tap')
t.test('verify sax global in browser', function (t) {
// "un-require" the xmldoc module that we loaded up top
delete require.cache[require.resolve('../')];
// also un-require the actual xmldoc module pulled in by index.js ('../')
delete require.cache[require.resolve('../lib/xmldoc.js')];
// this signal will be picked up on by xmldoc.js
global.xmldocAssumeBrowser = true;
t.throws(function() {
require('../');
});
// try again, but this time satisfy the sax check
delete require.cache[require.resolve('../')];
delete require.cache[require.resolve('../lib/xmldoc.js')];
global.sax = {};
require('../');
t.ok(global.XmlDocument);
t.end();
})
t.test('extend util', function(t) {
delete require.cache[require.resolve('../')];
delete require.cache[require.resolve('../lib/xmldoc.js')];
Object.prototype.cruftyExtension = "blah";
try {
require('../');
}
finally {
delete Object.prototype.cruftyExtension;
}
t.end();
})
t.test('parse xml', function (t) {
var xmlString = 'world';
var parsed = new XmlDocument(xmlString);
t.ok(parsed);
t.throws(function() { new XmlDocument(); });
t.throws(function() { new XmlDocument(" "); });
t.end();
})
t.test('cdata handling', function (t) {
var xmlString = ']]>';
var parsed = new XmlDocument(xmlString);
t.equal(parsed.val, "");
t.end();
})
t.test('cdata and text handling', function (t) {
var xmlString = '(]]>)';
var parsed = new XmlDocument(xmlString);
t.equal(parsed.val, "()");
t.end();
})
t.test('doctype handling', function (t) {
var docWithType = new XmlDocument('world');
t.equal(docWithType.doctype, " HelloWorld");
var docWithoutType = new XmlDocument('world');
t.equal(docWithoutType.doctype, "");
t.throws(function() {
new XmlDocument('world');
});
t.end();
})
t.test('comment handling', function (t) {
var xmlString = '';
var parsed = new XmlDocument(xmlString);
t.equal(parsed.val, "");
t.end();
})
t.test('comment and text handling', function (t) {
var xmlString = '()';
var parsed = new XmlDocument(xmlString);
t.equal(parsed.val, "()");
t.end();
})
t.test('text, cdata, and comment handling', function (t) {
var xmlString = 'Hello ]]>!';
var parsed = new XmlDocument(xmlString);
t.equal(parsed.val, "Hello !");
t.end();
})
t.test('text with elements handling', function (t) {
var xmlString = 'hello, !';
var parsed = new XmlDocument(xmlString);
t.equal(parsed.val, "hello, !");
t.end();
})
t.test('text before root node', function (t) {
var xmlString = '\n\n*';
var xml = new XmlDocument(xmlString);
t.equal(xml.val, '*');
t.equal(xml.children.length, 1);
t.end();
})
t.test('text after root node', function (t) {
var xmlString = '*\n\n';
var xml = new XmlDocument(xmlString);
t.equal(xml.val, '*');
t.equal(xml.children.length, 1);
t.end();
})
t.test('text before root node with version', function (t) {
var xmlString = '\n\n*';
var xml = new XmlDocument(xmlString);
t.equal(xml.val, '*');
t.equal(xml.children.length, 1);
t.end();
})
t.test('text after root node with version', function (t) {
var xmlString = '*\n\n';
var xml = new XmlDocument(xmlString);
t.equal(xml.val, '*');
t.equal(xml.children.length, 1);
t.end();
})
t.test('comment before root node', function (t) {
var xmlString = '*';
var xml = new XmlDocument(xmlString);
t.equal(xml.val, '*');
t.equal(xml.children.length, 1);
t.end();
})
t.test('comment after root node', function (t) {
var xmlString = '*';
var xml = new XmlDocument(xmlString);
t.equal(xml.val, '*');
t.equal(xml.children.length, 1);
t.end();
})
t.test('error handling', function (t) {
var xmlString = '';
t.throws(function() {
var parsed = new XmlDocument(xmlString);
});
t.end();
})
t.test('tag locations', function (t) {
var xmlString = '';
var books = new XmlDocument(xmlString);
var book = books.children[0];
t.equal(book.attr.title, "Twilight");
t.equal(book.startTagPosition, 8);
t.equal(book.line, 0);
t.equal(book.column, 31);
t.equal(book.position, 31);
t.end();
})
t.test('eachChild', function (t) {
var xmlString = '';
var books = new XmlDocument(xmlString);
expectedTitles = ["Twilight", "Twister"];
books.eachChild(function(book, i, books) {
t.equal(book.attr.title, expectedTitles[i]);
});
called = 0;
books.eachChild(function(book, i, books) {
called++;
return false; // test that returning false short-circuits the loop
});
t.equal(called, 1);
t.end();
})
t.test('eachChild with text and comments', function (t) {
var xmlString = 'text!';
var books = new XmlDocument(xmlString);
expectedTitles = ["Twilight", "Twister"];
var elI = 0;
books.eachChild(function(book, i, books) {
t.equal(book.attr.title, expectedTitles[elI++]);
});
called = 0;
books.eachChild(function(book, i, books) {
called++;
return false; // test that returning false short-circuits the loop
});
t.equal(called, 1);
t.end();
})
t.test('childNamed', function (t) {
var xmlString = '';
var books = new XmlDocument(xmlString);
var goodBook = books.childNamed('good-book');
t.equal(goodBook.name, 'good-book');
var badBook = books.childNamed('bad-book');
t.equal(badBook, undefined);
t.end();
})
t.test('childNamed with text', function (t) {
var xmlString = 'text';
var books = new XmlDocument(xmlString);
var goodBook = books.childNamed('good-book');
t.equal(goodBook.name, 'good-book');
var badBook = books.childNamed('bad-book');
t.equal(badBook, undefined);
t.end();
})
t.test('childNamed', function (t) {
var xmlString = '';
var fruits = new XmlDocument(xmlString);
var apples = fruits.childrenNamed('apple');
t.equal(apples.length, 2);
t.equal(apples[0].attr.sweet, 'yes');
t.equal(apples[1].attr.sweet, 'no');
t.end();
})
t.test('childWithAttribute', function (t) {
var xmlString = '';
var fruits = new XmlDocument(xmlString);
var pickedFruit = fruits.childWithAttribute('pick', 'yes');
t.equal(pickedFruit.name, 'apple');
t.equal(pickedFruit.attr.pick, 'yes');
var rottenFruit = fruits.childWithAttribute('rotten');
t.equal(rottenFruit.name, 'orange');
var peeled = fruits.childWithAttribute('peeled');
t.equal(peeled, undefined);
t.end();
})
t.test('childWithAttribute with text', function (t) {
var xmlString = 'text';
var fruits = new XmlDocument(xmlString);
var pickedFruit = fruits.childWithAttribute('pick', 'yes');
t.equal(pickedFruit.name, 'apple');
t.equal(pickedFruit.attr.pick, 'yes');
var rottenFruit = fruits.childWithAttribute('rotten');
t.equal(rottenFruit.name, 'orange');
var peeled = fruits.childWithAttribute('peeled');
t.equal(peeled, undefined);
t.end();
})
t.test('descendantWithPath', function (t) {
var xmlString = 'George R.R.Martin';
var book = new XmlDocument(xmlString);
var lastNameNode = book.descendantWithPath('author.last');
t.equal(lastNameNode.val, 'Martin');
var middleNameNode = book.descendantWithPath('author.middle');
t.equal(middleNameNode, undefined);
var publisherNameNode = book.descendantWithPath('publisher.first');
t.equal(publisherNameNode, undefined);
t.end();
})
t.test('descendantWithPath with text', function (t) {
var xmlString = 'textGeorge R.R.Martin';
var book = new XmlDocument(xmlString);
var lastNameNode = book.descendantWithPath('author.last');
t.equal(lastNameNode.val, 'Martin');
var middleNameNode = book.descendantWithPath('author.middle');
t.equal(middleNameNode, undefined);
var publisherNameNode = book.descendantWithPath('publisher.first');
t.equal(publisherNameNode, undefined);
t.end();
})
t.test('valueWithPath', function (t) {
var xmlString = 'George R.R.Martin';
var book = new XmlDocument(xmlString);
var lastName = book.valueWithPath('author.last');
t.equal(lastName, 'Martin');
var lastNameHyphenated = book.valueWithPath('author.last@hyphenated');
t.equal(lastNameHyphenated, "no");
var publisherName = book.valueWithPath('publisher.last@hyphenated');
t.equal(publisherName, undefined);
t.end();
})
t.test('valueWithPath with text', function (t) {
var xmlString = 'textGeorge R.R.Martin';
var book = new XmlDocument(xmlString);
var lastName = book.valueWithPath('author.last');
t.equal(lastName, 'Martin');
var lastNameHyphenated = book.valueWithPath('author.last@hyphenated');
t.equal(lastNameHyphenated, "no");
var publisherName = book.valueWithPath('publisher.last@hyphenated');
t.equal(publisherName, undefined);
t.end();
})
t.test('toString', function (t) {
var xmlString = '';
var doc = new XmlDocument(xmlString);
t.equal(doc.toString(), '\n \n');
t.equal(doc.toString({compressed:true}), '');
xmlString = ' world ';
doc = new XmlDocument(xmlString);
t.equal(doc.toString(), 'world');
t.equal(doc.toString({preserveWhitespace:true}), ' world ');
xmlString = ']]>';
doc = new XmlDocument(xmlString);
t.equal(doc.toString(), ']]>');
xmlString = 'Hello ]]>!';
doc = new XmlDocument(xmlString);
t.equal(doc.toString({preserveWhitespace:true}), '\n Hello\n \n \n ]]>\n !\n');
xmlString = 'hello, !';
doc = new XmlDocument(xmlString);
t.equal(doc.toString(), '\n hello,\n \n !\n');
xmlString = 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam et accumsan nisi.';
doc = new XmlDocument(xmlString);
t.equal(doc.toString(), xmlString);
t.equal(doc.toString({trimmed:true}), 'Lorem ipsum dolor sit ameā¦')
try {
// test that adding stuff to the Object prototype doesn't interfere with attribute exporting
Object.prototype.cruftyExtension = "You don't want this string to be exported!";
var xmlString = '';
var doc = new XmlDocument(xmlString);
t.equal(doc.toString(), '\n \n');
}
finally {
delete Object.prototype.cruftyExtensionMethod;
}
xmlString = 'world';
doc = new XmlDocument(xmlString);
t.equal(doc.toString({compressed:true}), xmlString);
t.end();
})