Convert Figma logo to code with AI

dchester logojsonpath

Query and manipulate JavaScript objects with JSONPath expressions. Robust JSONPath engine for Node.js.

1,323
216
1,323
99

Top Related Projects

Java JsonPath implementation

Quick Overview

JSONPath is a JavaScript library for querying and manipulating JSON data using a syntax similar to XPath. It provides a powerful way to extract, modify, and navigate complex JSON structures, making it easier to work with nested data in JavaScript applications.

Pros

  • Simple and intuitive syntax for querying JSON data
  • Supports both Node.js and browser environments
  • Allows for complex queries and data manipulation
  • Lightweight and has no external dependencies

Cons

  • Limited documentation and examples
  • Not actively maintained (last commit was in 2019)
  • Lacks some advanced features found in other JSON query libraries
  • May have performance issues with very large JSON datasets

Code Examples

  1. Basic query to select all authors:
const jsonpath = require('jsonpath');
const data = {
  books: [
    { title: 'Book 1', author: 'Author 1' },
    { title: 'Book 2', author: 'Author 2' }
  ]
};

const authors = jsonpath.query(data, '$.books[*].author');
console.log(authors); // ['Author 1', 'Author 2']
  1. Using filters to select specific items:
const jsonpath = require('jsonpath');
const data = {
  products: [
    { name: 'Apple', price: 0.5 },
    { name: 'Banana', price: 0.3 },
    { name: 'Orange', price: 0.6 }
  ]
};

const expensiveProducts = jsonpath.query(data, '$.products[?(@.price > 0.4)]');
console.log(expensiveProducts);
// [{ name: 'Apple', price: 0.5 }, { name: 'Orange', price: 0.6 }]
  1. Modifying JSON data:
const jsonpath = require('jsonpath');
const data = {
  user: {
    name: 'John Doe',
    age: 30
  }
};

jsonpath.value(data, '$.user.age', 31);
console.log(data.user.age); // 31

Getting Started

To use JSONPath in your project, follow these steps:

  1. Install the library using npm:

    npm install jsonpath
    
  2. Import the library in your JavaScript file:

    const jsonpath = require('jsonpath');
    
  3. Use the query method to extract data from your JSON:

    const result = jsonpath.query(yourJsonData, '$.your.jsonpath.expression');
    
  4. Use the value method to modify data in your JSON:

    jsonpath.value(yourJsonData, '$.path.to.modify', newValue);
    

Competitor Comparisons

Java JsonPath implementation

Pros of JsonPath

  • More actively maintained with recent updates
  • Supports multiple programming languages (Java, JavaScript, Python)
  • Extensive documentation and examples available

Cons of JsonPath

  • Potentially more complex API for simple use cases
  • May have a steeper learning curve for beginners

Code Comparison

JsonPath:

String json = "{\"store\":{\"book\":[{\"title\":\"Sayings of the Century\"}]}}";
String title = JsonPath.read(json, "$.store.book[0].title");

jsonpath:

var jsonpath = require('jsonpath');
var json = {"store":{"book":[{"title":"Sayings of the Century"}]}};
var title = jsonpath.query(json, '$.store.book[0].title')[0];

Additional Considerations

  • JsonPath offers more robust features for complex JSON parsing scenarios
  • jsonpath provides a simpler, more lightweight solution for basic JSON querying
  • JsonPath has a larger community and ecosystem, potentially leading to better long-term support
  • jsonpath may be easier to integrate into existing Node.js projects due to its focused JavaScript implementation

Both libraries serve similar purposes, but JsonPath is generally more feature-rich and widely applicable across different programming environments, while jsonpath offers a streamlined experience for JavaScript developers.

Convert Figma logo designs to code with AI

Visual Copilot

Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.

Try Visual Copilot

README

Build Status

jsonpath

Query JavaScript objects with JSONPath expressions. Robust / safe JSONPath engine for Node.js.

Query Example

var cities = [
  { name: "London", "population": 8615246 },
  { name: "Berlin", "population": 3517424 },
  { name: "Madrid", "population": 3165235 },
  { name: "Rome",   "population": 2870528 }
];

var jp = require('jsonpath');
var names = jp.query(cities, '$..name');

// [ "London", "Berlin", "Madrid", "Rome" ]

Install

Install from npm:

$ npm install jsonpath

JSONPath Syntax

Here are syntax and examples adapted from Stefan Goessner's original post introducing JSONPath in 2007.

JSONPathDescription
$The root object/element
@The current object/element
.Child member operator
..Recursive descendant operator; JSONPath borrows this syntax from E4X
*Wildcard matching all objects/elements regardless their names
[]Subscript operator
[,]Union operator for alternate names or array indices as a set
[start:end:step]Array slice operator borrowed from ES4 / Python
?()Applies a filter (script) expression via static evaluation
()Script expression via static evaluation

Given this sample data set, see example expressions below:

{
  "store": {
    "book": [ 
      {
        "category": "reference",
        "author": "Nigel Rees",
        "title": "Sayings of the Century",
        "price": 8.95
      }, {
        "category": "fiction",
        "author": "Evelyn Waugh",
        "title": "Sword of Honour",
        "price": 12.99
      }, {
        "category": "fiction",
        "author": "Herman Melville",
        "title": "Moby Dick",
        "isbn": "0-553-21311-3",
        "price": 8.99
      }, {
         "category": "fiction",
        "author": "J. R. R. Tolkien",
        "title": "The Lord of the Rings",
        "isbn": "0-395-19395-8",
        "price": 22.99
      }
    ],
    "bicycle": {
      "color": "red",
      "price": 19.95
    }
  }
}

Example JSONPath expressions:

JSONPathDescription
$.store.book[*].authorThe authors of all books in the store
$..authorAll authors
$.store.*All things in store, which are some books and a red bicycle
$.store..priceThe price of everything in the store
$..book[2]The third book
$..book[(@.length-1)]The last book via script subscript
$..book[-1:]The last book via slice
$..book[0,1]The first two books via subscript union
$..book[:2]The first two books via subscript array slice
$..book[?(@.isbn)]Filter all books with isbn number
$..book[?(@.price<10)]Filter all books cheaper than 10
$..book[?(@.price==8.95)]Filter all books that cost 8.95
$..book[?(@.price<30 && @.category=="fiction")]Filter all fiction books cheaper than 30
$..*All members of JSON structure

Methods

jp.query(obj, pathExpression[, count])

Find elements in obj matching pathExpression. Returns an array of elements that satisfy the provided JSONPath expression, or an empty array if none were matched. Returns only first count elements if specified.

var authors = jp.query(data, '$..author');
// [ 'Nigel Rees', 'Evelyn Waugh', 'Herman Melville', 'J. R. R. Tolkien' ]

jp.paths(obj, pathExpression[, count])

Find paths to elements in obj matching pathExpression. Returns an array of element paths that satisfy the provided JSONPath expression. Each path is itself an array of keys representing the location within obj of the matching element. Returns only first count paths if specified.

var paths = jp.paths(data, '$..author');
// [
//   ['$', 'store', 'book', 0, 'author'] },
//   ['$', 'store', 'book', 1, 'author'] },
//   ['$', 'store', 'book', 2, 'author'] },
//   ['$', 'store', 'book', 3, 'author'] }
// ]

jp.nodes(obj, pathExpression[, count])

Find elements and their corresponding paths in obj matching pathExpression. Returns an array of node objects where each node has a path containing an array of keys representing the location within obj, and a value pointing to the matched element. Returns only first count nodes if specified.

var nodes = jp.nodes(data, '$..author');
// [
//   { path: ['$', 'store', 'book', 0, 'author'], value: 'Nigel Rees' },
//   { path: ['$', 'store', 'book', 1, 'author'], value: 'Evelyn Waugh' },
//   { path: ['$', 'store', 'book', 2, 'author'], value: 'Herman Melville' },
//   { path: ['$', 'store', 'book', 3, 'author'], value: 'J. R. R. Tolkien' }
// ]

jp.value(obj, pathExpression[, newValue])

Returns the value of the first element matching pathExpression. If newValue is provided, sets the value of the first matching element and returns the new value.

jp.parent(obj, pathExpression)

Returns the parent of the first matching element.

jp.apply(obj, pathExpression, fn)

Runs the supplied function fn on each matching element, and replaces each matching element with the return value from the function. The function accepts the value of the matching element as its only parameter. Returns matching nodes with their updated values.

var nodes = jp.apply(data, '$..author', function(value) { return value.toUpperCase() });
// [
//   { path: ['$', 'store', 'book', 0, 'author'], value: 'NIGEL REES' },
//   { path: ['$', 'store', 'book', 1, 'author'], value: 'EVELYN WAUGH' },
//   { path: ['$', 'store', 'book', 2, 'author'], value: 'HERMAN MELVILLE' },
//   { path: ['$', 'store', 'book', 3, 'author'], value: 'J. R. R. TOLKIEN' }
// ]

jp.parse(pathExpression)

Parse the provided JSONPath expression into path components and their associated operations.

var path = jp.parse('$..author');
// [
//   { expression: { type: 'root', value: '$' } },
//   { expression: { type: 'identifier', value: 'author' }, operation: 'member', scope: 'descendant' }
// ]

jp.stringify(path)

Returns a path expression in string form, given a path. The supplied path may either be a flat array of keys, as returned by jp.nodes for example, or may alternatively be a fully parsed path expression in the form of an array of path components as returned by jp.parse.

var pathExpression = jp.stringify(['$', 'store', 'book', 0, 'author']);
// "$.store.book[0].author"

Differences from Original Implementation

This implementation aims to be compatible with Stefan Goessner's original implementation with a few notable exceptions described below.

Evaluating Script Expressions

Script expressions (i.e, (...) and ?(...)) are statically evaluated via static-eval rather than using the underlying script engine directly. That means both that the scope is limited to the instance variable (@), and only simple expressions (with no side effects) will be valid. So for example, ?(@.length>10) will be just fine to match arrays with more than ten elements, but ?(process.exit()) will not get evaluated since process would yield a ReferenceError. This method is even safer than vm.runInNewContext, since the script engine itself is more limited and entirely distinct from the one running the application code. See more details in the implementation of the evaluator.

Grammar

This project uses a formal BNF grammar to parse JSONPath expressions, an attempt at reverse-engineering the intent of the original implementation, which parses via a series of creative regular expressions. The original regex approach can sometimes be forgiving for better or for worse (e.g., $['store] => $['store']), and in other cases, can be just plain wrong (e.g. [ => $).

Other Minor Differences

As a result of using a real parser and static evaluation, there are some arguable bugs in the original library that have not been carried through here:

  • strings in subscripts may now be double-quoted
  • final step arguments in slice operators may now be negative
  • script expressions may now contain . and @ characters not referring to instance variables
  • subscripts no longer act as character slices on string elements
  • non-ascii non-word characters are no-longer valid in member identifier names; use quoted subscript strings instead (e.g., $['$'] instead of $.$)
  • unions now yield real unions with no duplicates rather than concatenated results

License

MIT

NPM DownloadsLast 30 Days