Jawaban yang diterima tidak berfungsi untuk saya untuk objek bersarang karena beberapa alasan. Ini membuat saya membuat kode saya sendiri. Karena akhir 2019 ketika saya menulis ini, ada beberapa opsi lagi yang tersedia dalam bahasa ini.
Pembaruan: Saya percaya jawaban David Furlong adalah pendekatan yang lebih disukai untuk upaya saya sebelumnya, dan saya telah mengesampingkannya. Milik saya mengandalkan dukungan untuk Object.entries (...), jadi tidak ada dukungan Internet Explorer.
function normalize(sortingFunction) {
return function(key, value) {
if (typeof value === 'object' && !Array.isArray(value)) {
return Object
.entries(value)
.sort(sortingFunction || undefined)
.reduce((acc, entry) => {
acc[entry[0]] = entry[1];
return acc;
}, {});
}
return value;
}
}
JSON.stringify(obj, normalize(), 2);
-
MEMPERTAHANKAN VERSI LAMA INI UNTUK REFERENSI SEJARAH
Saya menemukan bahwa array datar sederhana dari semua kunci di objek akan berfungsi. Di hampir semua browser (bukan Edge atau Internet explorer, dapat diprediksi) dan Node 12+ ada solusi yang cukup singkat sekarang karena Array.prototype.flatMap (...) tersedia. (Setara lodash akan berfungsi juga.) Saya hanya menguji di Safari, Chrome, dan Firefox, tetapi saya tidak melihat alasan mengapa itu tidak akan berfungsi di tempat lain yang mendukung flatMap dan standar JSON.stringify (...) .
function flattenEntries([key, value]) {
return (typeof value !== 'object')
? [ [ key, value ] ]
: [ [ key, value ], ...Object.entries(value).flatMap(flattenEntries) ];
}
function sortedStringify(obj, sorter, indent = 2) {
const allEntries = Object.entries(obj).flatMap(flattenEntries);
const sorted = allEntries.sort(sorter || undefined).map(entry => entry[0]);
return JSON.stringify(obj, sorted, indent);
}
Dengan ini, Anda dapat merangkai tanpa dependensi pihak ketiga dan bahkan meneruskan algoritme pengurutan Anda sendiri yang mengurutkan pasangan entri nilai kunci, sehingga Anda dapat mengurutkan berdasarkan kunci, payload, atau kombinasi keduanya. Berfungsi untuk objek bersarang, larik, dan campuran apa pun dari tipe data lama biasa.
const obj = {
"c": {
"z": 4,
"x": 3,
"y": [
2048,
1999,
{
"x": false,
"g": "help",
"f": 5
}
]
},
"a": 2,
"b": 1
};
console.log(sortedStringify(obj, null, 2));
Cetakan:
{
"a": 2,
"b": 1,
"c": {
"x": 3,
"y": [
2048,
1999,
{
"f": 5,
"g": "help",
"x": false
}
],
"z": 4
}
}
Jika Anda harus memiliki kompatibilitas dengan mesin JavaScript yang lebih lama , Anda dapat menggunakan versi yang sedikit lebih panjang ini yang meniru perilaku flatMap. Klien harus mendukung setidaknya ES5, jadi tidak ada Internet Explorer 8 atau yang lebih rendah.
Ini akan mengembalikan hasil yang sama seperti di atas.
function flattenEntries([key, value]) {
if (typeof value !== 'object') {
return [ [ key, value ] ];
}
const nestedEntries = Object
.entries(value)
.map(flattenEntries)
.reduce((acc, arr) => acc.concat(arr), []);
nestedEntries.unshift([ key, value ]);
return nestedEntries;
}
function sortedStringify(obj, sorter, indent = 2) {
const sortedKeys = Object
.entries(obj)
.map(flattenEntries)
.reduce((acc, arr) => acc.concat(arr), [])
.sort(sorter || undefined)
.map(entry => entry[0]);
return JSON.stringify(obj, sortedKeys, indent);
}