Мне нужно сериализовать объект в JSON. Я использую jQuery. Существует ли "стандартный" способ сделать это?
Моя конкретная ситуация: у меня есть массив, как показано ниже:
var countries = new Array();
countries[0] = 'ga';
countries[1] = 'cd';
...
и мне нужно превратить это в строку, чтобы перейти к $.ajax()
следующим образом:
$.ajax({
type: "POST",
url: "Concessions.aspx/GetConcessions",
data: "{'countries':['ga','cd']}",
...
JSON-js - JSON в JavaScript.
Чтобы преобразовать объект в строку, используйте JSON.stringify
:
var json_text = JSON.stringify(your_object, null, 2);
Чтобы преобразовать строку JSON в объект, используйте JSON.parse
:
var your_object = JSON.parse(json_text);
Недавно был рекомендован John Resig:
... ПОЖАЛУЙСТА, начните мигрировать ваши приложения, использующие JSON, для Crockford json2.js. Это полностью совместимый с ECMAScript 5 спецификации и грамотно деградирует если выполняется нативная (более быстрая!) реализация существует.
Фактически, я только что приземлился на изменение jQuery вчера, в котором используется Метод JSON.parse, если он существует, теперь что он был полностью определен.
Я склонен доверять тому, что он говорит по вопросам JavaScript:)
Новые браузеры поддерживают
Я использую jquery-json в течение 6 месяцев, и он отлично работает. Это очень простое использование:
var myObj = {foo: "bar", "baz": "wockaflockafliz"};
$.toJSON(myObj);
// Result: {"foo":"bar","baz":"wockaflockafliz"}
Я не использовал его, но вы можете попробовать плагин jQuery, написанный Марк Гибсон
Он добавляет две функции: $.toJSON(value)
, $.parseJSON(json_str, [safe])
.
$.parseJSON
теперь находится в ядре jQuery.
Нет, стандартный способ сериализации в JSON - использовать существующую библиотеку сериализации JSON. Если вы не хотите этого делать, вам придется написать свои собственные методы сериализации.
Если вы хотите получить инструкции о том, как это сделать, я бы предложил изучить источник некоторых доступных библиотек.
РЕДАКТИРОВАТЬ: Я не собираюсь выходить и говорить, что писать свои собственные методы серллизации - это плохо, но вы должны учитывать, что если для вашего приложения важно использовать хорошо сформированный JSON, то вы должны взвесить накладные расходы "еще одной зависимости" от возможности того, что ваши пользовательские методы могут однажды столкнуться с неудачным случаем, которого вы не ожидали. Является ли этот риск приемлемым, это ваш звонок.
Я нашел это где-то. Не могу вспомнить, где, хотя... возможно, на StackOverflow:)
$.fn.serializeObject = function(){
var o = {};
var a = this.serializeArray();
$.each(a, function() {
if (o[this.name]) {
if (!o[this.name].push) {
o[this.name] = [o[this.name]];
}
o[this.name].push(this.value || '');
} else {
o[this.name] = this.value || '';
}
});
return o;
};
Если вы не хотите использовать внешние библиотеки, существует собственный метод JavaScript .toSource()
, но он не совсем кросс-браузер.
Лучший способ - включить объект polyfill для JSON.
Но если вы настаиваете на создании метода для сериализации объекта для нотации JSON (допустимые значения для JSON) внутри пространства имен jQuery, вы можете сделать что-то вроде этого:
// This is a reference to JSON.stringify and provides a polyfill for old browsers.
// stringify serializes an object, array or primitive value and return it as JSON.
jQuery.stringify = (function ($) {
var _PRIMITIVE, _OPEN, _CLOSE;
if (window.JSON && typeof JSON.stringify === "function")
return JSON.stringify;
_PRIMITIVE = /string|number|boolean|null/;
_OPEN = {
object: "{",
array: "["
};
_CLOSE = {
object: "}",
array: "]"
};
//actions to execute in each iteration
function action(key, value) {
var type = $.type(value),
prop = "";
//key is not an array index
if (typeof key !== "number") {
prop = '"' + key + '":';
}
if (type === "string") {
prop += '"' + value + '"';
} else if (_PRIMITIVE.test(type)) {
prop += value;
} else if (type === "array" || type === "object") {
prop += toJson(value, type);
} else return;
this.push(prop);
}
//iterates over an object or array
function each(obj, callback, thisArg) {
for (var key in obj) {
if (obj instanceof Array) key = +key;
callback.call(thisArg, key, obj[key]);
}
}
//generates the json
function toJson(obj, type) {
var items = [];
each(obj, action, items);
return _OPEN[type] + items.join(",") + _CLOSE[type];
}
//exported function that generates the json
return function stringify(obj) {
if (!arguments.length) return "";
var type = $.type(obj);
if (_PRIMITIVE.test(type))
return (obj === null ? type : obj.toString());
//obj is array or object
return toJson(obj, type);
}
}(jQuery));
var myObject = {
"0": null,
"total-items": 10,
"undefined-prop": void(0),
sorted: true,
images: ["bg-menu.png", "bg-body.jpg", [1, 2]],
position: { //nested object literal
"x": 40,
"y": 300,
offset: [{ top: 23 }]
},
onChange: function() { return !0 },
pattern: /^bg-.+\.(?:png|jpe?g)$/i
};
var json = jQuery.stringify(myObject);
console.log(json);
Да, вы должны JSON.stringify и JSON.parse "Json_PostData" перед вызовом $.ajax
$.ajax({ url: post_http_site, type: "POST", data: JSON.parse(JSON.stringify(Json_PostData)), cache: false, error: function (xhr, ajaxOptions, thrownError) { alert(" write json item, Ajax error! " + xhr.status + " error =" + thrownError + " xhr.responseText = " + xhr.responseText ); }, success: function (data) { alert("write json item, Ajax OK"); } });
Это в основном двухэтапный процесс:
Во-первых, вам нужно выполнить такой стиль
var JSON_VAR = JSON.stringify(OBJECT_NAME, null, 2);
После этого вам нужно преобразовать строку в Object
var obj = JSON.parse(JSON_VAR);
Одна вещь, которую не учитываются вышеприведенными решениями, заключается в том, что у вас есть массив входных данных, но было предоставлено только одно значение.
Например, если задний конец ожидает массив людей, но в данном конкретном случае вы просто имеете дело с одним человеком. Затем выполните:
<input type="hidden" name="People" value="Joe" />
Затем с предыдущими решениями он будет просто сопоставляться с чем-то вроде:
{
"People" : "Joe"
}
Но он должен действительно отображаться на
{
"People" : [ "Joe" ]
}
Чтобы исправить это, вход должен выглядеть так:
<input type="hidden" name="People[]" value="Joe" />
И вы будете использовать следующую функцию (основанную на других решениях, но немного расширенную)
$.fn.serializeObject = function() {
var o = {};
var a = this.serializeArray();
$.each(a, function() {
if (this.name.substr(-2) == "[]"){
this.name = this.name.substr(0, this.name.length - 2);
o[this.name] = [];
}
if (o[this.name]) {
if (!o[this.name].push) {
o[this.name] = [o[this.name]];
}
o[this.name].push(this.value || '');
} else {
o[this.name] = this.value || '';
}
});
return o;
};
countries
- это имя переменной, а не ключа ... эта информация будет потеряна при попытке ее сериализации.