// Generated by CoffeeScript 1.7.1 (function() { var bom, builder, events, isEmpty, processName, processors, sax, __hasProp = {}.hasOwnProperty, __extends = function(child, parent) { for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; } function ctor() { this.constructor = child; } ctor.prototype = parent.prototype; child.prototype = new ctor(); child.__super__ = parent.prototype; return child; }, __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }; sax = require('sax'); events = require('events'); builder = require('xmlbuilder'); bom = require('./bom'); processors = require('./processors'); isEmpty = function(thing) { return typeof thing === "object" && (thing != null) && Object.keys(thing).length === 0; }; processName = function(processors, processedName) { var process, _i, _len; for (_i = 0, _len = processors.length; _i < _len; _i++) { process = processors[_i]; processedName = process(processedName); } return processedName; }; exports.processors = processors; exports.defaults = { "0.1": { explicitCharkey: false, trim: true, normalize: true, normalizeTags: false, attrkey: "@", charkey: "#", explicitArray: false, ignoreAttrs: false, mergeAttrs: false, explicitRoot: false, validator: null, xmlns: false, explicitChildren: false, childkey: '@@', charsAsChildren: false, async: false, strict: true, attrNameProcessors: null, tagNameProcessors: null }, "0.2": { explicitCharkey: false, trim: false, normalize: false, normalizeTags: false, attrkey: "$", charkey: "_", explicitArray: true, ignoreAttrs: false, mergeAttrs: false, explicitRoot: true, validator: null, xmlns: false, explicitChildren: false, childkey: '$$', charsAsChildren: false, async: false, strict: true, attrNameProcessors: null, tagNameProcessors: null, rootName: 'root', xmldec: { 'version': '1.0', 'encoding': 'UTF-8', 'standalone': true }, doctype: null, renderOpts: { 'pretty': true, 'indent': ' ', 'newline': '\n' }, headless: false } }; exports.ValidationError = (function(_super) { __extends(ValidationError, _super); function ValidationError(message) { this.message = message; } return ValidationError; })(Error); exports.Builder = (function() { function Builder(opts) { var key, value, _ref; this.options = {}; _ref = exports.defaults["0.2"]; for (key in _ref) { if (!__hasProp.call(_ref, key)) continue; value = _ref[key]; this.options[key] = value; } for (key in opts) { if (!__hasProp.call(opts, key)) continue; value = opts[key]; this.options[key] = value; } } Builder.prototype.buildObject = function(rootObj) { var attrkey, charkey, render, rootElement, rootName; attrkey = this.options.attrkey; charkey = this.options.charkey; if ((Object.keys(rootObj).length === 1) && (this.options.rootName === exports.defaults['0.2'].rootName)) { rootName = Object.keys(rootObj)[0]; rootObj = rootObj[rootName]; } else { rootName = this.options.rootName; } render = function(element, obj) { var attr, child, entry, index, key, value, _ref, _ref1; if (typeof obj !== 'object') { element.txt(obj); } else { for (key in obj) { if (!__hasProp.call(obj, key)) continue; child = obj[key]; if (key === attrkey) { if (typeof child === "object") { for (attr in child) { value = child[attr]; element = element.att(attr, value); } } } else if (key === charkey) { element = element.txt(child); } else if (typeof child === 'object' && ((child != null ? child.constructor : void 0) != null) && ((child != null ? (_ref = child.constructor) != null ? _ref.name : void 0 : void 0) != null) && (child != null ? (_ref1 = child.constructor) != null ? _ref1.name : void 0 : void 0) === 'Array') { for (index in child) { if (!__hasProp.call(child, index)) continue; entry = child[index]; if (typeof entry === 'string') { element = element.ele(key, entry).up(); } else { element = arguments.callee(element.ele(key), entry).up(); } } } else if (typeof child === "object") { element = arguments.callee(element.ele(key), child).up(); } else { element = element.ele(key, child.toString()).up(); } } } return element; }; rootElement = builder.create(rootName, this.options.xmldec, this.options.doctype, { headless: this.options.headless }); return render(rootElement, rootObj).end(this.options.renderOpts); }; return Builder; })(); exports.Parser = (function(_super) { __extends(Parser, _super); function Parser(opts) { this.parseString = __bind(this.parseString, this); this.reset = __bind(this.reset, this); this.assignOrPush = __bind(this.assignOrPush, this); var key, value, _ref; if (!(this instanceof exports.Parser)) { return new exports.Parser(opts); } this.options = {}; _ref = exports.defaults["0.2"]; for (key in _ref) { if (!__hasProp.call(_ref, key)) continue; value = _ref[key]; this.options[key] = value; } for (key in opts) { if (!__hasProp.call(opts, key)) continue; value = opts[key]; this.options[key] = value; } if (this.options.xmlns) { this.options.xmlnskey = this.options.attrkey + "ns"; } if (this.options.normalizeTags) { if (!this.options.tagNameProcessors) { this.options.tagNameProcessors = []; } this.options.tagNameProcessors.unshift(processors.normalize); } this.reset(); } Parser.prototype.assignOrPush = function(obj, key, newValue) { if (!(key in obj)) { if (!this.options.explicitArray) { return obj[key] = newValue; } else { return obj[key] = [newValue]; } } else { if (!(obj[key] instanceof Array)) { obj[key] = [obj[key]]; } return obj[key].push(newValue); } }; Parser.prototype.reset = function() { var attrkey, charkey, ontext, stack; this.removeAllListeners(); this.saxParser = sax.parser(this.options.strict, { trim: false, normalize: false, xmlns: this.options.xmlns }); this.saxParser.errThrown = false; this.saxParser.onerror = (function(_this) { return function(error) { _this.saxParser.resume(); if (!_this.saxParser.errThrown) { _this.saxParser.errThrown = true; return _this.emit("error", error); } }; })(this); this.saxParser.ended = false; this.EXPLICIT_CHARKEY = this.options.explicitCharkey; this.resultObject = null; stack = []; attrkey = this.options.attrkey; charkey = this.options.charkey; this.saxParser.onopentag = (function(_this) { return function(node) { var key, newValue, obj, processedKey, _ref; obj = {}; obj[charkey] = ""; if (!_this.options.ignoreAttrs) { _ref = node.attributes; for (key in _ref) { if (!__hasProp.call(_ref, key)) continue; if (!(attrkey in obj) && !_this.options.mergeAttrs) { obj[attrkey] = {}; } newValue = node.attributes[key]; processedKey = _this.options.attrNameProcessors ? processName(_this.options.attrNameProcessors, key) : key; if (_this.options.mergeAttrs) { _this.assignOrPush(obj, processedKey, newValue); } else { obj[attrkey][processedKey] = newValue; } } } obj["#name"] = _this.options.tagNameProcessors ? processName(_this.options.tagNameProcessors, node.name) : node.name; if (_this.options.xmlns) { obj[_this.options.xmlnskey] = { uri: node.uri, local: node.local }; } return stack.push(obj); }; })(this); this.saxParser.onclosetag = (function(_this) { return function() { var cdata, emptyStr, err, node, nodeName, obj, old, s, xpath; obj = stack.pop(); nodeName = obj["#name"]; delete obj["#name"]; cdata = obj.cdata; delete obj.cdata; s = stack[stack.length - 1]; if (obj[charkey].match(/^\s*$/) && !cdata) { emptyStr = obj[charkey]; delete obj[charkey]; } else { if (_this.options.trim) { obj[charkey] = obj[charkey].trim(); } if (_this.options.normalize) { obj[charkey] = obj[charkey].replace(/\s{2,}/g, " ").trim(); } if (Object.keys(obj).length === 1 && charkey in obj && !_this.EXPLICIT_CHARKEY) { obj = obj[charkey]; } } if (isEmpty(obj)) { obj = _this.options.emptyTag !== void 0 ? _this.options.emptyTag : emptyStr; } if (_this.options.validator != null) { xpath = "/" + ((function() { var _i, _len, _results; _results = []; for (_i = 0, _len = stack.length; _i < _len; _i++) { node = stack[_i]; _results.push(node["#name"]); } return _results; })()).concat(nodeName).join("/"); try { obj = _this.options.validator(xpath, s && s[nodeName], obj); } catch (_error) { err = _error; _this.emit("error", err); } } if (_this.options.explicitChildren && !_this.options.mergeAttrs && typeof obj === 'object') { node = {}; if (_this.options.attrkey in obj) { node[_this.options.attrkey] = obj[_this.options.attrkey]; delete obj[_this.options.attrkey]; } if (!_this.options.charsAsChildren && _this.options.charkey in obj) { node[_this.options.charkey] = obj[_this.options.charkey]; delete obj[_this.options.charkey]; } if (Object.getOwnPropertyNames(obj).length > 0) { node[_this.options.childkey] = obj; } obj = node; } if (stack.length > 0) { return _this.assignOrPush(s, nodeName, obj); } else { if (_this.options.explicitRoot) { old = obj; obj = {}; obj[nodeName] = old; } _this.resultObject = obj; _this.saxParser.ended = true; return _this.emit("end", _this.resultObject); } }; })(this); ontext = (function(_this) { return function(text) { var s; s = stack[stack.length - 1]; if (s) { s[charkey] += text; return s; } }; })(this); this.saxParser.ontext = ontext; return this.saxParser.oncdata = (function(_this) { return function(text) { var s; s = ontext(text); if (s) { return s.cdata = true; } }; })(this); }; Parser.prototype.parseString = function(str, cb) { var err; if ((cb != null) && typeof cb === "function") { this.on("end", function(result) { this.reset(); if (this.options.async) { return process.nextTick(function() { return cb(null, result); }); } else { return cb(null, result); } }); this.on("error", function(err) { this.reset(); if (this.options.async) { return process.nextTick(function() { return cb(err); }); } else { return cb(err); } }); } if (str.toString().trim() === '') { this.emit("end", null); return true; } try { return this.saxParser.write(bom.stripBOM(str.toString())).close(); } catch (_error) { err = _error; if (!(this.saxParser.errThrown || this.saxParser.ended)) { this.emit('error', err); return this.saxParser.errThrown = true; } } }; return Parser; })(events.EventEmitter); exports.parseString = function(str, a, b) { var cb, options, parser; if (b != null) { if (typeof b === 'function') { cb = b; } if (typeof a === 'object') { options = a; } } else { if (typeof a === 'function') { cb = a; } options = {}; } parser = new exports.Parser(options); return parser.parseString(str, cb); }; }).call(this);