JSONPath Cheat Sheet: Syntax, Examples, and Quick Reference
JSONPath lets you extract data from JSON documents using simple expressions — like CSS selectors for JSON. This cheat sheet covers every operator with examples you can copy and use immediately. Bookmark this page for quick reference.
Sample Data
All examples in this cheat sheet use this JSON document:
{
"store": {
"name": "TechBooks",
"book": [
{ "category": "reference", "author": "Nigel Rees",
"title": "Sayings of the Century", "price": 8.95, "in_stock": true },
{ "category": "fiction", "author": "Evelyn Waugh",
"title": "Sword of Honour", "price": 12.99, "in_stock": false },
{ "category": "fiction", "author": "Herman Melville",
"title": "Moby Dick", "isbn": "0-553-21311-3", "price": 8.99, "in_stock": true },
{ "category": "fiction", "author": "J.R.R. Tolkien",
"title": "The Lord of the Rings", "isbn": "0-395-19395-8", "price": 22.99, "in_stock": true }
],
"bicycle": { "color": "red", "price": 399.99 }
}
}Try these expressions live in our JSONPath tester — paste the data above and run any query.
Core Syntax Reference
| Expression | Description | Example | Result |
|---|---|---|---|
$ | Root object | $ | Entire document |
.key | Child property | $.store.name | "TechBooks" |
['key'] | Child (bracket notation) | $['store']['name'] | "TechBooks" |
[n] | Array index (0-based) | $.store.book[0] | First book object |
[-n] | Array index from end | $.store.book[-1] | Last book object |
[*] | All array elements | $.store.book[*] | All 4 book objects |
.* | All object properties | $.store.bicycle.* | ["red", 399.99] |
[start:end] | Array slice | $.store.book[0:2] | First 2 books |
[start:end:step] | Array slice with step | $.store.book[::2] | Every other book |
.. | Recursive descent | $..price | All prices at any depth |
[?()] | Filter expression | $.store.book[?(@.price < 10)] | Books under $10 |
@ | Current element (in filters) | @.price | Price of current item |
Property Access Examples
# Direct property
$.store.name → "TechBooks"
# Nested property
$.store.bicycle.color → "red"
# Bracket notation (required for special chars)
$.store['bicycle']['color'] → "red"
$['store']['book'][0]['title'] → "Sayings of the Century"
# Property with dash or space
$['my-property'] → value of "my-property"
$['property name'] → value of "property name"Try it live: Paste the sample data above into our JSONPath tester and run any expression from this cheat sheet to see results instantly.
Array Access Examples
# First element
$.store.book[0] → first book object
# Last element
$.store.book[-1] → last book (Lord of the Rings)
# Specific index
$.store.book[2] → third book (Moby Dick)
# Multiple indices
$.store.book[0,2] → first and third books
# All elements
$.store.book[*] → all 4 book objects
# Specific field from all elements
$.store.book[*].title → ["Sayings of the Century", "Sword of Honour",
"Moby Dick", "The Lord of the Rings"]
$.store.book[*].price → [8.95, 12.99, 8.99, 22.99]Array Slicing
# First two elements [start:end]
$.store.book[0:2] → books at index 0, 1
# Skip first element
$.store.book[1:] → books at index 1, 2, 3
# Last two elements
$.store.book[-2:] → books at index 2, 3
# Every other element [start:end:step]
$.store.book[::2] → books at index 0, 2
# Reverse order
$.store.book[::-1] → all books, reversedRecursive Descent (..)
The .. operator searches the entire document tree. Use it to find values at any nesting depth:
# All prices anywhere in the document
$..price → [8.95, 12.99, 8.99, 22.99, 399.99]
(includes bicycle price!)
# All authors
$..author → ["Nigel Rees", "Evelyn Waugh",
"Herman Melville", "J.R.R. Tolkien"]
# All ISBN values (only some books have them)
$..isbn → ["0-553-21311-3", "0-395-19395-8"]
# All values named "color"
$..color → ["red"]Filter Expressions
Filters let you select elements based on conditions. The @ symbol refers to the current element being evaluated:
Comparison filters
# Books cheaper than $10
$.store.book[?(@.price < 10)]
→ [Sayings of the Century ($8.95), Moby Dick ($8.99)]
# Books that cost exactly $12.99
$.store.book[?(@.price == 12.99)]
→ [Sword of Honour]
# Books $10 or more
$.store.book[?(@.price >= 10)]
→ [Sword of Honour ($12.99), Lord of the Rings ($22.99)]
# Fiction books
$.store.book[?(@.category == 'fiction')]
→ [Sword of Honour, Moby Dick, Lord of the Rings]
# Non-fiction books
$.store.book[?(@.category != 'fiction')]
→ [Sayings of the Century]Existence filters
# Books that have an ISBN
$.store.book[?(@.isbn)]
→ [Moby Dick, Lord of the Rings]
# Books without an ISBN
$.store.book[?(!@.isbn)]
→ [Sayings of the Century, Sword of Honour]
# Books that are in stock
$.store.book[?(@.in_stock == true)]
→ [Sayings of the Century, Moby Dick, Lord of the Rings]Combining filters
# Fiction books under $15
$.store.book[?(@.category == 'fiction' && @.price < 15)]
→ [Sword of Honour, Moby Dick]
# Books that are cheap OR in stock
$.store.book[?(@.price < 10 || @.in_stock == true)]
→ [Sayings of the Century, Moby Dick, Lord of the Rings]
# In-stock fiction books with ISBN
$.store.book[?(@.category == 'fiction' && @.in_stock == true && @.isbn)]
→ [Moby Dick, Lord of the Rings]JSONPath vs jq Equivalents
If you switch between JSONPath (in code) and jq (on the command line), this mapping helps:
| Task | JSONPath | jq |
|---|---|---|
| Root | $ | . |
| Property | $.store.name | .store.name |
| Array element | $.book[0] | .book[0] |
| All elements | $.book[*] | .book[] |
| All titles | $.book[*].title | .book[].title |
| Recursive | $..price | .. | .price? // empty |
| Filter | $.book[?(@.price<10)] | .book[] | select(.price < 10) |
| Slice | $.book[0:2] | .book[0:2] |
| Length | $.book.length | .book | length |
Working with complex nested JSON? Use our Tree Viewer to visualize the structure first — it makes it much easier to figure out the right JSONPath expression.
Using JSONPath in Code
JavaScript
// npm install jsonpath-plus
import { JSONPath } from 'jsonpath-plus';
const titles = JSONPath({ path: '$.store.book[*].title', json: data });
// ["Sayings of the Century", "Sword of Honour", "Moby Dick", "The Lord of the Rings"]
const cheap = JSONPath({ path: '$.store.book[?(@.price<10)]', json: data });
// [{ title: "Sayings of the Century", ... }, { title: "Moby Dick", ... }]Python
# pip install jsonpath-ng
from jsonpath_ng.ext import parse
expr = parse("$.store.book[*].title")
titles = [match.value for match in expr.find(data)]
# ["Sayings of the Century", "Sword of Honour", "Moby Dick", "The Lord of the Rings"]
expr = parse("$.store.book[?price < 10]")
cheap = [match.value for match in expr.find(data)]Java
// com.jayway:json-path
import com.jayway.jsonpath.JsonPath;
List<String> titles = JsonPath.read(json, "$.store.book[*].title");
// ["Sayings of the Century", "Sword of Honour", "Moby Dick", "The Lord of the Rings"]
List<Map> cheapBooks = JsonPath.read(json, "$.store.book[?(@.price < 10)]");Command line (jq)
# All titles
cat data.json | jq '.store.book[].title'
# Books under $10
cat data.json | jq '.store.book[] | select(.price < 10)'
# Count books
cat data.json | jq '.store.book | length'
# Get unique categories
cat data.json | jq '[.store.book[].category] | unique'Not sure if your JSON is valid? Run it through our JSON Validator before querying — JSONPath on invalid JSON gives unpredictable results.
Common Patterns
Extract all values of a specific field
# All emails from a user list
$.users[*].email
# All error messages from a response
$.errors[*].message
# All image URLs from a product catalog
$.products[*].images[0] → first image of each productNavigate API pagination
# Get the data array from a paginated response
$.data[*]
# Get pagination info
$.meta.total_count
$.meta.next_page
$.links.nextQuery Kubernetes resources
# All container images in a deployment
$.spec.template.spec.containers[*].image
# All environment variables
$.spec.template.spec.containers[*].env[*].name
# Resource limits
$.spec.template.spec.containers[0].resources.limitsParse package.json
# All dependency names
$.dependencies → entire dependencies object
$.devDependencies → entire devDependencies object
$.scripts.test → test script commandTips and Gotchas
- Indices are 0-based.
$.items[1]is the second item, not the first. - Bracket notation for special keys. Use
$['my-key']when keys contain dashes, dots, or spaces. - Recursive descent is expensive.
$..scans the entire document. Use specific paths when you know the structure. - Filter syntax varies. Some libraries use
@.price, others use@['price']. Check your library's docs. - Missing paths return empty. If a path doesn't exist, most implementations return an empty array — not an error.
- String comparison is case-sensitive.
[?(@.status == 'Active')]won't match"active".
Try it live
Paste JSON and test any JSONPath expression from this cheat sheet in our interactive tester.
Open JSONPath Tester🔗 Related Tools & Resources
Explore these related JSON tools and guides