Free JSONPath Tester
Paste JSON and a JSONPath expression to see every value it matches, or the exact location of each one.
What is a JSONPath Tester?
JSONPath is a way to point at parts of a JSON document, the way XPath points into XML. An expression like $.store.book[*].author picks every author. This tester runs an expression on JSON you paste and lists each match.
Evaluation uses jsonpath-plus, a widely used JavaScript implementation of Stefan Goessner’s original JSONPath, with filters run in its sandboxed evaluator. Values mode shows what matched, and Paths mode shows the normalized path of each match, such as $['store']['book'][0]['author'].
Key Features
Values or Locations
Switch between the matched values and their normalized paths. Paths tell you exactly where each match lives, which helps when writing a patch or a fix.
Filters, Wildcards and Descent
Filters like [?(@.price < 10)], wildcards, slices, unions and the recursive .. operator all work, as in Goessner’s article.
Sandboxed Filters
Filter expressions run in a restricted evaluator that can’t reach browser globals, so pasted paths can’t run arbitrary code.
Clear Syntax Errors
Unclosed brackets, the RFC 9535 filter form and filters that try to call functions get their own messages instead of an empty result.
JSON Stays Local
The document is searched in your browser and isn’t uploaded, so API responses and customer data stay private.
Perfect for everyone
- API testers writing assertions
- QA engineers using Postman or REST Assured
- Developers extracting values in Kubernetes or monitoring tools
- Anyone learning JSONPath
How to Use the JSONPath Tester
Paste JSON, write a path starting with $, and pick values or paths.
Paste the JSON Document
Copy an API response, a config file or a test fixture into the second box. It must be an object or an array.
Write the Path
Start with $ for the root and add steps: .name for a field, [0] for an index, [*] for every element, and .. to search at any depth.
Add a Filter if Needed
Narrow a list with [?(@.field == value)], where @ is the current element. Combine conditions with && and ||.
Read Values or Paths
Values lists what matched as JSON. Paths lists where each match is, which you can copy into a test or a JSON Patch.
JSONPath Against Goessner’s Bookstore
These run against a trimmed copy of the bookstore document from the original JSONPath article. Each shows the path, three dashes, then the JSON, and the answer is the tester’s output.
“$.store.book[*].author --- {"store":{"book":[{"category":"reference","author":"Nigel Rees","title":"Sayings of the Century","price":8.95},{"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}}}”
“$..price --- {"store":{"book":[{"category":"reference","author":"Nigel Rees","title":"Sayings of the Century","price":8.95},{"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}}}”
“$..book[?(@.price < 10)].title --- {"store":{"book":[{"category":"reference","author":"Nigel Rees","title":"Sayings of the Century","price":8.95},{"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}}}”
“$..book[?(@.isbn)].title --- {"store":{"book":[{"category":"reference","author":"Nigel Rees","title":"Sayings of the Century","price":8.95},{"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}}}”
“$..book[-1:].title --- {"store":{"book":[{"category":"reference","author":"Nigel Rees","title":"Sayings of the Century","price":8.95},{"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}}}”
“$..book[0,1].title --- {"store":{"book":[{"category":"reference","author":"Nigel Rees","title":"Sayings of the Century","price":8.95},{"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}}}”
“$.store.* --- {"store":{"book":[{"title":"Moby Dick"}],"bicycle":{"color":"red","price":19.95}}}”
“$..book[?@.price<10].title --- {"store":{"book":[{"title":"Moby Dick","price":8.99}]}}”
“$.store.book[0 --- {"store":{"book":[{"title":"Moby Dick"}]}}”
“$.store.magazine --- {"store":{"book":[{"title":"Moby Dick"}]}}”
JSONPath Syntax Reference
Goessner’s original JSONPath has a small set of operators. These ten are enough for nearly every query.
$ Is the Root
Every path starts at $, the whole document. jsonpath-plus adds it for you if you leave it off.
“What does $ alone match?”
Dot and Bracket Notation
$.store.book and $['store']['book'] mean the same thing. Use brackets with quotes for names containing dots, spaces or dashes.
“How do you reach a key named first-name?”
Wildcard
[*] or .* matches every element of an array or every member of an object. $.store.* returns both the book list and the bicycle.
“What does $.store.* return?”
Recursive Descent
Two dots search every level below, so $..price finds prices at any depth. It’s handy but can match more than you expect.
“Which operator searches at any depth?”
Array Index
[0] is the first element and [-1] the last. Indexes are zero-based, as in JavaScript.
“Which index is the third book?”
Slices
[start:end:step] takes a range, with the end excluded, as in Python. [-1:] means from the last element to the end.
“What does [0:2] return?”
Unions
A comma between indexes or names picks several at once, as in [0,1] or ['title','price']. Results come back in the order listed.
“How do you pick the first and third books?”
Filters
[?(expression)] keeps elements where the expression is true, with @ as the current element. Comparisons, && and || are allowed.
“How do you keep books priced under 10?”
Existence Tests
A filter with just a field, such as [?(@.isbn)], keeps elements that have that field. It’s the simplest way to find optional data.
“Which books does [?(@.isbn)] keep?”
Normalized Paths
Every match has a canonical address like $['store']['book'][0]['title']. Paths mode shows them, and they never contain wildcards.
“What does a normalized path use for names?”
The Same Query in Other Path Languages
JSONPath often has to be rewritten for another tool. These pairs show the usual equivalents for the bookstore document.
Every Author in JMESPath
JMESPath has no root symbol and uses [*] the same way, so $.store.book[*].author becomes store.book[*].author. Results come back as one list either way.
“What is $.store.book[*].author in JMESPath?”
A Filter in JMESPath
JMESPath filters drop the @ prefix for fields and need numbers in backticks. The condition moves to [?price < `10`].
“What is $..book[?(@.price < 10)] in JMESPath?”
Every Author in jq
jq walks arrays with .[] and starts each path with a dot, so the same query is .store.book[].author. jq prints each match as a separate value.
“What is $.store.book[*].author in jq?”
A Filter in jq
jq filters with select, which passes through elements where the condition is true. The current element is a dot rather than @.
“How does jq keep books under 10?”
Recursive Descent in jq
In jq, the recurse operator, written as two dots, walks every value, so finding all prices needs a guard for values without that key. JSONPath’s $..price is shorter.
“What is $..price in jq?”
One Element as a JSON Pointer
JSON Pointer, from RFC 6901, addresses a single location with slashes and no wildcards. Paths mode gives the normalized path to convert from.
“What is $['store']['book'][0]['title'] as a JSON Pointer?”
kubectl Syntax
kubectl wraps the expression in braces and drops the leading $. A filter keeps its parentheses, as in the original syntax.
“How does kubectl write $.items[*].metadata.name?”
RFC 9535 Syntax
The 2024 standard keeps most selectors but writes filters without parentheses. Convert back by wrapping the condition in parentheses for this tester.
“What is [?@.price < 10] for jsonpath-plus?”
JSONPath Dialects
JSONPath went fifteen years without a standard, so tools differ. Know which one you’re targeting.
Goessner’s Original (2007)
The blog post that defined JSONPath, with filters in parentheses. jsonpath-plus, used here, follows it with a few extensions.
RFC 9535 (2024)
The IETF standard writes filters without parentheses, as in [?@.price < 10], and defines functions such as length and match. Many tools haven’t adopted it yet.
Jayway JsonPath for Java
Used by Spring and REST Assured, it adds functions like length() and min(). Its filter syntax matches the original with parentheses.
Kubernetes kubectl
kubectl -o jsonpath wraps expressions in braces and drops the leading $, and supports range and end for loops. Translate those before testing here.
Postman and API Test Tools
Postman scripts usually navigate JSON in JavaScript, while tools such as Karate and REST Assured accept JSONPath directly in assertions.
PostgreSQL and MySQL
Databases use their own SQL/JSON path language, with lax and strict modes and different filter syntax. Test those in the database itself.
JSONPath Mistakes
These make a query return nothing, too much, or an error.
Mixing Filter Syntaxes
[?@.price < 10] is RFC 9535 syntax and [?(@.price < 10)] is the original. Use the form your tool supports.
Overusing Recursive Descent
$..id matches ids at every level, including nested ones you didn’t mean. Write the full path when you know it.
Expecting a Single Value
JSONPath always returns a list, even for one match. Take the first element in your code or assertion.
Comparing Strings Without Quotes
[?(@.status == active)] compares with an undefined name. Quote string values, as in [?(@.status == 'active')].
Dots in Key Names
$.config.app.name walks three levels, not into a key named app.name. Use $.config['app.name'] instead.
Off-by-One Slices
[0:2] stops before index 2, so it returns two elements. Add one to the end index when you mean inclusive.
Assuming Every Tool Is the Same
Functions, regex filters and negative steps differ between implementations. Test in the same library your code uses.
Treating No Match as an Error
A path that matches nothing returns an empty list, not an error. Check the result length in tests rather than relying on an exception.
When to Reach for a JSONPath Tester
Any time you need to point at data inside JSON and be sure you’re right.
Writing API Test Assertions
Build the path for a REST Assured, Karate or contract test against a real response before committing the test.
Extracting Values in Monitoring
Monitoring and alerting tools read JSON health endpoints with JSONPath. Check the path picks the field the alert needs.
Finding Where a Value Lives
Use Paths mode with recursive descent, like $..email, to discover every location of a field in a large document.
Preparing a JSON Patch
Copy a normalized path and convert it to a JSON Pointer for an RFC 6902 patch operation.
Filtering Kubernetes Output
Prototype the expression here on kubectl get -o json output, then add kubectl’s braces for the real command.
Configuring Integration Tools
Low-code and automation tools often ask for a JSONPath to map fields. Test it first instead of rerunning the integration.
Learning JSONPath
Work through wildcards, slices and filters on the classic bookstore sample and see each result immediately.