123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343 |
- /**
- The below work is licensed under Creative Commons GNU LGPL License.
- Original work:
- License: http://creativecommons.org/licenses/LGPL/2.1/
- Author: Stefan Goessner/2006
- Web: http://goessner.net/
- Modifications made:
- Version: 0.9-p5
- Description: Restructured code, JSLint validated (no strict whitespaces),
- added handling of empty arrays, empty strings, and int/floats values.
- Author: Michael Schøler/2008-01-29
- Web: http://michael.hinnerup.net/blog/2008/01/26/converting-json-to-xml-and-xml-to-json/
- Description: json2xml added support to convert functions as CDATA
- so it will be easy to write characters that cause some problems when convert
- Author: Tony Tomov
- */
- /*global jQuery, alert, define, exports, module, require */
- /*jslint browser: true, vars: true, regexp: true, white: true */
- (function (global, factory) {
- "use strict";
- if (typeof define === "function" && define.amd) {
- // AMD. Register as an anonymous module.
- //console.log("jsonxml AMD");
- define([
- "jquery"
- ], function ($) {
- //console.log("jsonxml AMD: define callback");
- return factory($, global);
- });
- } else if (typeof module === "object" && module.exports) {
- // Node/CommonJS
- //console.log("jsonxml CommonJS, typeof define=" + typeof define + ", define=" + define);
- module.exports = function (root, $) {
- //console.log("jsonxml CommonJS: in module.exports");
- if (!root) {
- root = window;
- }
- //console.log("jsonxml CommonJS: before require('jquery')");
- if ($ === undefined) {
- // require("jquery") returns a factory that requires window to
- // build a jQuery instance, we normalize how we use modules
- // that require this pattern but the window provided is a noop
- // if it's defined (how jquery works)
- $ = typeof window !== "undefined" ?
- require("jquery") :
- require("jquery")(root);
- }
- //console.log("jsonxml CommonJS: before factory");
- return factory($, root);
- };
- } else {
- // Browser globals
- //console.log("jsonxml Browser: before factory");
- factory(jQuery, global);
- }
- }(typeof window !== "undefined" ? window : this, function ($, window) {
- "use strict";
- // begin module jsonxml
- var xmlJsonClass = {
- // Param "xml": Element or document DOM node.
- // Param "tab": Tab or indent string for pretty output formatting omit or use empty string "" to supress.
- // Returns: JSON string
- xml2json: function (xml, tab) {
- if (xml.nodeType === 9) {
- // document node
- xml = xml.documentElement;
- }
- var nws = this.removeWhite(xml),
- obj = this.toObj(nws),
- json = this.toJson(obj, xml.nodeName, "\t");
- return "{\n" + tab + (tab ? json.replace(/\t/g, tab) : json.replace(/\t|\n/g, "")) + "\n}";
- },
- // Param "o": JavaScript object
- // Param "tab": tab or indent string for pretty output formatting omit or use empty string "" to supress.
- // Returns: XML string
- json2xml: function (o, tab) {
- var toXml = function (v, name, ind) {
- var xml = "", i, n, sXml, hasChild, m;
- if (v instanceof Array) {
- if (v.length === 0) {
- xml += ind + "<" + name + ">__EMPTY_ARRAY_</" + name + ">\n";
- } else {
- for (i = 0, n = v.length; i < n; i += 1) {
- sXml = ind + toXml(v[i], name, ind + "\t") + "\n";
- xml += sXml;
- }
- }
- } else if (typeof v === "object") {
- hasChild = false;
- xml += ind + "<" + name;
- for (m in v) {
- if (v.hasOwnProperty(m)) {
- if (m.charAt(0) === "@") {
- xml += " " + m.substr(1) + "=\"" + v[m].toString() + "\"";
- } else {
- hasChild = true;
- }
- }
- }
- xml += hasChild ? ">" : "/>";
- if (hasChild) {
- for (m in v) {
- if (v.hasOwnProperty(m)) {
- if (m === "#text") {
- xml += v[m];
- } else if (m === "#cdata") {
- xml += "<![CDATA[" + v[m] + "]]>";
- } else if (m.charAt(0) !== "@") {
- xml += toXml(v[m], m, ind + "\t");
- }
- }
- }
- xml += (xml.charAt(xml.length - 1) === "\n" ? ind : "") + "</" + name + ">";
- }
- } else if (typeof v === "function") {
- xml += ind + "<" + name + ">" + "<![CDATA[" + v + "]]>" + "</" + name + ">";
- } else {
- if (v === undefined) {
- v = "";
- }
- if (v.toString() === "\"\"" || v.toString().length === 0) {
- xml += ind + "<" + name + ">__EMPTY_STRING_</" + name + ">";
- } else {
- xml += ind + "<" + name + ">" + v.toString() + "</" + name + ">";
- }
- }
- return xml;
- },
- xml1 = "",
- p;
- for (p in o) {
- if (o.hasOwnProperty(p)) {
- xml1 += toXml(o[p], p, "");
- }
- }
- return tab ? xml1.replace(/\t/g, tab) : xml1.replace(/\t|\n/g, "");
- },
- // Internal methods
- toObj: function (xml) {
- var o = {}, funcTest = /function/i, i, textChild = 0, cdataChild = 0, hasElementChild = false, n;
- if (xml.nodeType === 1) {
- // element node ..
- if (xml.attributes.length) {
- // element with attributes ..
- for (i = 0; i < xml.attributes.length; i += 1) {
- o["@" + xml.attributes[i].nodeName] = (xml.attributes[i].nodeValue || "").toString();
- }
- }
- if (xml.firstChild) {
- // element has child nodes ..
- for (n = xml.firstChild; n; n = n.nextSibling) {
- if (n.nodeType === 1) {
- hasElementChild = true;
- } else if (n.nodeType === 3 && n.nodeValue.match(/[^ \f\n\r\t\v]/)) {
- // non-whitespace text
- textChild += 1;
- } else if (n.nodeType === 4) {
- // cdata section node
- cdataChild += 1;
- }
- }
- if (hasElementChild) {
- if (textChild < 2 && cdataChild < 2) {
- // structured element with evtl. a single text or/and cdata node ..
- this.removeWhite(xml);
- for (n = xml.firstChild; n; n = n.nextSibling) {
- if (n.nodeType === 3) {
- // text node
- o["#text"] = this.escape(n.nodeValue);
- } else if (n.nodeType === 4) {
- // cdata node
- if (funcTest.test(n.nodeValue)) {
- o[n.nodeName] = [o[n.nodeName], n.nodeValue];
- } else {
- o["#cdata"] = this.escape(n.nodeValue);
- }
- } else if (o[n.nodeName]) {
- // multiple occurence of element ..
- if (o[n.nodeName] instanceof Array) {
- o[n.nodeName][o[n.nodeName].length] = this.toObj(n);
- } else {
- o[n.nodeName] = [o[n.nodeName], this.toObj(n)];
- }
- } else {
- // first occurence of element ..
- o[n.nodeName] = this.toObj(n);
- }
- }
- } else {
- // mixed content
- if (!xml.attributes.length) {
- o = this.escape(this.innerXml(xml));
- } else {
- o["#text"] = this.escape(this.innerXml(xml));
- }
- }
- } else if (textChild) {
- // pure text
- if (!xml.attributes.length) {
- o = this.escape(this.innerXml(xml));
- if (o === "__EMPTY_ARRAY_") {
- o = "[]";
- } else if (o === "__EMPTY_STRING_") {
- o = "";
- }
- } else {
- o["#text"] = this.escape(this.innerXml(xml));
- }
- } else if (cdataChild) {
- // cdata
- if (cdataChild > 1) {
- o = this.escape(this.innerXml(xml));
- } else {
- for (n = xml.firstChild; n; n = n.nextSibling) {
- if (funcTest.test(xml.firstChild.nodeValue)) {
- o = xml.firstChild.nodeValue;
- break;
- }
- o["#cdata"] = this.escape(n.nodeValue);
- }
- }
- }
- }
- if (!xml.attributes.length && !xml.firstChild) {
- o = null;
- }
- } else if (xml.nodeType === 9) {
- // document.node
- o = this.toObj(xml.documentElement);
- } else {
- ($.jgrid != null && $.jgrid.defaults != null && $.isFunction($.jgrid.defaults.fatalError) ? $.jgrid.defaults.fatalError : alert)("unhandled node type: " + xml.nodeType);
- }
- return o;
- },
- toJson: function (o, name, ind, wellform) {
- if (wellform === undefined) {
- wellform = true;
- }
- var json = name ? ("\"" + name + "\"") : "", tab = "\t", newline = "\n", n, i, ar = [], arr = [], m;
- if (!wellform) {
- tab = "";
- newline = "";
- }
- if (o === "[]") {
- json += (name ? ":[]" : "[]");
- } else if (o instanceof Array) {
- for (i = 0, n = o.length; i < n; i += 1) {
- ar[i] = this.toJson(o[i], "", ind + tab, wellform);
- }
- json += (name ? ":[" : "[") + (ar.length > 1 ? (newline + ind + tab + ar.join("," + newline + ind + tab) + newline + ind) : ar.join("")) + "]";
- } else if (o === null) {
- json += (name && ":") + "null";
- } else if (typeof o === "object") {
- for (m in o) {
- if (o.hasOwnProperty(m)) {
- arr[arr.length] = this.toJson(o[m], m, ind + tab, wellform);
- }
- }
- json += (name ? ":{" : "{") + (arr.length > 1 ? (newline + ind + tab + arr.join("," + newline + ind + tab) + newline + ind) : arr.join("")) + "}";
- } else if (typeof o === "string") {
- json += (name && ":") + "\"" + o.replace(/\\/g, "\\\\").replace(/\"/g, '\\"') + "\"";
- } else {
- json += (name && ":") + o.toString();
- }
- return json;
- },
- innerXml: function (node) {
- var s = "", child,
- asXml = function (n) {
- var str = "", i, c;
- if (n.nodeType === 1) {
- str += "<" + n.nodeName;
- for (i = 0; i < n.attributes.length; i += 1) {
- str += " " + n.attributes[i].nodeName + "=\"" + (n.attributes[i].nodeValue || "").toString() + "\"";
- }
- if (n.firstChild) {
- str += ">";
- for (c = n.firstChild; c; c = c.nextSibling) {
- str += asXml(c);
- }
- str += "</" + n.nodeName + ">";
- } else {
- str += "/>";
- }
- } else if (n.nodeType === 3) {
- str += n.nodeValue;
- } else if (n.nodeType === 4) {
- str += "<![CDATA[" + n.nodeValue + "]]>";
- }
- return str;
- };
- if (node.hasOwnProperty("innerHTML")) {
- s = node.innerHTML;
- } else {
- for (child = node.firstChild; child; child = child.nextSibling) {
- s += asXml(child);
- }
- }
- return s;
- },
- escape: function (txt) {
- return txt.replace(/[\\]/g, "\\\\").replace(/[\"]/g, '\\"').replace(/[\n]/g, "\\n").replace(/[\r]/g, "\\r");
- },
- removeWhite: function (e) {
- e.normalize();
- var n = e.firstChild, nxt;
- while (n) {
- if (n.nodeType === 3) {
- // text node
- if (!n.nodeValue.match(/[^ \f\n\r\t\v]/)) {
- // pure whitespace text node
- nxt = n.nextSibling;
- e.removeChild(n);
- n = nxt;
- } else {
- n = n.nextSibling;
- }
- } else if (n.nodeType === 1) {
- // element node
- this.removeWhite(n);
- n = n.nextSibling;
- } else {
- // any other node
- n = n.nextSibling;
- }
- }
- return e;
- }
- };
- window.xmlJsonClass = xmlJsonClass;
- // end module jsonxml
- return xmlJsonClass;
- }));
|