ngdvar array = [].constructor;
/**
* @workInProgress
* @ngdoc function
* @name angular.toJson
* @function
*
* @description
* Serializes the input into a JSON formated string.
*
* @param {Object|Array|Date|string|number} obj Input to jsonify.
* @param {boolean=} pretty If set to true, the JSON output will contain newlines and whitespace.
* @returns {string} Jsonified string representing `obj`.
*/
function toJson(obj, pretty) {
var buf = [];
toJsonArray(buf, obj, pretty ? "\n " : _null, []);
return buf.join('');
}
/**
* @workInProgress
* @ngdoc function
* @name angular.fromJson
* @function
*
* @description
* Deserializes a string in the JSON format.
*
* @param {string} json JSON string to deserialize.
* @param {boolean} [useNative=false] Use native JSON parser if available
* @returns {Object|Array|Date|string|number} Deserialized thingy.
*/
function fromJson(json, useNative) {
if (!isString(json)) return json;
var obj, p, expression;
try {
if (useNative && JSON && JSON.parse) {
obj = JSON.parse(json);
return transformDates(obj);
}
p = parser(json, true);
expression = p.primary();
p.assertAllConsumed();
return expression();
} catch (e) {
error("fromJson error: ", json, e);
throw e;
}
// TODO make forEach optionally recursive and remove this function
function transformDates(obj) {
if (isString(obj) && obj.length === DATE_ISOSTRING_LN) {
return angularString.toDate(obj);
} else if (isArray(obj) || isObject(obj)) {
forEach(obj, function(val, name) {
obj[name] = transformDates(val);
});
}
return obj;
}
}
angular['toJson'] = toJson;
angular['fromJson'] = fromJson;
function toJsonArray(buf, obj, pretty, stack) {
if (isObject(obj)) {
if (obj === window) {
buf.push('WINDOW');
return;
}
if (obj === document) {
buf.push('DOCUMENT');
return;
}
if (includes(stack, obj)) {
buf.push('RECURSION');
return;
}
stack.push(obj);
}
if (obj === _null) {
buf.push($null);
} else if (obj instanceof RegExp) {
buf.push(angular['String']['quoteUnicode'](obj.toString()));
} else if (isFunction(obj)) {
return;
} else if (isBoolean(obj)) {
buf.push('' + obj);
} else if (isNumber(obj)) {
if (isNaN(obj)) {
buf.push($null);
} else {
buf.push('' + obj);
}
} else if (isString(obj)) {
return buf.push(angular['String']['quoteUnicode'](obj));
} else if (isObject(obj)) {
if (isArray(obj)) {
buf.push("[");
var len = obj.length;
var sep = false;
for(var i=0; i<len; i++) {
var item = obj[i];
if (sep) buf.push(",");
if (!(item instanceof RegExp) && (isFunction(item) || isUndefined(item))) {
buf.push($null);
} else {
toJsonArray(buf, item, pretty, stack);
}
sep = true;
}
buf.push("]");
} else if (isDate(obj)) {
buf.push(angular['String']['quoteUnicode'](angular['Date']['toString'](obj)));
} else {
buf.push("{");
if (pretty) buf.push(pretty);
var comma = false;
var childPretty = pretty ? pretty + " " : false;
var keys = [];
for(var k in obj) {
if (obj[k] === _undefined)
continue;
keys.push(k);
}
keys.sort();
for ( var keyIndex = 0; keyIndex < keys.length; keyIndex++) {
var key = keys[keyIndex];
var value = obj[key];
if (typeof value != $function) {
if (comma) {
buf.push(",");
if (pretty) buf.push(pretty);
}
buf.push(angular['String']['quote'](key));
buf.push(":");
toJsonArray(buf, value, childPretty, stack);
comma = true;
}
}
buf.push("}");
}
}
if (isObject(obj)) {
stack.pop();
}
}