summaryrefslogtreecommitdiffstats
path: root/dom/xslt/tests
diff options
context:
space:
mode:
authorMatt A. Tobin <mattatobin@localhost.localdomain>2018-02-02 04:16:08 -0500
committerMatt A. Tobin <mattatobin@localhost.localdomain>2018-02-02 04:16:08 -0500
commit5f8de423f190bbb79a62f804151bc24824fa32d8 (patch)
tree10027f336435511475e392454359edea8e25895d /dom/xslt/tests
parent49ee0794b5d912db1f95dce6eb52d781dc210db5 (diff)
downloadUXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.gz
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.lz
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.xz
UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.zip
Add m-esr52 at 52.6.0
Diffstat (limited to 'dom/xslt/tests')
-rw-r--r--dom/xslt/tests/XSLTMark/XSLTMark-static.js49
-rw-r--r--dom/xslt/tests/XSLTMark/XSLTMark-test.js46
-rw-r--r--dom/xslt/tests/XSLTMark/XSLTMark-view.js175
-rw-r--r--dom/xslt/tests/XSLTMark/XSLTMark.css8
-rw-r--r--dom/xslt/tests/XSLTMark/XSLTMark.xul52
-rw-r--r--dom/xslt/tests/buster/DiffDOM.js103
-rw-r--r--dom/xslt/tests/buster/DumpDOM.js85
-rw-r--r--dom/xslt/tests/buster/ReadMe22
-rw-r--r--dom/xslt/tests/buster/buster-files.js81
-rw-r--r--dom/xslt/tests/buster/buster-handlers.js37
-rw-r--r--dom/xslt/tests/buster/buster-statics.js87
-rw-r--r--dom/xslt/tests/buster/buster-test.js356
-rw-r--r--dom/xslt/tests/buster/buster-view.js193
-rw-r--r--dom/xslt/tests/buster/buster.css20
-rw-r--r--dom/xslt/tests/buster/buster.xul196
-rw-r--r--dom/xslt/tests/buster/helper/generate-rdf.pl95
-rw-r--r--dom/xslt/tests/buster/install.js17
-rw-r--r--dom/xslt/tests/buster/jar.mn18
-rw-r--r--dom/xslt/tests/buster/result-inspector.xul37
-rw-r--r--dom/xslt/tests/buster/result-view.css16
-rw-r--r--dom/xslt/tests/buster/result-view.js105
-rw-r--r--dom/xslt/tests/buster/result-view.xul46
-rw-r--r--dom/xslt/tests/buster/xslt-qa-overlay.js10
-rw-r--r--dom/xslt/tests/buster/xslt-qa-overlay.xul12
-rw-r--r--dom/xslt/tests/mochitest/file_bug1135764.xml3
-rw-r--r--dom/xslt/tests/mochitest/file_bug1135764.xsl19
-rw-r--r--dom/xslt/tests/mochitest/mochitest.ini20
-rw-r--r--dom/xslt/tests/mochitest/test_bug1072116.html37
-rw-r--r--dom/xslt/tests/mochitest/test_bug1135764.html53
-rw-r--r--dom/xslt/tests/mochitest/test_bug319374.xhtml109
-rw-r--r--dom/xslt/tests/mochitest/test_bug427060.html49
-rw-r--r--dom/xslt/tests/mochitest/test_bug440974.html46
-rw-r--r--dom/xslt/tests/mochitest/test_bug453441.html57
-rw-r--r--dom/xslt/tests/mochitest/test_bug468208.html35
-rw-r--r--dom/xslt/tests/mochitest/test_bug511487.html59
-rw-r--r--dom/xslt/tests/mochitest/test_bug551412.html48
-rw-r--r--dom/xslt/tests/mochitest/test_bug551654.html49
-rw-r--r--dom/xslt/tests/mochitest/test_bug566629.html70
-rw-r--r--dom/xslt/tests/mochitest/test_bug566629.xhtml73
-rw-r--r--dom/xslt/tests/mochitest/test_bug603159.html54
-rw-r--r--dom/xslt/tests/mochitest/test_bug616774.html28
-rw-r--r--dom/xslt/tests/mochitest/test_bug667315.html46
-rw-r--r--dom/xslt/tests/mochitest/test_exslt_regex.html60
-rw-r--r--dom/xslt/tests/mochitest/test_parameter.html31
44 files changed, 2812 insertions, 0 deletions
diff --git a/dom/xslt/tests/XSLTMark/XSLTMark-static.js b/dom/xslt/tests/XSLTMark/XSLTMark-static.js
new file mode 100644
index 000000000..d3284aac8
--- /dev/null
+++ b/dom/xslt/tests/XSLTMark/XSLTMark-static.js
@@ -0,0 +1,49 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+const enablePrivilege = netscape.security.PrivilegeManager.enablePrivilege;
+const IOSERVICE_CTRID = "@mozilla.org/network/io-service;1";
+const nsIIOService = Components.interfaces.nsIIOService;
+const SIS_CTRID = "@mozilla.org/scriptableinputstream;1";
+const nsISIS = Components.interfaces.nsIScriptableInputStream;
+const nsIFilePicker = Components.interfaces.nsIFilePicker;
+const STDURL_CTRID = "@mozilla.org/network/standard-url;1";
+const nsIURI = Components.interfaces.nsIURI;
+
+Components.utils.import("resource://gre/modules/NetUtil.jsm");
+
+var gStop = false;
+
+function loadFile(aUriSpec)
+{
+ enablePrivilege('UniversalXPConnect');
+ var serv = Components.classes[IOSERVICE_CTRID].
+ getService(nsIIOService);
+ if (!serv) {
+ throw Components.results.ERR_FAILURE;
+ }
+ var chan = NetUtil.newChannel({
+ uri: aUriSpec,
+ loadUsingSystemPrincipal: true
+ });
+ var instream =
+ Components.classes[SIS_CTRID].createInstance(nsISIS);
+ instream.init(chan.open2());
+
+ return instream.read(instream.available());
+}
+
+function dump20(aVal)
+{
+ const pads = ' ';
+ if (typeof(aVal)=='string')
+ out = aVal;
+ else if (typeof(aVal)=='number')
+ out = Number(aVal).toFixed(2);
+ else
+ out = new String(aVal);
+ dump(pads.substring(0, 20 - out.length));
+ dump(out);
+}
diff --git a/dom/xslt/tests/XSLTMark/XSLTMark-test.js b/dom/xslt/tests/XSLTMark/XSLTMark-test.js
new file mode 100644
index 000000000..4037c75e4
--- /dev/null
+++ b/dom/xslt/tests/XSLTMark/XSLTMark-test.js
@@ -0,0 +1,46 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+var gParser = new DOMParser;
+var gTimeout;
+
+function Test(aTitle, aSourceURL, aStyleURL, aNumber, aObserver)
+{
+ this.mTitle = aTitle;
+ this.mObserver = aObserver;
+ this.mTotal = aNumber;
+ this.mDone = 0;
+ var xmlcontent = loadFile(aSourceURL);
+ var xslcontent = loadFile(aStyleURL);
+ this.mSource = gParser.parseFromString(xmlcontent, 'application/xml');
+ this.mStyle = gParser.parseFromString(xslcontent, 'application/xml');
+}
+
+function runTest(aTitle, aSourceURL, aStyleURL, aNumber, aObserver)
+{
+ test = new Test(aTitle, aSourceURL, aStyleURL, aNumber,
+ aObserver);
+ gTimeout = setTimeout(onNextTransform, 100, test, 0);
+}
+
+function onNextTransform(aTest, aNumber)
+{
+ var proc = new XSLTProcessor;
+ var startTime = Date.now();
+ proc.importStylesheet(aTest.mStyle);
+ var res = proc.transformToDocument(aTest.mSource);
+ var endTime = Date.now();
+ aNumber++;
+ var progress = aNumber / aTest.mTotal * 100;
+ if (aTest.mObserver) {
+ aTest.mObserver.progress(aTest.mTitle, endTime - startTime,
+ progress);
+ }
+ if (aNumber < aTest.mTotal) {
+ gTimeout = setTimeout(onNextTransform, 100, aTest, aNumber);
+ } else if (aTest.mObserver) {
+ aTest.mObserver.done(aTest.mTitle);
+ }
+}
diff --git a/dom/xslt/tests/XSLTMark/XSLTMark-view.js b/dom/xslt/tests/XSLTMark/XSLTMark-view.js
new file mode 100644
index 000000000..7342d0d9a
--- /dev/null
+++ b/dom/xslt/tests/XSLTMark/XSLTMark-view.js
@@ -0,0 +1,175 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+var view =
+{
+ configUrl: null,
+ testArray: null,
+ mCurrent: null,
+
+ browseForConfig: function()
+ {
+ enablePrivilege('UniversalXPConnect');
+ var fp = Components.classes["@mozilla.org/filepicker;1"].
+ createInstance(nsIFilePicker);
+ fp.init(window,'XSLTMark Description File',nsIFilePicker.modeOpen);
+ fp.appendFilter('*.conf', '*.conf');
+ fp.appendFilters(nsIFilePicker.filterAll);
+ var res = fp.show();
+
+ if (res == nsIFilePicker.returnOK) {
+ this.configUrl = Components.classes[STDURL_CTRID].createInstance(nsIURI);
+ this.configUrl.spec = fp.fileURL.spec;
+ document.getElementById('config').setAttribute('value', this.configUrl.spec);
+ }
+ this.parseConfig();
+ return true;
+ },
+
+ parseConfig: function()
+ {
+ this.testArray = new Array();
+ var test;
+ if (!this.configUrl) {
+ return;
+ }
+
+ var content = loadFile(this.configUrl.spec);
+
+ var lines = content.split("\n");
+ var line, res;
+ var head = /^\[(.+)\]$/;
+ var instruct = /^(.+)=(.+)$/;
+ while (lines.length) {
+ line = lines.shift();
+ if (head.test(line)) {
+ test = new Object;
+ res = head.exec(line);
+ test['title'] = res[1];
+ this.testArray.push(test);
+ }
+ else if (line == '') {
+ test = undefined;
+ }
+ else {
+ res = instruct.exec(line);
+ test[res[1]] = res[2];
+ }
+ }
+ },
+
+ onLoad: function()
+ {
+ this.mCurrentStatus = document.getElementById('currentStatus');
+ this.mCurrentProgress = document.getElementById('currentProgress');
+ this.mTotalProgress = document.getElementById('totalProgress');
+ this.mOutput = document.getElementById('transformOutput');
+ this.mDetailOutput =
+ document.getElementById('transformDetailedOutput');
+ this.mDetail = true;
+ },
+
+ progress: function(aTitle, aTime, aProgress)
+ {
+ // dump20(aTitle);
+ // dump20(aTime);
+ // dump20(aProgress);
+ this.mCurrentProgress.value = aProgress;
+ this.displayDetailTime(aTime);
+ this.mTimes.push(aTime);
+ // dump("\n");
+ },
+
+ done: function(aTitle)
+ {
+ // dump(aTitle + " is finished.\n");
+ this.mCurrent++;
+ this.mCurrentProgress.value = 0;
+ this.displayTotalTime();
+ if (this.mCurrent >= this.testArray.length) {
+ this.mTotalProgress.value = 0;
+ this.mCurrentStatus.value = "done";
+ return;
+ }
+ this.mTotalProgress.value = this.mCurrent*100/this.testArray.length;
+ var test = this.testArray[this.mCurrent];
+ enablePrivilege('UniversalXPConnect');
+ this.displayTest(test.title);
+ runTest(test.title, this.configUrl.resolve(test.input),
+ this.configUrl.resolve(test.stylesheet),
+ test.iterations, this);
+ },
+
+ onStop: function()
+ {
+ clearTimeout(gTimeout);
+ this.mCurrentProgress.value = 0;
+ this.mTotalProgress.value = 0;
+ this.mCurrentStatus.value = "stopped";
+ },
+
+ displayTest: function(aTitle)
+ {
+ this.mTimes = new Array;
+ aTitle += "\t";
+ this.mCurrentStatus.value = aTitle;
+ this.mOutput.value += aTitle;
+ if (this.mDetail) {
+ this.mDetailOutput.value += aTitle;
+ }
+ },
+
+ displayDetailTime: function(aTime)
+ {
+ if (this.mDetail) {
+ this.mDetailOutput.value += aTime + " ms\t";
+ }
+ },
+
+ displayTotalTime: function()
+ {
+ var sum = 0;
+ for (k = 0; k < this.mTimes.length; k++) {
+ sum += this.mTimes[k];
+ }
+ var mean = sum / this.mTimes.length;
+ this.mOutput.value += Number(mean).toFixed(2) + " ms\t" + sum + " ms\t";
+ var variance = 0;
+ for (k = 0; k < this.mTimes.length; k++) {
+ var n = this.mTimes[k] - mean;
+ variance += n*n;
+ }
+ variance = Math.sqrt(variance/this.mTimes.length);
+ this.mOutput.value += Number(variance).toFixed(2)+"\n";
+ if (this.mDetail) {
+ this.mDetailOutput.value += "\n";
+ }
+ },
+
+ runBenchmark: function()
+ {
+ enablePrivilege('UniversalXPConnect');
+ if (!this.testArray) {
+ if (!this.configUrl) {
+ this.configUrl = Components.classes[STDURL_CTRID].createInstance(nsIURI);
+ this.configUrl.spec = document.getElementById('config').value;
+ }
+ this.parseConfig();
+ }
+
+ this.mCurrent = 0;
+ var test = this.testArray[this.mCurrent];
+ this.mOutput.value = '';
+ if (this.mDetail) {
+ this.mDetailOutput.value = '';
+ }
+ this.displayTest(test.title);
+ runTest(test.title, this.configUrl.resolve(test.input),
+ this.configUrl.resolve(test.stylesheet),
+ test.iterations, this);
+ return true;
+ }
+}
+
diff --git a/dom/xslt/tests/XSLTMark/XSLTMark.css b/dom/xslt/tests/XSLTMark/XSLTMark.css
new file mode 100644
index 000000000..80386ae2d
--- /dev/null
+++ b/dom/xslt/tests/XSLTMark/XSLTMark.css
@@ -0,0 +1,8 @@
+/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+textbox.out {
+ white-space: pre;
+}
diff --git a/dom/xslt/tests/XSLTMark/XSLTMark.xul b/dom/xslt/tests/XSLTMark/XSLTMark.xul
new file mode 100644
index 000000000..bc34a7a03
--- /dev/null
+++ b/dom/xslt/tests/XSLTMark/XSLTMark.xul
@@ -0,0 +1,52 @@
+<?xml version="1.0"?><!-- -*- Mode: xml; tab-width: 2; indent-tabs-mode: nil -*- -->
+<!-- This Source Code Form is subject to the terms of the Mozilla Public
+ - License, v. 2.0. If a copy of the MPL was not distributed with this
+ - file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
+
+<?xml-stylesheet href="chrome://communicator/skin/" type="text/css"?>
+<?xml-stylesheet href="XSLTMark.css" type="text/css"?>
+<window id="XSLTMarkHarness"
+ title="XSLTMark"
+ onload="view.onLoad()"
+ xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
+ orient="vertical">
+<script type="application/x-javascript" src="XSLTMark-static.js" />
+<script type="application/x-javascript" src="XSLTMark-test.js" />
+<script type="application/x-javascript" src="XSLTMark-view.js" />
+
+<hbox>
+ <groupbox orient="horizontal">
+ <caption label="test description file" />
+ <label value=""/><!-- needed, otherwise groupbox fucks up :-( -->
+ <textbox id="config" persist="value" readonly="true"/>
+ <button label="browse..." oncommand="view.browseForConfig();" />
+ </groupbox>
+ <groupbox orient="horizontal">
+ <caption label="test control" />
+ <button label="run..."
+ oncommand="setTimeout('view.runBenchmark();', 0);" />
+ <button label="stop" oncommand="view.onStop();" />
+ </groupbox>
+ <groupbox orient="horizontal">
+ <caption label="options" />
+ <label value="responsiveness: "/>
+ <menulist label="sloppy">
+ <menupopup>
+ <menuitem label="sloppy" selected="true"/>
+ <menuitem label="bad"/>
+ </menupopup>
+ </menulist>
+ </groupbox>
+</hbox>
+<hbox>
+ <textbox id="currentStatus" readonly="true" flex="1"/>
+ <progressmeter id="currentProgress" mode="normal" value="0" flex="2"/>
+ <progressmeter id="totalProgress" mode="normal" value="0" flex="2"/>
+</hbox>
+<hbox flex="1">
+ <textbox id="transformOutput" class="out" readonly="true" multiline="true" flex="1"/>
+</hbox>
+<hbox flex="1">
+ <textbox id="transformDetailedOutput" class="out" readonly="true" multiline="true" flex="1"/>
+</hbox>
+</window> \ No newline at end of file
diff --git a/dom/xslt/tests/buster/DiffDOM.js b/dom/xslt/tests/buster/DiffDOM.js
new file mode 100644
index 000000000..587214ff3
--- /dev/null
+++ b/dom/xslt/tests/buster/DiffDOM.js
@@ -0,0 +1,103 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+// ----------------------
+// DiffDOM(node1,node2)
+// ----------------------
+
+var isHTML = false;
+
+function DiffDOM(node1, node2, aIsHTML)
+{
+ isHTML = aIsHTML;
+ return DiffNodeAndChildren(node1, node2);
+}
+
+
+// namespace attributes in the second node are ignored
+const nsreg = /^xmlns[|:\w]/;
+
+// This function does the work of DiffDOM by recursively calling
+// itself to explore the tree
+function DiffNodeAndChildren(node1, node2)
+{
+ if (!node1 && !node2)
+ return true;
+ if (!node1 || !node2)
+ return ErrorUp("One of the nodes is null", node1, node2);
+ if (node1.type!=node2.type)
+ return ErrorUp("Different node types", node1, node2);
+
+ var attributes = node2.attributes;
+ if (attributes && attributes.length) {
+ var item, name, ns, value, otherValue;
+ for (var index = 0; index < attributes.length; index++) {
+ item = attributes.item(index);
+ ns = item.namespaceURI;
+ if (ns) {
+ name = item.localName;
+ otherValue = node2.getAttributeNS(ns, name);
+ }
+ else {
+ name = item.nodeName;
+ otherValue = node2.getAttribute(name);
+ }
+ value = item.nodeValue;
+ if (!nsreg.test(name) && otherValue!=value) {
+ return ErrorUp("Different values for attribute", node1, node2);
+ }
+ }
+ }
+ else if (node1.attributes && node1.attributes.length) {
+ return ErrorUp("Different number of attributes", node1, node2);
+ }
+
+ if (isHTML) {
+ if (node1.nodeName.toLowerCase()!=node2.nodeName.toLowerCase())
+ return ErrorUp("Different node names", node1, node2);
+ }
+ else {
+ if (node1.nodeName!=node2.nodeName)
+ return ErrorUp("Different node names", node1, node2);
+ }
+ if (node1.nodeValue!=node2.nodeValue)
+ return ErrorUp("Different node values", node1, node2);
+ if (!isHTML)
+ if (node1.namespaceURI!=node2.namespaceURI)
+ return ErrorUp("Different namespace", node1, node2);
+ if (node1.hasChildNodes() != node2.hasChildNodes())
+ return ErrorUp("Different children", node1, node2);
+ if (node1.childNodes) {
+ if (node1.childNodes.length != node2.childNodes.length)
+ return ErrorUp("Different number of children", node1, node2);
+ for (var child = 0; child < node1.childNodes.length; child++) {
+ if (!DiffNodeAndChildren(node1.childNodes[child],
+ node2.childNodes[child])) {
+ return false;
+ }
+ }
+ }
+ return true;
+}
+
+function ErrorUp(errMsg, node1, node2)
+{
+ dump("Error: "+errMsg+"\n");
+ if (node1) {
+ dump("Node 1: "+node1+", ");
+ if (node1.nodeType == Node.TEXT_NODE)
+ dump("nodeValue: "+node1.nodeValue+"\n");
+ else
+ dump("nodeName: "+node1.namespaceURI+":"+node1.nodeName+"\n");
+ }
+ if (node2) {
+ dump("Node 2: "+node2+", ");
+ if (node2.nodeType == Node.TEXT_NODE)
+ dump("nodeValue: "+node2.nodeValue+"\n");
+ else
+ dump("nodeName: "+node2.namespaceURI+":"+node2.nodeName+"\n");
+ }
+ return false;
+}
diff --git a/dom/xslt/tests/buster/DumpDOM.js b/dom/xslt/tests/buster/DumpDOM.js
new file mode 100644
index 000000000..0a90ce9d0
--- /dev/null
+++ b/dom/xslt/tests/buster/DumpDOM.js
@@ -0,0 +1,85 @@
+// ----------------------
+// DumpDOM(node)
+//
+// Call this function to dump the contents of the DOM starting at the specified node.
+// Use node = document.documentElement to dump every element of the current document.
+// Use node = top.window.document.documentElement to dump every element.
+//
+// 8-13-99 Updated to dump almost all attributes of every node. There are still some attributes
+// that are purposely skipped to make it more readable.
+// ----------------------
+function DumpDOM(node)
+{
+ dump("--------------------- DumpDOM ---------------------\n");
+
+ DumpNodeAndChildren(node, "");
+
+ dump("------------------- End DumpDOM -------------------\n");
+}
+
+
+// This function does the work of DumpDOM by recursively calling itself to explore the tree
+function DumpNodeAndChildren(node, prefix)
+{
+ dump(prefix + "<" + node.nodeName);
+
+ var attributes = node.attributes;
+
+ if ( attributes && attributes.length )
+ {
+ var item, name, value;
+
+ for ( var index = 0; index < attributes.length; index++ )
+ {
+ item = attributes.item(index);
+ name = item.nodeName;
+ value = item.nodeValue;
+
+ if ( (name == 'lazycontent' && value == 'true') ||
+ (name == 'xulcontentsgenerated' && value == 'true') ||
+ (name == 'id') ||
+ (name == 'instanceOf') )
+ {
+ // ignore these
+ }
+ else
+ {
+ dump(" " + name + "=\"" + value + "\"");
+ }
+ }
+ }
+
+ if ( node.nodeType == 1 )
+ {
+ // id
+ var text = node.getAttribute('id');
+ if ( text && text[0] != '$' )
+ dump(" id=\"" + text + "\"");
+ }
+
+ if ( node.nodeType == Node.TEXT_NODE )
+ dump(" = \"" + node.data + "\"");
+
+ dump(">\n");
+
+ // dump IFRAME && FRAME DOM
+ if ( node.nodeName == "IFRAME" || node.nodeName == "FRAME" )
+ {
+ if ( node.name )
+ {
+ var wind = top.frames[node.name];
+ if ( wind && wind.document && wind.document.documentElement )
+ {
+ dump(prefix + "----------- " + node.nodeName + " -----------\n");
+ DumpNodeAndChildren(wind.document.documentElement, prefix + " ");
+ dump(prefix + "--------- End " + node.nodeName + " ---------\n");
+ }
+ }
+ }
+ // children of nodes (other than frames)
+ else if ( node.childNodes )
+ {
+ for ( var child = 0; child < node.childNodes.length; child++ )
+ DumpNodeAndChildren(node.childNodes[child], prefix + " ");
+ }
+}
diff --git a/dom/xslt/tests/buster/ReadMe b/dom/xslt/tests/buster/ReadMe
new file mode 100644
index 000000000..82ad04d96
--- /dev/null
+++ b/dom/xslt/tests/buster/ReadMe
@@ -0,0 +1,22 @@
+The buster is a XUL interface to the conformance tests shipped as part of
+Xalan. For information about Xalan, please see http://xml.apache.org/.
+For your convenience we provide a packed distribution of all needed files
+in http://www.axel.pike.org/mozilla/xalan.tar.gz. Please see the included
+LICENSE.txt or http://xml.apache.org/dist/LICENSE.txt for terms of
+distributing those files.
+
+To use the buster, open buster.xul with an XSLT enabled Mozilla.
+Open the rdf index file shipped with the test package into the
+"Xalan index", and the available tests will show up as a tree.
+Once you have selected the tests you're interested in, press the button
+"run checked tests", and all the tests will be run.
+You can save the results into an rdf, and load it for comparison and
+regression hunting.
+
+DiffDOM tries to find out, which tests failed, and will DumpDOM both the
+result and the reference solution. Not all reference solutions load
+properly, those need manual love.
+
+Good luck and fun
+
+Axel Hecht <axel@pike.org>
diff --git a/dom/xslt/tests/buster/buster-files.js b/dom/xslt/tests/buster/buster-files.js
new file mode 100644
index 000000000..cbdb8bdd2
--- /dev/null
+++ b/dom/xslt/tests/buster/buster-files.js
@@ -0,0 +1,81 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+const kFileOutStreamCID = "@mozilla.org/network/file-output-stream;1";
+const nsIFileOutputStream = Components.interfaces.nsIFileOutputStream;
+
+var cmdFileController =
+{
+ supportsCommand: function(aCommand)
+ {
+ switch(aCommand) {
+ case 'cmd_fl_save':
+ case 'cmd_fl_import':
+ return true;
+ default:
+ }
+ return false;
+ },
+ isCommandEnabled: function(aCommand)
+ {
+ return this.supportsCommand(aCommand);
+ },
+ doCommand: function(aCommand)
+ {
+ switch(aCommand) {
+ case 'cmd_fl_save':
+ var sink = new Object;
+ sink.write = function(aContent, aCount)
+ {
+ // replace NC:succ with NC:orig_succ,
+ // so the rdf stuff differs
+ var content = aContent.replace(/NC:succ/g,"NC:orig_succ");
+ content = content.replace(/NC:failCount/g,"NC:orig_failCount");
+ this.mSink.write(content, content.length);
+ return aCount;
+ };
+ var fp = doCreateRDFFP('Xalan results',
+ nsIFilePicker.modeSave);
+ var res = fp.show();
+
+ if (res == nsIFilePicker.returnOK ||
+ res == nsIFilePicker.returnReplace) {
+ var serial = doCreate(kRDFXMLSerializerID,
+ nsIRDFXMLSerializer);
+ serial.init(view.mResultDS);
+ serial.QueryInterface(nsIRDFXMLSource);
+ var fl = fp.file;
+ var fstream = doCreate(kFileOutStreamCID,
+ nsIFileOutputStream);
+ fstream.init(fl, 26, 420, 0);
+ sink.mSink = fstream;
+ serial.Serialize(sink);
+ }
+ break;
+ case 'cmd_fl_import':
+ var fp = doCreateRDFFP('Previous Xalan results',
+ nsIFilePicker.modeLoad);
+ var res = fp.show();
+
+ if (res == nsIFilePicker.returnOK) {
+ var fl = fp.file;
+ if (view.mPreviousResultDS) {
+ view.database.RemoveDataSource(view.mPreviousResultDS);
+ view.mPreviousResultDS = null;
+ }
+ view.mPreviousResultDS = kRDFSvc.GetDataSource(fp.fileURL.spec);
+ view.database.AddDataSource(view.mPreviousResultDS);
+ }
+
+ document.getElementById('obs_orig_success')
+ .setAttribute('hidden','false');
+ break;
+ default:
+ alert('Unknown Command'+aCommand);
+ }
+ }
+};
+
+registerController(cmdFileController);
diff --git a/dom/xslt/tests/buster/buster-handlers.js b/dom/xslt/tests/buster/buster-handlers.js
new file mode 100644
index 000000000..4e6f85fcc
--- /dev/null
+++ b/dom/xslt/tests/buster/buster-handlers.js
@@ -0,0 +1,37 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+var xalan_field;
+
+function onLoad()
+{
+ view.tree = document.getElementById('out');
+ view.boxObject = view.tree.boxObject;
+ {
+ view.mIframe = document.getElementById('hiddenHtml');
+ view.mIframe.webNavigation.allowPlugins = false;
+ view.mIframe.webNavigation.allowJavascript = false;
+ view.mIframe.webNavigation.allowMetaRedirects = false;
+ view.mIframe.webNavigation.allowImages = false;
+ }
+ view.database = view.tree.database;
+ view.builder = view.tree.builder.QueryInterface(nsIXULTemplateBuilder);
+ view.builder.QueryInterface(nsIXULTreeBuilder);
+ runItem.prototype.kDatabase = view.database;
+ xalan_field = document.getElementById("xalan_rdf");
+ var persistedUrl = xalan_field.getAttribute('url');
+ if (persistedUrl) {
+ view.xalan_url = persistedUrl;
+ xalan_field.value = persistedUrl;
+ }
+ view.setDataSource();
+ return true;
+}
+
+function onUnload()
+{
+ if (xalan_field)
+ xalan_field.setAttribute('url', xalan_field.value);
+}
diff --git a/dom/xslt/tests/buster/buster-statics.js b/dom/xslt/tests/buster/buster-statics.js
new file mode 100644
index 000000000..b70cef511
--- /dev/null
+++ b/dom/xslt/tests/buster/buster-statics.js
@@ -0,0 +1,87 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+// helper function to shortcut component creation
+function doCreate(aContract, aInterface)
+{
+ return Components.classes[aContract].createInstance(aInterface);
+}
+
+// for the items, loading a text file
+const IOSERVICE_CTRID = "@mozilla.org/network/io-service;1";
+const nsIIOService = Components.interfaces.nsIIOService;
+const SIS_CTRID = "@mozilla.org/scriptableinputstream;1"
+const nsISIS = Components.interfaces.nsIScriptableInputStream;
+
+// rdf foo, onload handler
+const kRDFSvcContractID = "@mozilla.org/rdf/rdf-service;1";
+const kRDFInMemContractID =
+ "@mozilla.org/rdf/datasource;1?name=in-memory-datasource";
+const kRDFContUtilsID = "@mozilla.org/rdf/container-utils;1";
+const kRDFXMLSerializerID = "@mozilla.org/rdf/xml-serializer;1";
+const kIOSvcContractID = "@mozilla.org/network/io-service;1";
+const kStandardURL = Components.classes["@mozilla.org/network/standard-url;1"];
+const nsIURL = Components.interfaces.nsIURL;
+const nsIStandardURL = Components.interfaces.nsIStandardURL;
+const nsIFilePicker = Components.interfaces.nsIFilePicker;
+const nsIXULTreeBuilder = Components.interfaces.nsIXULTreeBuilder;
+const nsIXULTemplateBuilder = Components.interfaces.nsIXULTemplateBuilder;
+const kIOSvc = Components.classes[kIOSvcContractID]
+ .getService(Components.interfaces.nsIIOService);
+const nsIRDFService = Components.interfaces.nsIRDFService;
+const nsIRDFDataSource = Components.interfaces.nsIRDFDataSource;
+const nsIRDFRemoteDataSource = Components.interfaces.nsIRDFRemoteDataSource;
+const nsIRDFPurgeableDataSource =
+ Components.interfaces.nsIRDFPurgeableDataSource;
+const nsIRDFResource = Components.interfaces.nsIRDFResource;
+const nsIRDFLiteral = Components.interfaces.nsIRDFLiteral;
+const nsIRDFInt = Components.interfaces.nsIRDFInt;
+const nsIRDFContainerUtils = Components.interfaces.nsIRDFContainerUtils;
+const nsIRDFXMLSerializer = Components.interfaces.nsIRDFXMLSerializer;
+const nsIRDFXMLSource = Components.interfaces.nsIRDFXMLSource;
+const kRDFSvc =
+ Components.classes[kRDFSvcContractID].getService(nsIRDFService);
+const krTypeCat = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#category");
+const krTypeFailCount = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#failCount");
+const krTypeName = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#name");
+const krTypeSucc = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#succ");
+const krTypeOrigSucc = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#orig_succ");
+const krTypeOrigFailCount = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#orig_failCount");
+const krTypeOrigSuccCount = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#orig_succCount");
+const krTypePath = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#path");
+const krTypeParent = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#parent");
+const krTypePurp = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#purp");
+const krTypeSuccCount = kRDFSvc.GetResource("http://home.netscape.com/NC-rdf#succCount");
+const kGood = kRDFSvc.GetLiteral("yes");
+const kBad = kRDFSvc.GetLiteral("no");
+const kMixed = kRDFSvc.GetLiteral("+-");
+const kContUtils = doCreate(kRDFContUtilsID, nsIRDFContainerUtils);
+
+function doCreateRDFFP(aTitle, aMode)
+{
+ var fp = doCreate("@mozilla.org/filepicker;1", nsIFilePicker);
+ fp.init(window, aTitle, aMode);
+ fp.appendFilter('*.rdf', '*.rdf');
+ fp.appendFilters(nsIFilePicker.filterAll);
+ return fp;
+}
+
+function goDoCommand(aCommand)
+{
+ try {
+ var controller =
+ top.document.commandDispatcher.getControllerForCommand(aCommand);
+ if (controller && controller.isCommandEnabled(aCommand))
+ controller.doCommand(aCommand);
+ }
+ catch(e) {
+ dump("An error "+e+" occurred executing the "+aCommand+" command\n");
+ }
+}
+
+function registerController(aController)
+{
+ top.controllers.appendController(aController);
+}
diff --git a/dom/xslt/tests/buster/buster-test.js b/dom/xslt/tests/buster/buster-test.js
new file mode 100644
index 000000000..2cc838685
--- /dev/null
+++ b/dom/xslt/tests/buster/buster-test.js
@@ -0,0 +1,356 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+Components.utils.import("resource://gre/modules/NetUtil.jsm");
+
+var parser = new DOMParser();
+var methodExpr = (new XPathEvaluator).createExpression("xsl:output/@method",
+ {
+ lookupNamespaceURI: function(aPrefix)
+ {
+ if (aPrefix == "xsl")
+ return "http://www.w3.org/1999/XSL/Transform";
+ return "";
+ }
+ });
+
+const nsIWebProgListener = Components.interfaces.nsIWebProgressListener;
+
+var runQueue =
+{
+ mArray : new Array(),
+ push : function(aRunItem)
+ {
+ this.mArray.push(aRunItem);
+ },
+ observe : function(aSubject, aTopic, aData)
+ {
+ var item = this.mArray.shift();
+ if (item) {
+ item.run(this);
+ }
+ },
+ run : function()
+ {
+ this.observe(null,'','');
+ }
+}
+
+var itemCache =
+{
+ mArray : new Array(),
+ getItem : function(aResource)
+ {
+ // Directory selected
+ if (kContUtils.IsSeq(runItem.prototype.kDatabase, aResource)) {
+ var aSeq = kContUtils.MakeSeq(runItem.prototype.kDatabase, aResource);
+ dump("sequence: "+aSeq+" with "+aSeq.GetCount()+" elements\n");
+ var child, children = aSeq.GetElements();
+ var m = 0, first;
+ while (children.hasMoreElements()) {
+ m += 1;
+ child = children.getNext();
+ child.QueryInterface(nsIRDFResource);
+ if (!first)
+ first = itemCache.getItem(child);
+ else
+ itemCache.getItem(child);
+ }
+ return first;
+ }
+ if (aResource.Value in this.mArray) {
+ return this.mArray[aResource.Value];
+ }
+ var retItem = new runItem(aResource);
+ this.mArray[aResource.Value] = retItem;
+ runQueue.push(retItem);
+ return retItem;
+ },
+ rerunItem : function(aResource, aObserver)
+ {
+ var anItem = new runItem(aResource);
+ this.mArray[aResource.Value] = anItem;
+ anItem.run(aObserver);
+ },
+ observe : function(aSubject, aTopic, aData)
+ {
+ this.mRun += 1;
+ if (aTopic == "success") {
+ if (aData == "yes") {
+ this.mGood += 1;
+ }
+ else {
+ this.mFalse +=1;
+ }
+ }
+ }
+}
+
+function runItem(aResource)
+{
+ this.mResource = aResource;
+ // Directory selected
+ if (kContUtils.IsSeq(this.kDatabase,this.mResource)) {
+ var aSeq = kContUtils.MakeSeq(this.kDatabase,this.mResource);
+ dump("THIS SHOULDN'T HAPPEN\n");
+ var child, children = aSeq.GetElements();
+ var m = 0;
+ while (children.hasMoreElements()) {
+ m += 1;
+ child = children.getNext();
+ child.QueryInterface(nsIRDFResource);
+ itemCache.getItem(child);
+ }
+ }
+}
+
+runItem.prototype =
+{
+ // RDF resource associated with this test
+ mResource : null,
+ // XML documents for the XSLT transformation
+ mSourceDoc : null,
+ mStyleDoc : null,
+ mResDoc : null,
+ // XML or plaintext document for the reference
+ mRefDoc : null,
+ // bitfield signaling the loaded documents
+ mLoaded : 0,
+ kSource : 1,
+ kStyle : 2,
+ kReference : 4,
+ // a observer, potential argument to run()
+ mObserver : null,
+ mSuccess : null,
+ mMethod : 'xml',
+ // XSLTProcessor, shared by the instances
+ kProcessor : new XSLTProcessor(),
+ kXalan : kStandardURL.createInstance(nsIURL),
+ kDatabase : null,
+ kObservers : new Array(),
+
+ run : function(aObserver)
+ {
+ if (aObserver && typeof(aObserver)=='function' ||
+ (typeof(aObserver)=='object' &&
+ typeof(aObserver.observe)=='function')) {
+ this.mObserver=aObserver;
+ }
+ var name = this.kDatabase.GetTarget(this.mResource, krTypeName, true);
+ if (name) {
+ var cat = this.kDatabase.GetTarget(this.mResource, krTypeCat, true);
+ var path = this.kDatabase.GetTarget(this.mResource, krTypePath, true);
+ cat = cat.QueryInterface(nsIRDFLiteral);
+ name = name.QueryInterface(nsIRDFLiteral);
+ path = path.QueryInterface(nsIRDFLiteral);
+ var xalan_fl = this.kXalan.resolve(cat.Value+"/"+path.Value);
+ var xalan_ref = this.kXalan.resolve(cat.Value+"-gold/"+path.Value);
+ this.mRefURL =
+ this.kXalan.resolve(cat.Value + "-gold/" + path.Value + ".out");
+ dump(name.Value+" links to "+xalan_fl+"\n");
+ }
+ // Directory selected
+ if (kContUtils.IsSeq(this.kDatabase,this.mResource)) {
+ return;
+ var aSeq = kContUtils.MakeSeq(this.kDatabase,this.mResource);
+ dump("sequence: "+aSeq+" with "+aSeq.GetCount()+" elements\n");
+ var child, children = aSeq.GetElements();
+ var m = 0;
+ while (children.hasMoreElements()) {
+ m += 1;
+ child = children.getNext();
+ child.QueryInterface(nsIRDFResource);
+ }
+ }
+ this.mSourceDoc = document.implementation.createDocument('', '', null);
+ this.mSourceDoc.addEventListener("load",this.onload(1),false);
+ this.mSourceDoc.load(xalan_fl+".xml");
+ this.mStyleDoc = document.implementation.createDocument('', '', null);
+ this.mStyleDoc.addEventListener("load",this.styleLoaded(),false);
+ this.mStyleDoc.load(xalan_fl+".xsl");
+ },
+
+ // nsIWebProgressListener
+ QueryInterface: function(aIID)
+ {
+ return this;
+ },
+ onStateChange: function(aProg, aRequest, aFlags, aStatus)
+ {
+ if ((aFlags & nsIWebProgListener.STATE_STOP) &&
+ (aFlags & nsIWebProgListener.STATE_IS_DOCUMENT)) {
+ aProg.removeProgressListener(this);
+ this.mRefDoc = document.getElementById('hiddenHtml').contentDocument;
+ this.fileLoaded(4);
+ }
+ },
+ onProgressChange: function(aProg, b,c,d,e,f)
+ {
+ },
+ onLocationChange: function(aProg, aRequest, aURI, aFlags)
+ {
+ },
+ onStatusChange: function(aProg, aRequest, aStatus, aMessage)
+ {
+ },
+ onSecurityChange: function(aWebProgress, aRequest, aState)
+ {
+ },
+
+ // onload handler helper
+ onload : function(file)
+ {
+ var self = this;
+ return function(e)
+ {
+ return self.fileLoaded(file);
+ };
+ },
+
+ styleLoaded : function()
+ {
+ var self = this;
+ return function(e)
+ {
+ return self.styleLoadedHelper();
+ };
+ },
+ styleLoadedHelper : function()
+ {
+ var method = methodExpr.evaluate(this.mStyleDoc.documentElement, 2,
+ null).stringValue;
+ var refContent;
+ if (!method) {
+ // implicit method, guess from result
+ refContent = this.loadTextFile(this.mRefURL);
+ if (refContent.match(/^\s*<html/gi)) {
+ method = 'html';
+ }
+ else {
+ method = 'xml';
+ }
+ }
+ this.mMethod = method;
+
+ switch (method) {
+ case 'xml':
+ if (!refContent) {
+ refContent = this.loadTextFile(this.mRefURL);
+ }
+ this.mRefDoc = parser.parseFromString(refContent, 'application/xml');
+ this.mLoaded += 4;
+ break;
+ case 'html':
+ view.loadHtml(this.mRefURL, this);
+ break;
+ case 'text':
+ if (!refContent) {
+ refContent = this.loadTextFile(this.mRefURL);
+ }
+ const ns = 'http://www.mozilla.org/TransforMiix';
+ const qn = 'transformiix:result';
+ this.mRefDoc =
+ document.implementation.createDocument(ns, qn, null);
+ var txt = this.mRefDoc.createTextNode(refContent);
+ this.mRefDoc.documentElement.appendChild(txt);
+ this.mLoaded += 4;
+ break;
+ default:
+ throw "unkown XSLT output method";
+ }
+ this.fileLoaded(2)
+ },
+
+ fileLoaded : function(mask)
+ {
+ this.mLoaded += mask;
+ if (this.mLoaded < 7) {
+ return;
+ }
+ this.doTransform();
+ },
+
+ doTransform : function()
+ {
+ this.kProcessor.reset();
+ try {
+ this.kProcessor.importStylesheet(this.mStyleDoc);
+ this.mResDoc =
+ this.kProcessor.transformToDocument(this.mSourceDoc);
+ this.mRefDoc.normalize();
+ isGood = DiffDOM(this.mResDoc.documentElement,
+ this.mRefDoc.documentElement,
+ this.mMethod == 'html');
+ } catch (e) {
+ isGood = false;
+ };
+ dump("This succeeded. "+isGood+"\n");
+ isGood = isGood.toString();
+ for (var i=0; i<this.kObservers.length; i++) {
+ var aObs = this.kObservers[i];
+ if (typeof(aObs)=='object' && typeof(aObs.observe)=='function') {
+ aObs.observe(this.mResource, 'success', isGood);
+ }
+ else if (typeof(aObs)=='function') {
+ aObs(this.mResource, 'success', isGood);
+ }
+ }
+ if (this.mObserver) {
+ if (typeof(this.mObserver)=='object') {
+ this.mObserver.observe(this.mResource, 'success', isGood);
+ }
+ else {
+ this.mObserver(this.mResource, 'success', isGood);
+ }
+ }
+ },
+
+ loadTextFile : function(url)
+ {
+ var chan = NetUtil.newChannel({
+ uri: url,
+ loadUsingSystemPrincipal: true
+ });
+ var instream = doCreate(SIS_CTRID, nsISIS);
+ instream.init(chan.open2());
+
+ return instream.read(instream.available());
+ }
+}
+
+runItem.prototype.kXalan.QueryInterface(nsIStandardURL);
+
+var cmdTestController =
+{
+ supportsCommand: function(aCommand)
+ {
+ switch(aCommand) {
+ case 'cmd_tst_run':
+ case 'cmd_tst_runall':
+ return true;
+ default:
+ }
+ return false;
+ },
+ isCommandEnabled: function(aCommand)
+ {
+ return this.supportsCommand(aCommand);
+ },
+ doCommand: function(aCommand)
+ {
+ switch(aCommand) {
+ case 'cmd_tst_run':
+ dump("cmd_tst_run\n");
+ break;
+ case 'cmd_tst_runall':
+ dump("cmd_tst_runall\n");
+ var tst_run = document.getElementById('cmd_tst_run');
+ tst_run.doCommand();
+ default:
+ }
+ }
+};
+
+registerController(cmdTestController);
diff --git a/dom/xslt/tests/buster/buster-view.js b/dom/xslt/tests/buster/buster-view.js
new file mode 100644
index 000000000..3ee4af28c
--- /dev/null
+++ b/dom/xslt/tests/buster/buster-view.js
@@ -0,0 +1,193 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+var view =
+{
+ onRun : function()
+ {
+ runQueue.mArray = new Array();
+ var sels = this.boxObject.view.selection,a=new Object(),b=new Object(),k;
+ var rowResource, name, path;
+ for (k=0;k<sels.getRangeCount();k++){
+ sels.getRangeAt(k,a,b);
+ for (var l=a.value;l<=b.value;l++) {
+ rowResource = this.builder.getResourceAtIndex(l);
+ itemCache.getItem(rowResource);
+ }
+ }
+ runQueue.run();
+ },
+ displayTest : function()
+ {
+ var current = this.boxObject.view.selection.currentIndex;
+ var rowResource = this.builder.getResourceAtIndex(current);
+ var item = itemCache.getItem(rowResource);
+ },
+ browseForRDF : function()
+ {
+ var fp = doCreateRDFFP('Xalan Description File',
+ nsIFilePicker.modeOpen);
+ var res = fp.show();
+
+ if (res == nsIFilePicker.returnOK) {
+ var furl = fp.fileURL;
+ this.setDataSource(fp.fileURL.spec);
+ }
+ },
+ dump_Good : function()
+ {
+ var enumi = this.mResultDS.GetSources(krTypeSucc, kGood, true);
+ var k = 0;
+ while (enumi.hasMoreElements()) {
+ k += 1;
+ dump(enumi.getNext().QueryInterface(nsIRDFResource).Value+"\n");
+ }
+ dump("found "+k+" good tests\n");
+ },
+ prune_ds : function()
+ {
+ if (this.mResultDS) {
+ this.mResultDS.QueryInterface(nsIRDFPurgeableDataSource).Sweep();
+ }
+ regressionStats.init()
+ itemCache.mArray = new Array();
+ },
+ setDataSource : function(aSpec)
+ {
+ var baseSpec;
+ if (aSpec) {
+ baseSpec = aSpec;
+ }
+ else {
+ baseSpec = document.getElementById("xalan_rdf").value;
+ }
+ if (this.mXalanDS && this.mXalanDS.URI == baseSpec) {
+ this.mXalanDS.QueryInterface(nsIRDFRemoteDataSource);
+ this.mXalanDS.Refresh(true);
+ }
+ else {
+ if (this.mXalanDS) {
+ this.database.RemoveDataSource(view.mXalanDS);
+ }
+ this.mXalanDS = kRDFSvc.GetDataSourceBlocking(baseSpec);
+ if (!this.mXalanDS) {
+ alert("Unable do load DataSource: "+baseSpec);
+ return;
+ }
+ this.database.AddDataSource(this.mXalanDS);
+ }
+ regressionStats.init();
+ if (!this.mResultDS) {
+ this.mResultDS = doCreate(kRDFInMemContractID,
+ nsIRDFDataSource);
+ this.database.AddDataSource(view.mResultDS);
+ if (!this.mResultDS) {
+ alert("Unable to create result InMemDatasource");
+ return;
+ }
+ }
+
+ this.builder.rebuild();
+ document.getElementById("xalan_rdf").value = baseSpec;
+ runItem.prototype.kXalan.init(runItem.prototype.kXalan.URLTYPE_STANDARD,
+ 0, baseSpec, null, null);
+ },
+ loadHtml : function(aUrl, aListener)
+ {
+ const nsIIRequestor = Components.interfaces.nsIInterfaceRequestor;
+ const nsIWebProgress = Components.interfaces.nsIWebProgress;
+ var req = this.mIframe.webNavigation.QueryInterface(nsIIRequestor);
+ var prog = req.getInterface(nsIWebProgress);
+ prog.addProgressListener(aListener, nsIWebProgress.NOTIFY_ALL);
+ this.mIframe.webNavigation.loadURI(aUrl, 0,null,null,null);
+ },
+ fillItemContext : function()
+ {
+ var index = view.boxObject.view.selection.currentIndex;
+ var res = view.builder.getResourceAtIndex(index);
+ var purp = view.mXalanDS.GetTarget(res, krTypePurp, true);
+ return (purp != null);
+ }
+}
+
+regressionStats =
+{
+ observe: function(aSubject, aTopic, aData)
+ {
+ if (aTopic != 'success') {
+ return;
+ }
+ var arc = (aData == "true") ? krTypeSuccCount : krTypeFailCount;
+ this.assertNewCount(aSubject, arc, 1);
+ },
+ init: function()
+ {
+ if (this.mRegressionDS) {
+ this.mRegressionDS.QueryInterface(nsIRDFPurgeableDataSource).Sweep();
+ }
+ else {
+ this.mRegressionDS =
+ doCreate(kRDFInMemContractID, nsIRDFDataSource);
+ view.database.AddDataSource(this.mRegressionDS);
+ }
+ },
+ getParent: function(aDS, aSource)
+ {
+ // parent chached?
+ var parent = this.mRegressionDS.GetTarget(aSource, krTypeParent, true);
+ if (!parent) {
+ var labels = view.mXalanDS.ArcLabelsIn(aSource);
+ while (labels.hasMoreElements()) {
+ var arc = labels.getNext().QueryInterface(nsIRDFResource);
+ if (arc.Value.match(this.mChildRE)) {
+ parent = view.mXalanDS.GetSource(arc, aSource, true);
+ // cache the parent
+ this.mRegressionDS.Assert(aSource, krTypeParent,
+ parent, true);
+ }
+ }
+ }
+ return parent;
+ },
+ assertNewCount: function(aSource, aArc, aIncrement)
+ {
+ var root = kRDFSvc.GetResource('urn:root');
+ var count = 0;
+ // parent chached?
+ var parent = this.getParent(view.XalanDS, aSource);
+ while (parent && !parent.EqualsNode(root)) {
+ var countRes = view.mResultDS.GetTarget(parent, aArc, true);
+ if (countRes) {
+ count = countRes.QueryInterface(nsIRDFInt).Value;
+ }
+ var newCountRes = kRDFSvc.GetIntLiteral(count + aIncrement);
+ if (!newCountRes) {
+ return;
+ }
+
+ if (countRes) {
+ view.mResultDS.Change(parent, aArc, countRes, newCountRes);
+ }
+ else {
+ view.mResultDS.Assert(parent, aArc, newCountRes, true);
+ }
+ parent = this.getParent(view.XalanDS, parent);
+ }
+ },
+ mRegressionDS: 0,
+ mChildRE: /http:\/\/www\.w3\.org\/1999\/02\/22-rdf-syntax-ns#_/
+}
+
+function rdfObserve(aSubject, aTopic, aData)
+{
+ if (aTopic == "success") {
+ var target = (aData == "true") ? kGood : kBad;
+ view.mResultDS.Assert(aSubject, krTypeSucc, target, true);
+
+ regressionStats.observe(aSubject, aTopic, aData);
+ }
+}
+
+runItem.prototype.kObservers.push(rdfObserve);
diff --git a/dom/xslt/tests/buster/buster.css b/dom/xslt/tests/buster/buster.css
new file mode 100644
index 000000000..fe11c10d9
--- /dev/null
+++ b/dom/xslt/tests/buster/buster.css
@@ -0,0 +1,20 @@
+/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+label.head {
+ padding: 5px;
+ font-size: medium;
+ font-weight: bold;
+}
+
+treechildren::-moz-tree-cell(success yes)
+{
+ background-color: green ;
+}
+
+treechildren::-moz-tree-cell(success no)
+{
+ background-color: red ;
+}
diff --git a/dom/xslt/tests/buster/buster.xul b/dom/xslt/tests/buster/buster.xul
new file mode 100644
index 000000000..7191dff4e
--- /dev/null
+++ b/dom/xslt/tests/buster/buster.xul
@@ -0,0 +1,196 @@
+<?xml version="1.0"?><!-- -*- Mode: xml; tab-width: 2; indent-tabs-mode: nil -*- -->
+<!-- This Source Code Form is subject to the terms of the Mozilla Public
+ - License, v. 2.0. If a copy of the MPL was not distributed with this
+ - file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
+
+<?xml-stylesheet href="chrome://communicator/skin/" type="text/css"?>
+<?xml-stylesheet href="buster.css" type="text/css"?>
+
+<?xul-overlay href="chrome://global/content/globalOverlay.xul"?>
+<?xul-overlay href="chrome://communicator/content/utilityOverlay.xul"?>
+
+<window id="XalanBuster"
+ xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
+ onload="onLoad()" onunload="onUnload()"
+ title="Xalan testcase harness"
+ persist="width,height"
+ width="800"
+ height="600"
+ orient="vertical">
+<script type="application/x-javascript" src="buster-statics.js" />
+<script type="application/x-javascript" src="buster-test.js" />
+<script type="application/x-javascript" src="buster-view.js" />
+<script type="application/x-javascript" src="buster-handlers.js" />
+<script type="application/x-javascript" src="result-view.js" />
+<script type="application/x-javascript" src="buster-files.js" />
+<script type="application/x-javascript" src="DumpDOM.js" />
+<script type="application/x-javascript" src="DiffDOM.js" />
+
+<commands id="busterKing">
+ <commandset id="buster_file_cmds">
+ <command id="cmd_fl_save" oncommand="goDoCommand('cmd_fl_save')" />
+ <command id="cmd_fl_import" oncommand="goDoCommand('cmd_fl_import')"/>
+ </commandset>
+ <commandset id="buster_test_cmds">
+ <command id="cmd_tst_run" oncommand="goDoCommand('cmd_tst_run')" />
+ <command id="cmd_tst_runall" oncommand="goDoCommand('cmd_tst_runall')" />
+ </commandset>
+ <commandset id="commands">
+ <command id="cmd_quit"/>
+ <command id="cmd_close" oncommand="window.close();"/>
+ </commandset>
+</commands>
+
+<keyset>
+ <key id="key_quit"/>
+ <key id="key_close"/>
+</keyset>
+
+<broadcasterset>
+ <broadcaster id="obs_orig_success" hidden="true"/>
+ <broadcaster id="not_yet" disabled="true"/>
+</broadcasterset>
+
+
+<menubar>
+ <menu id="menu_File" label="File" accesskey="f">
+ <menupopup id="menu_FilePopup">
+ <menuitem label="Save results ..." accesskey="s"
+ observes="cmd_fl_save"/>
+ <menuitem label="Import results ..." accesskey="i"
+ observes="cmd_fl_import"/>
+ <menuitem id="menu_close"/>
+ </menupopup>
+ </menu>
+ <menu id="busterTests" label="Tests" accesskey="t">
+ <menupopup id="tests-popup">
+ <menuitem label="run a test" accesskey="r"
+ observes="cmd_tst_run"/>
+ <menuitem label="run all tests" accesskey="a"
+ observes="cmd_tst_runall"/>
+ </menupopup>
+ </menu>
+</menubar>
+
+<popupset>
+ <popup id="itemcontext" onpopupshowing="return view.fillItemContext();">
+ <menuitem label="View Test" oncommand="onNewResultView(event)"/>
+ </popup>
+</popupset>
+
+<hbox>
+ <button label="check all" oncommand="check(true)" observes="not_yet"/>
+ <button label="uncheck all" oncommand="check(false)" observes="not_yet"/>
+ <button label="reset success" oncommand="view.prune_ds()" />
+ <button label="run checked tests" oncommand="view.onRun()" />
+</hbox>
+<hbox>
+ <label value="Xalan index: " class="head"/>
+ <textbox id="xalan_rdf" persist="url" crop="end" size="40"/>
+ <button label="browse..." oncommand="view.browseForRDF()" />
+</hbox>
+<hbox>
+<groupbox orient="horizontal"><caption label="search" />
+ <button label="Search for " oncommand="select()" observes="not_yet"/>
+ <textbox style="width: 10em;" id="search-name" persist="value" /><label value=" in " />
+ <menulist id="search-field" persist="data" observes="not_yet">
+ <menupopup>
+ <menuitem value="1" label="Name" />
+ <menuitem value="2" label="Purpose" />
+ <menuitem value="3" label="Comment" />
+ </menupopup>
+ </menulist>
+</groupbox>
+<spacer flex="1" /></hbox>
+
+<tree id="out" flex="1" flags="dont-build-content" hidecolumnpicker="true"
+ datasources="rdf:null" ref="urn:root" context="itemcontext">
+ <treecols>
+ <treecol id="NameColumn" flex="1" label="Name" sort="?name"
+ primary="true" />
+ <splitter class="tree-splitter" />
+ <treecol id="PurpsColumn" flex="2" label="Purpose" sort="?purp" />
+ <splitter class="tree-splitter" />
+ <treecol id="SuccessColumn" flex="0" label="Success" />
+ <splitter class="tree-splitter" observes="obs_orig_success" />
+ <treecol id="OrigSuccessColumn" flex="0" label="Previously"
+ observes="obs_orig_success" />
+ </treecols>
+ <template>
+ <rule>
+ <conditions>
+ <content uri="?uri" />
+ <member container="?uri" child="?subheading" />
+ <triple subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#purp"
+ object="?purp" />
+ </conditions>
+
+ <bindings>
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#name"
+ object="?name" />
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#succ"
+ object="?succ" />
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#orig_succ"
+ object="?orig_succ" />
+ </bindings>
+
+ <action>
+ <treechildren>
+ <treeitem uri="?subheading">
+ <treerow>
+ <treecell ref="NameColumn" label="?name" />
+ <treecell ref="PurpsColumn" label="?purp" />
+ <treecell ref="SuccessColumn" label="?succ"
+ properties="success ?succ"/>
+ <treecell ref="OrigSuccessColumn" label="?orig_succ"
+ properties="success ?orig_succ" />
+ </treerow>
+ </treeitem>
+ </treechildren>
+ </action>
+ </rule>
+ <rule>
+ <conditions>
+ <content uri="?uri" />
+ <member container="?uri" child="?subheading" />
+ </conditions>
+
+ <bindings>
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#dir"
+ object="?dir" />
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#succCount"
+ object="?succ" />
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#failCount"
+ object="?fail" />
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#orig_succCount"
+ object="?orig_succ" />
+ <binding subject="?subheading"
+ predicate="http://home.netscape.com/NC-rdf#orig_failCount"
+ object="?orig_fail" />
+ </bindings>
+
+ <action>
+ <treechildren>
+ <treeitem uri="?subheading">
+ <treerow>
+ <treecell ref="NameColumn" label="?dir" />
+ <treecell ref="PurpsColumn" label="" />
+ <treecell ref="SuccessColumn" label="?succ / ?fail" />
+ <treecell ref="OrigSuccessColumn" label="?orig_succ / ?orig_fail" />
+ </treerow>
+ </treeitem>
+ </treechildren>
+ </action>
+ </rule>
+ </template>
+</tree>
+<iframe style="visibility:hidden; height:0px;" id="hiddenHtml" />
+</window>
diff --git a/dom/xslt/tests/buster/helper/generate-rdf.pl b/dom/xslt/tests/buster/helper/generate-rdf.pl
new file mode 100644
index 000000000..c2bdc7b92
--- /dev/null
+++ b/dom/xslt/tests/buster/helper/generate-rdf.pl
@@ -0,0 +1,95 @@
+use File::Spec;
+
+my(@chunks, @list, $entry, $main_cats, $spacing);
+@list = ('conf', 'perf');
+foreach $entry (@list) {
+ $main_cats .= " <rdf:li><rdf:Description about=\"urn:x-buster:$entry\" nc:dir=\"$entry\" /></rdf:li>\n";
+ go_in($entry, '', $entry);
+}
+if ($ARGV[0]) {
+ open OUTPUT, ">$ARGV[0]";
+}
+else {
+ open OUTPUT, ">xalan.rdf";
+};
+select(OUTPUT);
+print '<?xml version="1.0"?>
+
+<rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
+ xmlns:nc="http://home.netscape.com/NC-rdf#">
+ <rdf:Seq about="urn:root">
+' . $main_cats . ' </rdf:Seq>
+';
+print join('',@chunks);
+print '</rdf:RDF>
+';
+exit 0;
+
+sub go_in {
+ my($current, $about, $cat) = @_;
+ my (@list, $entry, @subdirs, @files, @purps, $rdf);
+ chdir $current;
+ @list = <*>;
+
+ LOOP: foreach $entry (@list) {
+ next LOOP if $entry=~/^CVS$/;
+ if (! -d $entry) {
+ if ($entry=~/^($current.*)\.xsl$/) {
+ local $source = $entry;
+ $source=~s/xsl$/xml/;
+ next LOOP if ! -f $source;
+ $entry=~/^($current.*)\.xsl$/;
+ push(@files, $1);
+ local ($purp, $purp_open);
+ open STYLE, $entry;
+ $purp_open = 0;
+ while (<STYLE>) {
+ if (/<!--\s+purpose: (.+)\s*-->/i) {
+ $purp .= $1;
+ }
+ elsif (/<!--\s+purpose: (.+)\s*$/i) {
+ $purp_open = 1;
+ $purp .= $1;
+ }
+ elsif ($purp_open) {
+ if (/\s*(\s.+)\s*-->/) {
+ $purp_open = 0;
+ $purp .= $1;
+ }
+ elsif (/\s*(\s.+)\s*$/) {
+ $purp .= $1;
+ }
+ }
+ }
+ $purp=~s/"/'/g; $purp=~s/&/&amp;/g; $purp=~s/</&lt;/g;
+ $purp=~s/\r/ /g; $purp=~s/\s\s/ /g; $purp=~s/\s$//g;
+ push(@purps, $purp);
+ }
+ }
+ else {
+ push(@subdirs, $entry);
+ }
+ }
+
+ if (@subdirs > 0 || @files > 0) {
+ my $topic = $about.$current; $topic=~s/\///g;
+ $rdf = ' <rdf:Seq about="urn:x-buster:'.$topic."\">\n";
+ foreach $entry (@subdirs) {
+ if (go_in($entry, $about.$current.'/', $cat)) {
+ my $id = 'urn:x-buster:'.$about.$current.$entry; $id=~s/\///g;
+ $rdf .= " <rdf:li><rdf:Description about=\"$id\" nc:dir=\"$entry\" /></rdf:li>\n";
+ }
+ }
+ for (my $i=0; $i < @files; $i++) {
+ my $uri = $about.$current.'/'.$files[$i];
+ $uri=~s/[^\/]+\///;
+ my $id = $uri; $id=~s/\///g;
+ $rdf .= " <rdf:li><rdf:Description about=\"urn:x-buster:$files[$i]\" nc:name=\"$files[$i]\" nc:purp=\"$purps[$i]\" nc:path=\"$uri\" nc:category=\"$cat\" /></rdf:li>\n";
+ }
+ $rdf .= " </rdf:Seq>\n";
+ push(@chunks, $rdf);
+ }
+
+ chdir File::Spec->updir;
+ return (@subdirs > 0 || @files > 0);
+}
diff --git a/dom/xslt/tests/buster/install.js b/dom/xslt/tests/buster/install.js
new file mode 100644
index 000000000..0306db692
--- /dev/null
+++ b/dom/xslt/tests/buster/install.js
@@ -0,0 +1,17 @@
+const X_APP = "Buster";
+const X_VER = "2.0"
+const X_JAR_FILE = "xslt-qa.jar";
+
+var err = initInstall("Install " + X_APP, X_APP, X_VER);
+logComment("initInstall: " + err);
+logComment( "Installation started ..." );
+addFile("We're on our way ...", X_JAR_FILE, getFolder("chrome"), "");
+registerChrome(CONTENT|DELAYED_CHROME, getFolder("chrome", X_JAR_FILE), "content/xslt-qa/");
+err = getLastError();
+if (err == SUCCESS) {
+ performInstall();
+ alert("Please restart Mozilla");
+}
+else {
+ cancelInstall();
+}
diff --git a/dom/xslt/tests/buster/jar.mn b/dom/xslt/tests/buster/jar.mn
new file mode 100644
index 000000000..af7e395f0
--- /dev/null
+++ b/dom/xslt/tests/buster/jar.mn
@@ -0,0 +1,18 @@
+xslt-qa.jar:
+% content xslt-qa %content/xslt-qa/
+% overlay chrome://communicator/content/tasksOverlay.xul chrome://xslt-qa/content/xslt-qa-overlay.xul
+ content/xslt-qa/xslt-qa-overlay.xul
+ content/xslt-qa/xslt-qa-overlay.js
+ content/xslt-qa/buster/buster.xul
+ content/xslt-qa/buster/buster.css
+ content/xslt-qa/buster/buster-statics.js
+ content/xslt-qa/buster/buster-handlers.js
+ content/xslt-qa/buster/buster-files.js
+ content/xslt-qa/buster/buster-test.js
+ content/xslt-qa/buster/buster-view.js
+ content/xslt-qa/buster/result-view.xul
+ content/xslt-qa/buster/result-inspector.xul
+ content/xslt-qa/buster/result-view.css
+ content/xslt-qa/buster/result-view.js
+ content/xslt-qa/buster/DumpDOM.js
+ content/xslt-qa/buster/DiffDOM.js
diff --git a/dom/xslt/tests/buster/result-inspector.xul b/dom/xslt/tests/buster/result-inspector.xul
new file mode 100644
index 000000000..77c3ce180
--- /dev/null
+++ b/dom/xslt/tests/buster/result-inspector.xul
@@ -0,0 +1,37 @@
+<?xml version="1.0"?><!-- -*- Mode: xml; tab-width: 2; indent-tabs-mode: nil -*- -->
+<!-- This Source Code Form is subject to the terms of the Mozilla Public
+ - License, v. 2.0. If a copy of the MPL was not distributed with this
+ - file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
+
+<!DOCTYPE window [
+ <!ENTITY % dtd1 SYSTEM "chrome://inspector/locale/inspector.dtd"> %dtd1;
+ <!ENTITY % dtd2 SYSTEM "chrome://inspector/content/util.dtd"> %dtd2;
+]>
+
+<?xul-overlay href="chrome://inspector/content/commandOverlay.xul"?>
+<?xul-overlay href="chrome://inspector/content/keysetOverlay.xul"?>
+<?xul-overlay href="chrome://inspector/content/popupOverlay.xul"?>
+
+<?xml-stylesheet href="chrome://inspector/skin/inspectorWindow.css"?>
+
+<window class="color-dialog"
+ title="&Inspector.title;"
+ xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
+
+ <script type="application/x-javascript" src="chrome://inspector/content/ViewerRegistry.js"/>
+ <script type="application/x-javascript" src="chrome://inspector/content/utils.js"/>
+ <script type="application/x-javascript" src="chrome://inspector/content/jsutil/xpcom/XPCU.js"/>
+ <script type="application/x-javascript" src="chrome://inspector/content/jsutil/rdf/RDFU.js"/>
+ <script type="application/x-javascript" src="chrome://inspector/content/jsutil/rdf/RDFArray.js"/>
+ <script type="application/x-javascript" src="chrome://inspector/content/jsutil/events/ObserverManager.js"/>
+ <script type="application/x-javascript" src="chrome://inspector/content/jsutil/xul/FrameExchange.js"/>
+
+ <commandset id="cmdsGlobalCommands"/>
+ <keyset id="ksGlobalKeyset"/>
+ <popupset id="ppsViewerPopupset"/>
+
+ <domi-panelset id="bxPanelSet" flex="1" viewercommandset="cmdsGlobalCommands">
+ <domi-panel title="&bxDocPanel.title;" flex="1"/>
+ </domi-panelset>
+
+</window>
diff --git a/dom/xslt/tests/buster/result-view.css b/dom/xslt/tests/buster/result-view.css
new file mode 100644
index 000000000..b869cc12b
--- /dev/null
+++ b/dom/xslt/tests/buster/result-view.css
@@ -0,0 +1,16 @@
+label.heading {
+ font-size: medium;
+ font-weight: bold;
+}
+
+button.close {
+ font-size: small;
+}
+
+iframe {
+ padding-left: 10px;
+}
+
+vbox.hidden {
+ display: none;
+}
diff --git a/dom/xslt/tests/buster/result-view.js b/dom/xslt/tests/buster/result-view.js
new file mode 100644
index 000000000..de1b8c881
--- /dev/null
+++ b/dom/xslt/tests/buster/result-view.js
@@ -0,0 +1,105 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+function onNewResultView(event)
+{
+ dump("onNewResultView\n");
+ const db = runItem.prototype.kDatabase;
+ const kXalan = runItem.prototype.kXalan;
+ var index = view.boxObject.view.selection.currentIndex;
+ var res = view.builder.getResourceAtIndex(index);
+ var name = db.GetTarget(res, krTypeName, true);
+ if (!name) {
+ return false;
+ }
+ var cat = db.GetTarget(res, krTypeCat, true);
+ var path = db.GetTarget(res, krTypePath, true);
+ cat = cat.QueryInterface(nsIRDFLiteral);
+ name = name.QueryInterface(nsIRDFLiteral);
+ path = path.QueryInterface(nsIRDFLiteral);
+ xalan_fl = kXalan.resolve(cat.Value+"/"+path.Value);
+ xalan_ref = kXalan.resolve(cat.Value+"-gold/"+path.Value);
+ var currentResultItem = new Object();
+ currentResultItem.testpath = xalan_fl;
+ currentResultItem.refpath = xalan_ref;
+ var currentRunItem = itemCache.getItem(res);
+ // XXX todo, keep a list of these windows, so that we can close them.
+ resultWin = window.openDialog('result-view.xul','_blank',
+ 'chrome,resizable,dialog=no',
+ currentResultItem, currentRunItem);
+ return true;
+}
+
+var refInspector;
+var resInspector;
+
+function onResultViewLoad(event)
+{
+ dump("onResultViewLoad\n");
+ aResultItem = window.arguments[0];
+ aRunItem = window.arguments[1];
+ var loadFlags = Components.interfaces.nsIWebNavigation.LOAD_FLAGS_NONE;
+ document.getElementById('src').webNavigation.loadURI('view-source:'+
+ aResultItem.testpath+'.xml', loadFlags, null, null, null);
+ document.getElementById('style').webNavigation.loadURI('view-source:'+
+ aResultItem.testpath+'.xsl', loadFlags, null, null, null);
+
+ if (aRunItem && aRunItem.mRefDoc && aRunItem.mResDoc) {
+ document.getElementById("refSourceBox").setAttribute("class", "hidden");
+ refInspector = new ObjectApp();
+ refInspector.initialize("refInsp", aRunItem.mRefDoc);
+ resInspector = new ObjectApp();
+ resInspector.initialize("resInsp", aRunItem.mResDoc);
+ }
+ else {
+ document.getElementById("inspectorBox").setAttribute("class", "hidden");
+ document.getElementById('ref').webNavigation.loadURI('view-source:'+
+ aResultItem.refpath+'.out', loadFlags, null, null, null);
+ }
+ return true;
+}
+
+function onResultViewUnload(event)
+{
+ dump("onResultUnload\n");
+}
+
+function ObjectApp()
+{
+}
+
+ObjectApp.prototype =
+{
+ mDoc: null,
+ mPanelSet: null,
+
+ initialize: function(aId, aDoc)
+ {
+ this.mDoc = aDoc;
+ this.mPanelSet = document.getElementById(aId).contentDocument.getElementById("bxPanelSet");
+ this.mPanelSet.addObserver("panelsetready", this, false);
+ this.mPanelSet.initialize();
+ },
+
+ doViewerCommand: function(aCommand)
+ {
+ this.mPanelSet.execCommand(aCommand);
+ },
+
+ getViewer: function(aUID)
+ {
+ return this.mPanelSet.registry.getViewerByUID(aUID);
+ },
+
+ onEvent: function(aEvent)
+ {
+ switch (aEvent.type) {
+ case "panelsetready":
+ {
+ this.mPanelSet.getPanel(0).subject = this.mDoc;
+ }
+ }
+ }
+};
diff --git a/dom/xslt/tests/buster/result-view.xul b/dom/xslt/tests/buster/result-view.xul
new file mode 100644
index 000000000..e402067aa
--- /dev/null
+++ b/dom/xslt/tests/buster/result-view.xul
@@ -0,0 +1,46 @@
+<?xml version="1.0"?><!-- -*- Mode: xml; tab-width: 2; indent-tabs-mode: nil -*- -->
+<!-- This Source Code Form is subject to the terms of the Mozilla Public
+ - License, v. 2.0. If a copy of the MPL was not distributed with this
+ - file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
+
+<?xml-stylesheet href="chrome://communicator/skin/" type="text/css"?>
+<?xml-stylesheet href="result-view.css" type="text/css"?>
+
+<window id="buster-result-view" title="Xalan testcase details"
+ xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
+ orient="vertical" persist="width height"
+ onload="onResultViewLoad()" onunload="onResultViewUnload()">
+ <script type="application/x-javascript" src="DumpDOM.js" />
+ <script type="application/x-javascript" src="buster-statics.js" />
+ <script type="application/x-javascript" src="buster-test.js" />
+ <script type="application/x-javascript" src="result-view.js" />
+
+ <hbox>
+ <button class="close" label="close this window"
+ oncommand="window.close()" />
+ </hbox>
+ <vbox flex="1">
+ <label class="heading" value="XML Source:" />
+ <iframe flex="1" id="src" />
+ </vbox>
+ <vbox flex="1">
+ <label class="heading" value="XSL Source:" />
+ <iframe flex="1" id="style" />
+ </vbox>
+ <vbox flex="1" id="refSourceBox">
+ <label class="heading" value="Reference Source:" />
+ <iframe flex="1" id="ref" />
+ </vbox>
+ <vbox flex="2" id="inspectorBox">
+ <hbox flex="1">
+ <vbox flex="1">
+ <label class="heading" value="Reference" />
+ <iframe flex="1" id="refInsp" src="result-inspector.xul" />
+ </vbox>
+ <vbox flex="1">
+ <label class="heading" value="Result" />
+ <iframe flex="1" id="resInsp" src="result-inspector.xul" />
+ </vbox>
+ </hbox>
+ </vbox>
+</window>
diff --git a/dom/xslt/tests/buster/xslt-qa-overlay.js b/dom/xslt/tests/buster/xslt-qa-overlay.js
new file mode 100644
index 000000000..41bd764a5
--- /dev/null
+++ b/dom/xslt/tests/buster/xslt-qa-overlay.js
@@ -0,0 +1,10 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 4 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+function onStartBuster()
+{
+ window.open('chrome://xslt-qa/content/buster/buster.xul',
+ 'buster', 'chrome,resizable');
+}
diff --git a/dom/xslt/tests/buster/xslt-qa-overlay.xul b/dom/xslt/tests/buster/xslt-qa-overlay.xul
new file mode 100644
index 000000000..294d27f92
--- /dev/null
+++ b/dom/xslt/tests/buster/xslt-qa-overlay.xul
@@ -0,0 +1,12 @@
+<?xml version="1.0"?><!-- -*- Mode: xml; tab-width: 2; indent-tabs-mode: nil -*- -->
+<!-- This Source Code Form is subject to the terms of the Mozilla Public
+ - License, v. 2.0. If a copy of the MPL was not distributed with this
+ - file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
+
+<overlay id="xsltToolsMenuID"
+ xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
+ <script src="xslt-qa-overlay.js" />
+ <menupopup id="toolsPopup">
+ <menuitem label="Xalan Tests" oncommand="onStartBuster()"/>
+ </menupopup>
+</overlay>
diff --git a/dom/xslt/tests/mochitest/file_bug1135764.xml b/dom/xslt/tests/mochitest/file_bug1135764.xml
new file mode 100644
index 000000000..b9da87e5e
--- /dev/null
+++ b/dom/xslt/tests/mochitest/file_bug1135764.xml
@@ -0,0 +1,3 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<?xml-stylesheet type="text/xsl" href="file_bug1135764.xsl"?>
+<root/>
diff --git a/dom/xslt/tests/mochitest/file_bug1135764.xsl b/dom/xslt/tests/mochitest/file_bug1135764.xsl
new file mode 100644
index 000000000..e739086cb
--- /dev/null
+++ b/dom/xslt/tests/mochitest/file_bug1135764.xsl
@@ -0,0 +1,19 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
+
+<xsl:output method="html"
+ indent="yes"
+ version="5.0"
+ doctype-system="about:legacy-compat"/>
+
+<xsl:template match="/">
+<html>
+<head>
+</head>
+ <body>
+ Some text
+ </body>
+</html>
+</xsl:template>
+
+</xsl:stylesheet>
diff --git a/dom/xslt/tests/mochitest/mochitest.ini b/dom/xslt/tests/mochitest/mochitest.ini
new file mode 100644
index 000000000..53a6d001c
--- /dev/null
+++ b/dom/xslt/tests/mochitest/mochitest.ini
@@ -0,0 +1,20 @@
+[DEFAULT]
+
+[test_bug1072116.html]
+[test_bug319374.xhtml]
+[test_bug427060.html]
+[test_bug440974.html]
+[test_bug453441.html]
+[test_bug468208.html]
+[test_bug511487.html]
+[test_bug551412.html]
+[test_bug551654.html]
+[test_bug566629.html]
+[test_bug566629.xhtml]
+[test_bug603159.html]
+[test_bug616774.html]
+[test_bug667315.html]
+[test_bug1135764.html]
+support-files = file_bug1135764.xml file_bug1135764.xsl
+[test_exslt_regex.html]
+[test_parameter.html]
diff --git a/dom/xslt/tests/mochitest/test_bug1072116.html b/dom/xslt/tests/mochitest/test_bug1072116.html
new file mode 100644
index 000000000..2d0624725
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug1072116.html
@@ -0,0 +1,37 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=1072116
+-->
+<head>
+ <title>Test for Bug 1072116</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=1072116">Mozilla Bug 1072116</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script type="application/javascript">
+
+/** Test for Bug 1072116 **/
+var attr = document.createAttribute("c");
+
+var xpathExpr = document.createExpression('a', null);
+
+var status = false;
+try {
+ xpathExpr.evaluate(attr, null, null, null, null);
+} catch(e) {
+ status = true;
+}
+
+ok(status, "Still alive \\o/");
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug1135764.html b/dom/xslt/tests/mochitest/test_bug1135764.html
new file mode 100644
index 000000000..5a7410e37
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug1135764.html
@@ -0,0 +1,53 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=1135764
+-->
+<head>
+ <meta charset="utf-8">
+ <title>Test for Bug 1135764</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+ <script type="application/javascript">
+
+ /** Test for Bug 1135764 **/
+ SimpleTest.waitForExplicitFinish();
+ var counter = 0;
+ var startTimelineValue;
+
+ function waitATick() {
+ ++counter;
+ if (counter == 1) {
+ frames[0].requestAnimationFrame(waitATick);
+ return;
+ }
+ ok(frames[0].document.timeline.currentTime !== startTimelineValue,
+ "The timeline in an XSLT-transformed document should still advance");
+ SimpleTest.finish();
+ }
+ addLoadEvent(function() {
+ SpecialPowers.pushPrefEnv(
+ { "set": [[ "dom.animations-api.core.enabled", true]] },
+ function() {
+ var ifr = document.querySelector("iframe");
+ ifr.onload = function() {
+ startTimelineValue = frames[0].document.timeline.currentTime;
+ frames[0].requestAnimationFrame(waitATick);
+ }
+ ifr.src = "file_bug1135764.xml";
+ })
+ })
+ </script>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=1135764">Mozilla Bug 1135764</a>
+<p id="display">
+ <iframe></iframe>
+</p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug319374.xhtml b/dom/xslt/tests/mochitest/test_bug319374.xhtml
new file mode 100644
index 000000000..2342b3447
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug319374.xhtml
@@ -0,0 +1,109 @@
+<?xml version="1.0"?>
+<html xmlns="http://www.w3.org/1999/xhtml"
+ xmlns:xbl="http://www.mozilla.org/xbl">
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=319374
+-->
+<head>
+ <title>Test for Bug 319374</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+ <xbl:bindings>
+ <xbl:binding id="test">
+ <xbl:content>
+ <span attr="attribute"><span></span></span><span> anon text </span><br/>
+ </xbl:content>
+ </xbl:binding>
+ </xbl:bindings>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=319374">Mozilla Bug 319374</a>
+<p id="display"></p>
+<div id="content"><span style="-moz-binding: url(#test)"/><span style="-moz-binding: url(#test)"/><span style="-moz-binding: url(#test)"/></div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+<![CDATA[
+
+/** Test for Bug 319374 **/
+
+ function testChangesInAnonymousTree() {
+ // Test 1: Make sure that modifying anonymous content doesn't
+ // cause non-anonymous XPath result to throw exceptions..
+ var counter = 0;
+ var error = null;
+ function getAnonymousNodes(e) {
+ return SpecialPowers.wrap(document).getAnonymousNodes(e);
+ }
+ try {
+ var xp = new XPathEvaluator();
+ var result = xp.evaluate("*",
+ document.getElementById('content'),
+ null,
+ XPathResult.UNORDERED_NODE_ITERATOR_TYPE,
+ null);
+ var res = null;
+ while (res = result.iterateNext()) {
+ ++counter;
+ var anon = getAnonymousNodes(res);
+ anon[0].removeChild(anon[0].firstChild); // Removing a child node
+ anon[0].removeAttribute("attr1"); // Removing an attribute
+ anon[1].firstChild.data = "anon text changed" // Modifying text data
+ }
+ } catch (e) {
+ error = e;
+ }
+ ok(!error, error);
+ ok(counter == 3, "XPathEvaluator should have found 3 elements.")
+
+ // Test 2: If the context node is in anonymous content, changing some
+ // other anonymous tree shouldn't cause XPath result to throw.
+ var anonAttr1 =
+ getAnonymousNodes(document.getElementById('content').
+ firstChild)[0].getAttributeNode('attr');
+ var anonAttr2 =
+ getAnonymousNodes(document.getElementById('content').
+ lastChild)[0].getAttributeNode('attr');
+ var resultAttr = null;
+ try {
+ var xp2 = SpecialPowers.wrap(xp).evaluate(".",
+ anonAttr1,
+ null,
+ XPathResult.UNORDERED_NODE_ITERATOR_TYPE,
+ null);
+ // Attribute changing in a different anonymous tree.
+ anonAttr2.value = "foo";
+ resultAttr = xp2.iterateNext();
+ ok(SpecialPowers.compare(resultAttr, anonAttr1), "XPathEvaluator returned wrong attribute!")
+ } catch (e) {
+ ok(false, e);
+ }
+
+ // Test 3: If the anonymous tree in which context node is in is modified,
+ // XPath result should throw when iterateNext() is called.
+ resultAttr = null;
+ try {
+ var xp3 = xp.evaluate(".",
+ anonAttr1,
+ null,
+ XPathResult.UNORDERED_NODE_ITERATOR_TYPE,
+ null);
+ // Attribute changing in the same anonymous tree.
+ anonAttr1.ownerElement.setAttribute("foo", "bar");
+ resultAttr = xp3.iterateNext();
+ ok(resultAttr == anonAttr1,
+ "XPathEvaluator should have thrown an exception!")
+ } catch (e) {
+ ok(true, e);
+ }
+
+ SimpleTest.finish();
+ }
+
+ SimpleTest.waitForExplicitFinish();
+ addLoadEvent(testChangesInAnonymousTree);
+]]>
+</script>
+</pre>
+</body>
+</html>
+
diff --git a/dom/xslt/tests/mochitest/test_bug427060.html b/dom/xslt/tests/mochitest/test_bug427060.html
new file mode 100644
index 000000000..89bcb5255
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug427060.html
@@ -0,0 +1,49 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=427060
+-->
+<head>
+ <title>Test for Bug 427060</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=427060">Mozilla Bug 427060</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+
+/** Test for Bug 427060 **/
+
+var xmldoc, xsltdoc;
+
+xmldoc = new DOMParser().parseFromString('<opml version="1.0"><body></body></opml>', "text/xml");
+xsltdoc = new DOMParser().parseFromString('<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">\n\
+ <xsl:template match="/opml">\n\
+ <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">\n\
+ <head>\n\
+ <base target="_blank"></base>\n\
+ </head>\n\
+ <body></body>\n\
+ </html>\n\
+ </xsl:template>\n\
+ </xsl:stylesheet>', "text/xml");
+
+var processor = new XSLTProcessor;
+processor.importStylesheet(xsltdoc);
+try
+{
+ var result = processor.transformToDocument(xmldoc);
+}
+catch (e)
+{
+}
+ok(result && result instanceof Document, "XSLT transform should have created a document");
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug440974.html b/dom/xslt/tests/mochitest/test_bug440974.html
new file mode 100644
index 000000000..33b73e6de
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug440974.html
@@ -0,0 +1,46 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=440974
+-->
+<head>
+ <title>Test for Bug 440974</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=440974">Mozilla Bug 440974</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+
+/** Test for Bug 440974 **/
+
+function isTxResult(node)
+{
+ return node.namespaceURI == "http://www.mozilla.org/TransforMiix" &&
+ node.localName == "result";
+}
+
+var xmldoc, xsltdoc;
+
+xmldoc = new DOMParser().parseFromString('<items><item><id>1</id></item><item><id>2</id></item><item><id>3</id></item></items>', "text/xml");
+xsltdoc = new DOMParser().parseFromString('<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">\n\
+ <xsl:output method="xml" />\n\
+ <xsl:template match="item"><foo id="{id}"/></xsl:template>\n\
+ </xsl:stylesheet>', "text/xml");
+
+var processor = new XSLTProcessor;
+processor.importStylesheet(xsltdoc);
+var result = processor.transformToDocument(xmldoc);
+var resultElements = Array.prototype.filter.call(result.getElementsByTagName('*'), isTxResult);
+is(resultElements.length, 1, "there should be only one 'transformiix:result' element");
+is(resultElements[0], result.documentElement, "the 'transformiix:result' element should be the document element");
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug453441.html b/dom/xslt/tests/mochitest/test_bug453441.html
new file mode 100644
index 000000000..4decae56c
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug453441.html
@@ -0,0 +1,57 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=453441
+-->
+<head>
+ <title>Test for Bug 453441</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=453441">Mozilla Bug 453441</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+
+/** Test for Bug 453441 **/
+
+function tryImportStylesheet(xml, valid)
+{
+ var processor = new XSLTProcessor;
+
+ var xsltdoc = new DOMParser().parseFromString(xml, "text/xml");
+ try
+ {
+ processor.importStylesheet(xsltdoc);
+ ok(valid, "should be able to parse this XSLT stylesheet");
+ }
+ catch (e)
+ {
+ ok(!valid, "should not be able to parse this XSLT stylesheet");
+ }
+}
+
+tryImportStylesheet(
+ '<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">\n\
+ <xsl:template match="/">\n\
+ <html xmlns="http://www.w3.org/1999/xhtml" xsl:version="1.0" />\n\
+ </xsl:template>\n\
+ </xsl:stylesheet>'
+, true);
+
+tryImportStylesheet(
+ '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" />'
+, false);
+
+tryImportStylesheet(
+ '<xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" />'
+, false);
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug468208.html b/dom/xslt/tests/mochitest/test_bug468208.html
new file mode 100644
index 000000000..3da0349be
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug468208.html
@@ -0,0 +1,35 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=468208
+-->
+<head>
+ <title>Test for Bug 468208</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=468208">Mozilla Bug 468208</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+
+/** Test for Bug 468208 **/
+var xslt =
+ '<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">\n\
+ <xsl:strip-space elements="color"/>\n\
+ </xsl:stylesheet>'
+;
+var xsltdoc = new DOMParser().parseFromString(xslt, "text/xml");
+
+var processor = new XSLTProcessor;
+processor.importStylesheet(xsltdoc);
+ok(true, "XSLT shouldn't leak");
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug511487.html b/dom/xslt/tests/mochitest/test_bug511487.html
new file mode 100644
index 000000000..b5cd21cf6
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug511487.html
@@ -0,0 +1,59 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=511487
+-->
+<head>
+ <title>Test for Bug 511487</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=511487">Mozilla Bug 511487</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script type="application/javascript">
+
+/** Test for Bug 511487 **/
+
+ var didTransform = false;
+ var processor = new XSLTProcessor();
+ var style =
+ '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0" xmlns="http://www.w3.org/1999/xhtml">' +
+ '<xsl:output method="xml" version="1.0" encoding="UTF-8" doctype-system="http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd" doctype-public="-//W3C//DTD XHTML 1.0 Transitional//EN" />' +
+ '<xsl:template match="wml">' +
+ '<html xmlns="http://www.w3.org/1999/xhtml">' +
+ '<head>' +
+ '<title>XSLT test</title>' +
+ '</head>' +
+ '<body onload="window.alert(this)">' +
+ '</body>' +
+ '</html>' +
+ '</xsl:template>' +
+ '</xsl:stylesheet>';
+ var styleDoc = new DOMParser().parseFromString (style, "text/xml");
+
+ var data =
+ '<?xml version="1.0"?>' +
+ '<!DOCTYPE wml PUBLIC "-//WAPFORUM//DTD WML 1.1//EN" "http://www.wapforum.org/DTD/wml_1.1.xml">' +
+ '<wml><card><p>paragraph</p></card></wml>';
+ var originalDoc = new DOMParser().parseFromString(data, "text/xml");
+
+ processor.importStylesheet(styleDoc);
+ try {
+ var transformedDocument = processor.transformToDocument(originalDoc);
+ didTransform = true;
+ } catch (e) {
+ ok(false, e);
+ }
+
+ ok(didTransform, "transformToDocument didn't succeed!");
+
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug551412.html b/dom/xslt/tests/mochitest/test_bug551412.html
new file mode 100644
index 000000000..c6f5e13e8
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug551412.html
@@ -0,0 +1,48 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=551412
+-->
+<head>
+ <title>Test for Bug 551412</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=551412">Mozilla Bug 551412</a>
+<p id="display"></p>
+<div id="content" style="display: none"></div>
+<pre id="test">
+<script type="application/javascript">
+
+/** Test for Bug 551412 **/
+
+ var processor = new XSLTProcessor();
+ var style =
+ '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" ' +
+ 'xmlns:exsl="http://exslt.org/common" ' +
+ 'version="1.0">' +
+ '<xsl:output method="html"/>' +
+ '<xsl:variable name="rtf">1 <b>2</b> 3</xsl:variable>' +
+ '<xsl:template match="/">' +
+ '<xsl:copy-of select="exsl:node-set($rtf)"/>' +
+ '</xsl:template>' +
+ '</xsl:stylesheet>';
+ var styleDoc = new DOMParser().parseFromString (style, "text/xml");
+
+ var data =
+ '<root/>';
+ var originalDoc = new DOMParser().parseFromString(data, "text/xml");
+
+ processor.importStylesheet(styleDoc);
+
+ var fragment = processor.transformToFragment(originalDoc, document);
+ var content = document.getElementById("content");
+ content.appendChild(fragment);
+ is(content.innerHTML, "1 <b>2</b> 3",
+ "Result of transform should be '1 <b>2</b> 3'");
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug551654.html b/dom/xslt/tests/mochitest/test_bug551654.html
new file mode 100644
index 000000000..a72fa41fa
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug551654.html
@@ -0,0 +1,49 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=551654
+-->
+<head>
+ <title>Test for Bug 551654</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=551654">Mozilla Bug 551654</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script type="application/javascript">
+
+/** Test for Bug 551654 **/
+
+ var didTransform = false;
+ var processor = new XSLTProcessor();
+ var style =
+ '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" ' +
+ 'xmlns:exsl="http://exslt.org/common" ' +
+ 'version="1.0">' +
+ '<xsl:output method="html"/>' +
+ '<xsl:template match="/">' +
+ '<xsl:copy-of select="exsl:node-set(42)"/>' +
+ '</xsl:template>' +
+ '</xsl:stylesheet>';
+ var styleDoc = new DOMParser().parseFromString (style, "text/xml");
+
+ var data =
+ '<root/>';
+ var originalDoc = new DOMParser().parseFromString(data, "text/xml");
+
+ processor.importStylesheet(styleDoc);
+ var fragment = processor.transformToFragment(originalDoc, document);
+ is(fragment.firstChild.nodeType, Node.TEXT_NODE,
+ "Result of transform should be a textnode");
+ is(fragment.firstChild.nodeValue, "42",
+ "Result of transform should be a textnode with value '42'");
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug566629.html b/dom/xslt/tests/mochitest/test_bug566629.html
new file mode 100644
index 000000000..7d66d212b
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug566629.html
@@ -0,0 +1,70 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=566629
+-->
+<head>
+ <title>Test for Bug 566629</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=566629">Mozilla Bug 566629</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+
+/** Test for Bug 566629 **/
+
+var xsltdoc = new DOMParser().parseFromString(
+ '<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"\
+ xmlns:xhtml="http://www.w3.org/1999/xhtml">\
+ <xsl:template match="/">\
+ <xsl:value-of select="count(//body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="count(//xhtml:body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="count(//xsl:body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="name(//body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="local-name(//body)"/>\
+ </xsl:template>\
+ </xsl:stylesheet>',
+ "text/xml");
+
+var processor = new XSLTProcessor;
+processor.importStylesheet(xsltdoc);
+var result = processor.transformToFragment(document, document);
+ok(result instanceof DocumentFragment, "returned a docfragment");
+is(result.firstChild.nodeValue, "1,1,0,BODY,body",
+ "correct treatment of HTML elements in XSLT");
+
+is(document.evaluate("count(//body)", document, null, XPathResult.ANY_TYPE, null).numberValue,
+ 1, "namespace-less node-test");
+is(document.evaluate("count(//a:body)", document,
+ function() { return "http://www.w3.org/1999/xhtml" },
+ XPathResult.ANY_TYPE, null).numberValue,
+ 1, "with-namespace node-test");
+is(document.evaluate("count(//a:body)", document,
+ function() { return "foo" },
+ XPathResult.ANY_TYPE, null).numberValue,
+ 0, "wrong-namespace node-test");
+is(document.evaluate("//bODy", document, null, XPathResult.ANY_TYPE, null).iterateNext(),
+ document.body, "case insensitive matching");
+is(document.evaluate("count(//a:bODy)", document,
+ function() { return "http://www.w3.org/1999/xhtml" },
+ XPathResult.ANY_TYPE, null).numberValue,
+ 0, "with-namespace but wrong casing node-test");
+is(document.evaluate("name(//body)", document, null, XPathResult.ANY_TYPE, null).stringValue,
+ "BODY", "uppercase name() function");
+is(document.evaluate("local-name(//body)", document, null, XPathResult.ANY_TYPE, null).stringValue,
+ "body", "lowercase local-name() function");
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug566629.xhtml b/dom/xslt/tests/mochitest/test_bug566629.xhtml
new file mode 100644
index 000000000..e5fca2b58
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug566629.xhtml
@@ -0,0 +1,73 @@
+<html xmlns="http://www.w3.org/1999/xhtml">
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=566629
+-->
+<head>
+ <title>Test for Bug 566629</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=566629">Mozilla Bug 566629</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+<![CDATA[
+/** Test for Bug 566629 **/
+
+var xsltdoc = new DOMParser().parseFromString(
+ '<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"\
+ xmlns:xhtml="http://www.w3.org/1999/xhtml">\
+ <xsl:template match="/">\
+ <xsl:value-of select="count(//body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="count(//xhtml:body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="count(//xsl:body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="name(//xhtml:body)"/>\
+ <xsl:text>,</xsl:text>\
+ <xsl:value-of select="local-name(//xhtml:body)"/>\
+ </xsl:template>\
+ </xsl:stylesheet>',
+ "text/xml");
+
+var processor = new XSLTProcessor;
+processor.importStylesheet(xsltdoc);
+var result = processor.transformToFragment(document, document);
+ok(result instanceof DocumentFragment, "returned a docfragment");
+is(result.firstChild.nodeValue, "0,1,0,body,body",
+ "correct treatment of HTML elements in XSLT");
+
+is(document.evaluate("count(//body)", document, null, XPathResult.ANY_TYPE, null).numberValue,
+ 0, "namespace-less node-test");
+is(document.evaluate("count(//a:body)", document,
+ function() { return "http://www.w3.org/1999/xhtml" },
+ XPathResult.ANY_TYPE, null).numberValue,
+ 1, "with-namespace node-test");
+is(document.evaluate("count(//a:body)", document,
+ function() { return "foo" },
+ XPathResult.ANY_TYPE, null).numberValue,
+ 0, "wrong-namespace node-test");
+is(document.evaluate("count(//a:bODy)", document,
+ function() { return "http://www.w3.org/1999/xhtml" },
+ XPathResult.ANY_TYPE, null).numberValue,
+ 0, "with-namespace wrong-casing node-test");
+is(document.evaluate("count(//bODy)", document, null, XPathResult.ANY_TYPE, null).numberValue,
+ 0, "without-namespace wrong-casing node-test");
+is(document.evaluate("name(//a:body)", document,
+ function() { return "http://www.w3.org/1999/xhtml" },
+ XPathResult.ANY_TYPE, null).stringValue,
+ "body", "name()");
+is(document.evaluate("local-name(//a:body)", document,
+ function() { return "http://www.w3.org/1999/xhtml" },
+ XPathResult.ANY_TYPE, null).stringValue,
+ "body", "local-name()");
+]]>
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug603159.html b/dom/xslt/tests/mochitest/test_bug603159.html
new file mode 100644
index 000000000..ac0191bd3
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug603159.html
@@ -0,0 +1,54 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=603159
+-->
+<head>
+ <title>Test for Bug 603159</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=603159">Mozilla Bug 603159</a>
+<p id="display"></p>
+<div id="content" style="display: none"></div>
+<pre id="test">
+<script type="application/javascript">
+
+/** Test for Bug 603159 **/
+
+ var style =
+ '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" ' +
+ 'xmlns:date="http://exslt.org/dates-and-times" '+
+ 'version="1.0">' +
+ '<xsl:output method="html"/>' +
+ '<xsl:template match="/">' +
+ '<xsl:value-of select="date:date-time()" /> ' +
+ '</xsl:template>' +
+ '</xsl:stylesheet>';
+ var styleDoc = new DOMParser().parseFromString (style, "text/xml");
+
+ var data = '<root/>';
+ var originalDoc = new DOMParser().parseFromString(data, "text/xml");
+
+ var processor = new XSLTProcessor();
+ processor.importStylesheet(styleDoc);
+
+ var fragment = processor.transformToFragment(originalDoc, document);
+ var content = document.getElementById("content");
+ content.appendChild(fragment);
+
+ // use Gecko's Date.parse to parse, then compare the milliseconds since epoch
+ var xslt_ms = Date.parse(content.innerHTML);
+ var now_ms = new Date().getTime();
+ var accepted_diff = 30 * 60 * 1000; // 30 minutes
+ var diff = Math.abs(now_ms - xslt_ms);
+
+ ok(diff < accepted_diff, "generated timestamp should be not more than "
+ + accepted_diff + " ms before 'now', but the difference was: " + diff);
+
+ content.innerHTML = '';
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug616774.html b/dom/xslt/tests/mochitest/test_bug616774.html
new file mode 100644
index 000000000..3578d1704
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug616774.html
@@ -0,0 +1,28 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=616774-->
+<head>
+ <title>Test for Bug 616774</title>
+ <script type="text/javascript" src="/MochiKit/MochiKit.js"></script>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=616774">Mozilla Bug 616774</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+ 42
+</div>
+<pre id="test">
+<script class="testbody" type="text/javascript">
+
+/** Test for Bug 616774 **/
+is(document.evaluate('- "8"', document, null, XPathResult.ANY_TYPE, null).numberValue, -8, "Negated string literal should evaluate to itself negated");
+is(document.evaluate('- - "999"', document, null, XPathResult.ANY_TYPE, null).numberValue, 999, "String literal should evaluate to itself");
+is(document.evaluate('- - id("content")', document, null, XPathResult.ANY_TYPE, null).numberValue, 42, "DOM element should evaluate to itself coerced to a number");
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_bug667315.html b/dom/xslt/tests/mochitest/test_bug667315.html
new file mode 100644
index 000000000..fc5baff77
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_bug667315.html
@@ -0,0 +1,46 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+https://bugzilla.mozilla.org/show_bug.cgi?id=667315
+-->
+<head>
+ <title>Test for Bug 667315</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=667315">Mozilla Bug 667315</a>
+<p id="display"></p>
+<div id="content" style="display: none">
+
+</div>
+<pre id="test">
+<script type="application/javascript">
+
+/** Test for Bug 667315 **/
+
+var style =
+ '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" ' +
+ 'version="1.0">' +
+ '<xsl:variable name="var">' +
+ '<html><p>a</p></html>' +
+ '</xsl:variable>' +
+ '<xsl:template match="/">' +
+ '<xsl:copy-of select="$var" />' +
+ '</xsl:template>' +
+ '</xsl:stylesheet>';
+var styleDoc = new DOMParser().parseFromString (style, "text/xml");
+
+var data = '<root/>';
+var originalDoc = new DOMParser().parseFromString(data, "text/xml");
+
+var processor = new XSLTProcessor();
+processor.importStylesheet(styleDoc);
+
+var doc = processor.transformToDocument(originalDoc);
+ok(doc instanceof HTMLDocument, "should have switched to html output method");
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_exslt_regex.html b/dom/xslt/tests/mochitest/test_exslt_regex.html
new file mode 100644
index 000000000..f4e00f9d3
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_exslt_regex.html
@@ -0,0 +1,60 @@
+<!DOCTYPE HTML>
+<html>
+<!--
+Test EXSLT Regular Expression Extension
+http://www.exslt.org/regexp/index.html
+-->
+<head>
+ <title>Test for EXSLT Regular Expression Extensions</title>
+ <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<p id="display"></p>
+<div id="content" style="display: none"></div>
+<pre id="test">
+<script type="application/javascript">
+ var tests = [
+ { descr: "Testing regexp:test",
+ expr: "regexp:test('XSLT is great', 'XSLT', '')",
+ expResult: "true" },
+
+ { descr: "Testing regexp:match",
+ expr: "regexp:match('XSLT is great', 'XSL.', '')[1]",
+ expResult: "XSLT" },
+
+ { descr: "Testing regexp:replace",
+ expr: "regexp:replace('Food is great', 'Fo.d', '', 'XSLT')",
+ expResult: "XSLT is great" }
+ ];
+
+ for (test of tests) {
+ var style =
+ '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" ' +
+ 'xmlns:regexp="http://exslt.org/regular-expressions" '+
+ 'version="1.0">' +
+ '<xsl:output method="html"/>' +
+ '<xsl:template match="/">' +
+ '<xsl:value-of select="'+test.expr+'" /> ' +
+ '</xsl:template>' +
+ '</xsl:stylesheet>';
+ var styleDoc = new DOMParser().parseFromString (style, "text/xml");
+
+ var data = '<root/>';
+ var originalDoc = new DOMParser().parseFromString(data, "text/xml");
+
+ var processor = new XSLTProcessor();
+ processor.importStylesheet(styleDoc);
+
+ var fragment = processor.transformToFragment(originalDoc, document);
+ var content = document.getElementById("content");
+ content.appendChild(fragment);
+ is(content.innerHTML, test.expResult, test.descr);
+
+ content.innerHTML = '';
+ }
+
+</script>
+</pre>
+</body>
+</html>
diff --git a/dom/xslt/tests/mochitest/test_parameter.html b/dom/xslt/tests/mochitest/test_parameter.html
new file mode 100644
index 000000000..2430f75ec
--- /dev/null
+++ b/dom/xslt/tests/mochitest/test_parameter.html
@@ -0,0 +1,31 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+ <title>Test for setParameter/getParameter</title>
+ <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+ <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<p id="display"></p>
+<div id="content" style="display: none"></div>
+<pre id="test">
+<script>
+ var processor = new XSLTProcessor();
+
+ processor.setParameter(null, "test", "hello");
+ is(processor.getParameter(null, "test"), "hello", "null namespace works");
+
+ processor.setParameter("foo", "bar", "foobar");
+ is(processor.getParameter("foo", "bar"), "foobar", "non-null namespace works");
+
+ processor.setParameter(null, "test", 123);
+ is(processor.getParameter(null, "test"), 123, "number value works");
+
+ processor.removeParameter(null, "test");
+ is(processor.getParameter(null, "test"), null, "removeParameter works");
+
+ is(processor.getParameter(null, "not-here"), null, "nonexistant parameter");
+</script>
+</pre>
+</body>
+</html>