При поиске элементов в сложных массивах JSON и хэшах, например:
[
{ "id": 1, "name": "One", "objects": [
{ "id": 1, "name": "Response 1", "objects": [
// etc.
}]
}
]
Есть ли какой-то язык запросов, который я могу использовать для поиска элемента in [0].objects where id = 3
?
Ответ 1
Yup, он называется JSONPath:
Он также интегрирован в DOJO.
Ответ 2
Я думаю, что JSONQuery - это надмножество JSONPath и, следовательно, заменяет его в dojo. Затем также RQL.
Из Dojo документации:
JSONQuery - это расширенная версия JSONPath с дополнительными функциями для обеспечения безопасности, простоты использования и комплексного набора запросов данных инструменты, включая фильтрацию, рекурсивный поиск, сортировку, отображение, диапазон выбор и гибкие выражения с сопоставлениями подстановочных строк и различные операторы.
JSONselect имеет другую точку зрения на вопрос (CSS-селекторный, а не XPath) и имеет реализация JavaScript.
Ответ 3
Другие альтернативы, о которых я знаю,
- JSONiq спецификация, которая определяет два подтипа языков: тот, который скрывает детали XML и предоставляет JS-подобный синтаксис, и тот, который обогащает синтаксис XQuery с конструкторами JSON и т.д. Zorba реализует JSONiq.
- Corona, который построен поверх MarkLogic, предоставляет интерфейс REST для хранения, управления и поиска XML, JSON, Text и Двоичный контент.
- MarkLogic 6 и более поздние версии предоставляют аналогичный интерфейс REST как Corona из коробки.
- MarkLogic 8 и более поздние версии поддерживают JSON изначально как в среде JavaScript XQuery, так и на стороне сервера. Вы можете применить XPath к нему.
НТН.
Ответ 4
Попробуйте использовать JSPath
JSPath - это доменный язык (DSL), который позволяет вам перемещаться и находить данные в ваших документах JSON. Используя JSPath, вы можете выбрать элементы JSON для извлечения данных, которые они содержат.
JSPath для JSON, как XPath для XML.
Он сильно оптимизирован как для Node.js, так и для современных браузеров.
Ответ 5
Чтобы обобщить некоторые из текущих параметров для перемещения/фильтрации данных JSON и предоставить некоторые примеры синтаксиса...
-
JSPath
.automobiles{.maker === "Honda" && .year > 2009}.model
-
json: select() (больше вдохновлен CSS-селекторами)
.automobiles .maker:val("Honda") .model
-
JSONPath (больше вдохновил XPath)
$.automobiles[?(@.maker='Honda')].model
Я думаю, что JSPath выглядит красивее, поэтому я собираюсь попытаться интегрировать его с моим приложением AngularJS + CakePHP.
(Я изначально опубликовал этот ответ в другом потоке, но подумал, что здесь тоже будет полезно.)
Ответ 6
XQuery может использоваться для запроса JSON при условии, что процессор поддерживает JSON. Это простой пример того, как BaseX можно использовать для поиска объектов с "id" = 1:
json:parse('[
{ "id": 1, "name": "One", "objects": [
{ "id": 1, "name": "Response 1", "objects": [ "etc." ] }
]}
]')//value[.//id = 1]
Ответ 7
Json Pointer, похоже, тоже получает поддержку.
Ответ 8
ObjectPath - это язык запросов, похожий на XPath или JSONPath, но гораздо более мощный благодаря встроенным арифметическим вычислениям, механизмам сравнения и встроенным алгоритмам, в функциях.
См. Синтаксис:
Найдите в магазине все туфли красного цвета и цену менее 50
$.. обувь. * [цвет "красный" и цена < 50]
Ответ 9
Jsel является потрясающим и основан на реальном процессоре XPath. Он позволяет создавать выражения XPath для поиска любых типов данных JavaScript, а не только объектов (строки тоже).
Вы можете создавать собственные схемы и сопоставления, чтобы дать вам полный контроль над тем, как ваши данные могут быть перемещены движком XPath. Схема - это способ определения того, как элементы, дети, атрибуты и значения node определены в ваших данных. Затем вы можете создать свои собственные выражения.
Учитывая, что у вас была переменная с именем data
, в которой содержался JSON из вопроса, вы можете использовать jsel для записи:
jsel(data).select("//*[@id=3]")
Это вернет любой node с атрибутом id
3. Атрибут - это любое значение примитива (строка, число, дата, регулярное выражение) внутри объекта.
Ответ 10
Defiant.js выглядит также довольно круто, вот простой пример:
var obj = {
"car": [
{"id": 10, "color": "silver", "name": "Volvo"},
{"id": 11, "color": "red", "name": "Saab"},
{"id": 12, "color": "red", "name": "Peugeot"},
{"id": 13, "color": "yellow", "name": "Porsche"}
],
"bike": [
{"id": 20, "color": "black", "name": "Cannondale"},
{"id": 21, "color": "red", "name": "Shimano"}
]
},
search = JSON.search(obj, '//car[color="yellow"]/name');
console.log( search );
// ["Porsche"]
var reds = JSON.search(obj, '//*[color="red"]');
for (var i=0; i<reds.length; i++) {
console.log( reds[i].name );
}
// Saab
// Peugeot
// Shimano
Ответ 11
@Naftule - с "defiant.js", можно запросить структуру JSON с выражениями XPath. Проверьте этот оценщик, чтобы получить представление о том, как он работает:
http://www.defiantjs.com/#xpath_evaluator
В отличие от JSONPath, "defiant.js" обеспечивает полномасштабную поддержку синтаксиса запроса - XPath на структурах JSON.
Исходный код defiant.js можно найти здесь:
https://github.com/hbi99/defiant.js
Ответ 12
Если вы похожи на меня, и вы просто хотите сделать поиск на основе пути, но не заботитесь о реальном XPath, lodash _.get()
может работать. Пример из lodash docs:
var object = { 'a': [{ 'b': { 'c': 3 } }] };
_.get(object, 'a[0].b.c');
// → 3
_.get(object, ['a', '0', 'b', 'c']);
// → 3
_.get(object, 'a.b.c', 'default');
// → 'default'
Ответ 13
Попробуйте это - https://github.com/satyapaul/jpath/blob/master/JSONDataReader.java
Это очень простая реализация на аналогичной строке xpath для xml. Он называется jpath.