9 JSON R packages
R has 3 packages for working with JSON data
"RJSONIO"
by Duncan Temple Lang"rjson"
by Alex Couture-Beil"jsonlite"
by Jeroen Ooms, Duncan Temple Lang, Jonathan Wallace
All packages provide 2 main functions, toJSON()
and fromJSON()
, that allow
conversion to and from data in JSON format, respectively.
We’ll focus on the functions from "jsonlite"
.
For illustration purposes, let us consider the package "jsonlite"
.
There are 2 primary functions in "jsonlite"
:
toJSON()
converts an R object to a string in JSONfromJSON()
converts JSON content to R objects
9.1 Function toJSON()
The function jsonlite::toJSON()
converts an R object to a string in JSON.
Example: single number to JSON-array
Let’s begin with a super simple example by passing a single data value to the
function toJSON()
:
Example: vectors to JSON-arrays
Consider the following vectors
Applying toJSON()
to the vectors num
and lts
produces JSON arrays:
The argument pretty = TRUE
allows you to obtain a JSON string with added
indentation whitespace:
toJSON(num, pretty = TRUE)
#> [1, 2, 3, 4, 5]
toJSON(lts, pretty = TRUE)
#> ["a", "b", "c", "d", "e"]
What about an R vector with named elements? For example, here’s a vector vec
Converting vec
to JSON, we get:
As you can tell, the names of the elements in vec
are lost in translation.
Example: matrix to JSON-array
Here’s another example from an matrix to a JSON array:
mat <- matrix(9:1, nrow = 3, ncol = 3)
mat
#> [,1] [,2] [,3]
#> [1,] 9 6 3
#> [2,] 8 5 2
#> [3,] 7 4 1
toJSON()
converts an R matrix into a JSON-array
Notice that the returned output arranges the values of the matrix row-by-row,
also referred to as row-major. This means that when the input is an R matrix,
toJSON()
uses its argument matrix = "rowmajor"
.
You can change the arrangement to column-major by specifying the argument
matrix = "columnmajor"
:
Example: data frame to JSON-object
We can also use toJSON()
on data frames. Here’s an example of an assembled
data frame swdf
which will be converted to a JSON-object:
# toy data
sw_data <- rbind(
c("Anakin", "male", "Tatooine", "41.9BBY", "yes"),
c("Amidala", "female", "Naboo", "46BBY", "no"),
c("Luke", "male", "Tatooine", "19BBY", "yes"),
c("Leia", "female", "Alderaan", "19BBY", "no")
)
# convert to data.frame and add column names
swdf <- data.frame(sw_data, stringsAsFactors = FALSE)
names(swdf) <- c("Name", "Gender", "Homeworld", "Born", "Jedi")
swdf
#> Name Gender Homeworld Born Jedi
#> 1 Anakin male Tatooine 41.9BBY yes
#> 2 Amidala female Naboo 46BBY no
#> 3 Luke male Tatooine 19BBY yes
#> 4 Leia female Alderaan 19BBY no
The default output when you pass a data frame to jsonlite::toJSON()
is
# convert R data.frame to JSON
sw_json = toJSON(swdf)
sw_json
#> [{"Name":"Anakin","Gender":"male","Homeworld":"Tatooine","Born":"41.9BBY","Jedi":"yes"},{"Name":"Amidala","Gender":"female","Homeworld":"Naboo","Born":"46BBY","Jedi":"no"},{"Name":"Luke","Gender":"male","Homeworld":"Tatooine","Born":"19BBY","Jedi":"yes"},{"Name":"Leia","Gender":"female","Homeworld":"Alderaan","Born":"19BBY","Jedi":"no"}]
The argument dataframe
gives you more control on the output. This argument
has three options:
"rows"
: each row is converted to a JSON-object with key-value pairs formed by"column_name": "row_value"
;
toJSON(swdf, dataframe = "rows")
#> [{"Name":"Anakin","Gender":"male","Homeworld":"Tatooine","Born":"41.9BBY","Jedi":"yes"},{"Name":"Amidala","Gender":"female","Homeworld":"Naboo","Born":"46BBY","Jedi":"no"},{"Name":"Luke","Gender":"male","Homeworld":"Tatooine","Born":"19BBY","Jedi":"yes"},{"Name":"Leia","Gender":"female","Homeworld":"Alderaan","Born":"19BBY","Jedi":"no"}]
"columns"
: each column is converted into a JSON-object with a single key for each column, and values stored as arrays;
toJSON(swdf, dataframe = "columns")
#> {"Name":["Anakin","Amidala","Luke","Leia"],"Gender":["male","female","male","female"],"Homeworld":["Tatooine","Naboo","Tatooine","Alderaan"],"Born":["41.9BBY","46BBY","19BBY","19BBY"],"Jedi":["yes","no","yes","no"]}
"values"
: the values in each column are converted to a JSON-array, and the names of the columns are lost.
9.2 Function fromJSON()
In practice, instead of converting R objects to JSON objects, it is more common to have data in JSON format which needs to be converted into an R object.
The function jsonlite::fromJSON()
converts a JSON-object to an R object.
Example: JSON-object to R object
Consider a simple JSON-object, and its conversion to R with
jsonlite::fromJSON()
Notice that the obtained object is an R list in which the key becomes the name of the list, and the value becomes the content of the list’s element.
Consider a less simple JSON-object:
json_obj2 <- '{"name1": "Nicole", "name2": "Pleuni", "name3": "Rori"}'
fromJSON(json_obj2)
#> $name1
#> [1] "Nicole"
#>
#> $name2
#> [1] "Pleuni"
#>
#> $name3
#> [1] "Rori"
Another example:
Example: JSON-object to R object
Suppose you have a JSON object with the following data:
{
"Name": ["Anakin","Amidala","Luke","Leia"],
"Gender": ["male","female","male","female"],
"Homeworld": ["Tatooine","Naboo","Tatooine","Alderaan"],
"Born": ["41.9BBY","46BBY","19BBY","19BBY"],
"Jedi": ["yes","no","yes","no"]
}
and assume that the above data is stored as a single (continuous) string in
an R character vector json_sw
; applying fromJSON()
to this string gives
you the following list:
fromJSON(json_sw)
#> $Name
#> [1] "Anakin" "Amidala" "Luke" "Leia"
#>
#> $Gender
#> [1] "male" "female" "male" "female"
#>
#> $Homeworld
#> [1] "Tatooine" "Naboo" "Tatooine" "Alderaan"
#>
#> $Born
#> [1] "41.9BBY" "46BBY" "19BBY" "19BBY"
#>
#> $Jedi
#> [1] "yes" "no" "yes" "no"
Can this be transformed into a data frame? Yes, by passing the obtained list
to the function data.frame()
:
9.3 Reading JSON Data
Now that we have discussed the basics of JSON, and the common ways to convert
fromJSON()
and toJSON()
, let’s see how to read JSON data from the Web.
One of the typical ways to import JSON data from the Web to R is by passing
the url directly to fromJSON()
. Another way is by passing the name of the
file with the JSON content as a single string to the function fromJSON()
.
Here’s an example reading a JSON string from the website Advice Slip. The url https://api.adviceslip.com/advice gives you a random advice (see figure below):

Figure 9.1: Random advice from Advice Slip
As you can tell, the content is a simple JSON string
#> $slip
#> $slip$id
#> [1] 9
#>
#> $slip$advice
#> [1] "True happiness always resides in the quest!"
Example: Colors in Hexadecimal Notation
The following data comes from one of Dave Eddy’s github repositories:
https://raw.githubusercontent.com/bahamas10/css-color-names/master/css-color-names.json
This is a JSON-object in which the keys are color-names, and the values are the hexadecimal digits of the corresponding color:
{
"aliceblue": "#f0f8ff",
"antiquewhite": "#faebd7",
"aqua": "#00ffff",
"aquamarine": "#7fffd4",
"azure": "#f0ffff",
...
"wheat": "#f5deb3",
"white": "#ffffff",
"whitesmoke": "#f5f5f5",
"yellow": "#ffff00",
"yellowgreen": "#9acd32"
}
We pass the url to jsonlite::fromJSON()
colors_json <- "https://raw.githubusercontent.com/bahamas10/css-color-names/master/css-color-names.json"
hex_colors <- fromJSON(colors_json)
The output in hex_colors
is a list with 148 elements;
the first five elements are displayed below: