Jackson library makes it possible for us to convert data in JSON form to different data formats and vice versa. In this tutorial, I will show you how to convert data from JSON to CSV!
First, I will create a new Maven project:
with Jackson Dataformat CSV dependency as follows:
1 2 3 4 5 |
<dependency> <groupId>com.fasterxml.jackson.dataformat</groupId> <artifactId>jackson-dataformat-csv</artifactId> <version>2.18.1</version> </dependency> |
As an example, I will convert the following JSON string to a CSV file:
1 2 3 4 5 6 |
{ "name" : "Khanh", "code" : 99, "date" : "04-07-2017", "gotMarried": true } |
To start, I will create a new Application class with the main() method as follows:
1 2 3 4 5 6 7 8 |
package com.huongdanjava.jackson; public class Application { public static void main(String[] args) { } } |
First, you can use the readTree() method of Jackson’s ObjectMapper object to read the JSON content that you need to convert.
There are many overload readTree() methods to help you do this:
You can read JSON content from file, from string, from byte,… Depending on your need, please use overload methods of readTree() for reasonable. Here, I will save the above JSON content into the data.json file in the src/main/resources directory for an example:
1 |
JsonNode jsonNode = new ObjectMapper().readTree(new File("src/main/resources/data.json")); |
This JSON content will be saved to the JsonNode object as you can see!
Next, we will use the CsvSchema Builder object to define the columns of the CSV file.
For my example, the code would look like this:
1 2 |
CsvSchema.Builder builder = CsvSchema.builder(); jsonNode.elements().next().fieldNames().forEachRemaining(f -> builder.addColumn(f)); |
The above code is that we are getting all the keys in the JSON data, including name, code, date, gotMarried in our example, to define it as a column in the CSV file.
You can also specify which data, corresponding to which key in the JSON data, is converted to a CSV file by defining the CsvSchema Builder as follows:
1 2 3 4 |
CsvSchema.Builder builder = CsvSchema.builder() .addColumn("name") .addColumn("code") .addColumn("date"); |
With this code, my example only has the data of the column name, code and date converted. I will use this code in this tutorial as an example.
After you have the CsvSchema Builder, you can get the CsvSchema object as follows:
1 |
CsvSchema csvSchema = builder.build().withHeader(); |
Now we can use CsvMapper to convert JSON data to CSV data:
1 2 3 4 5 |
CsvMapper csvMapper = new CsvMapper(); csvMapper.configure(Feature.IGNORE_UNKNOWN, true); csvMapper.writerFor(JsonNode.class) .with(csvSchema) .writeValue(new File("src/main/resources/data.cvs"), jsonNode); |
Because I am defining the columns manually, there will be columns that CsvMapper is not aware of when doing the conversion. Therefore, I need to configure it to ignore those columns.
In this example, I save the output file data.csv in the directory src/main/resources.
The entire code of the example is as follows:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
package com.huongdanjava.jackson; import com.fasterxml.jackson.core.JsonGenerator.Feature; import com.fasterxml.jackson.databind.JsonNode; import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.dataformat.csv.CsvMapper; import com.fasterxml.jackson.dataformat.csv.CsvSchema; import java.io.File; import java.io.IOException; public class Application { public static void main(String[] args) throws IOException { JsonNode jsonNode = new ObjectMapper().readTree(new File("src/main/resources/data.json")); CsvSchema.Builder builder = CsvSchema.builder() .addColumn("name") .addColumn("code") .addColumn("date"); CsvSchema csvSchema = builder.build().withHeader(); CsvMapper csvMapper = new CsvMapper(); csvMapper.configure(Feature.IGNORE_UNKNOWN, true); csvMapper.writerFor(JsonNode.class) .with(csvSchema) .writeValue(new File("src/main/resources/data.csv"), jsonNode); } } |
The output when running the program is as follows:
Jackson will not work with nested JSON data types.
For example, if you have the following JSON string:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
{ "name" : "Khanh", "code" : 99, "date" : "04-07-2017", "gotMarried": true, "group" : [ "ABC", "XYZ" ], "class" : { "name" : "A", "code" : 123 } } |
then when you code, you need to manually define the names of the columns to remove these nested JSON guys!