JMESPath is a JSON query language. JMESPath in Python allows you to obtain the data you need from a JSON document or dictionary easily. This library is available for Python, but also for many other programming languages, meaning that if you master the JMESPath query language, you can use it in many places.
Table of Contents
The problem JMESPath solves
As weβve seen on the previous page, itβs easy to get a nested value from a Python dictionary using Pythonβs own JSON library. For example: doc["person"]["age"]
will get you the nested value for age in a document that looks like this:
{ "persons": { "name": "erik", "age": "38" } }
But what if you want to extract all the age fields from an array of persons, in a document like the one below?
{ "persons": [ { "name": "erik", "age": 38 }, { "name": "john", "age": 45 }, { "name": "rob", "age": 14 } ] }
We could write a Python for-loop and loop over all the persons. Easy peasy. But loops are slow and introduce complexity to your code. This is where JMESPath comes in!
Installing JMESPath for Python
JMESPath is not part of the Python standard library, meaning youβll need to install it with pip or pipenv. The JMESPath package is hosted on PyPI, like most Python packages. Itβs available under the unsurprising name jmespath.
For example, when using pip in a virtual environment, you can install with pip, and import the module as follows:
$ pip3 install jmespath
$ python3
Python 3.8.2 (default, Jul 16 2020, 14:00:26)
>>> import jmespath
>>> j = { "people": [{ "name": "erik", "age": 38 }] }
>>> jmespath.search("people[*].age", j)
[38]
>>>
Code language: Shell Session (shell)
JMESPath Python examples
Letβs start with some simple use-cases. Weβll fetch the first person from the array, and then get the first personβs age:
>>> jmespath.search('persons[0]', persons) {'name': 'erik', 'age': 38} >>> jmespath.search('persons[0].age', persons) 38
In the problem statement above, we wanted to extract all the age fields from the array of persons in the JSON document. This JMESPath expression will get the job done:
>>> import jmespath >>> persons = { ... "persons": [ ... { "name": "erik", "age": 38 }, ... { "name": "john", "age": 45 }, ... { "name": "rob", "age": 14 } ... ] ... } >>> jmespath.search('persons[*].age', persons) [38, 45, 14]
Suppose you want to filter the list, and only get the ages for people named βerikβ. You can do so with a filter:
>>> jmespath.search("persons[?name=='erik'].age", persons) [38]
Note that weβre now using double quotes because we need to quote the name inside the filter expression.
Keep learning
Youβre now ready to start experimenting! If you want to learn more, try these links:
- The interactive tutorial
- The examples on the JMESPath site!