Commit 16c6984a authored by Karsten Loesing's avatar Karsten Loesing
Browse files

Replace Gson with Jackson.

Implements #26159.
parent 77bbd742
# Changes in version 2.4.0 - 2018-05-??
* Medium changes
- Replace Gson with Jackson. Applications must provide Jackson
2.8.6 or compatible as dependency and do not need to provide Gson
as dependency anymore.
# Changes in version 2.3.0 - 2018-04-18
* Medium changes
......
......@@ -15,7 +15,9 @@
<patternset id="runtime" >
<include name="commons-compress-1.13.jar"/>
<include name="gson-2.4.jar"/>
<include name="jackson-annotations-2.8.6.jar"/>
<include name="jackson-core-2.8.6.jar"/>
<include name="jackson-databind-2.8.6.jar"/>
<include name="slf4j-api-1.7.22.jar" />
<include name="xz-1.6.jar"/>
</patternset>
......
......@@ -3,8 +3,6 @@
package org.torproject.descriptor.index;
import com.google.gson.annotations.Expose;
import java.util.SortedSet;
/**
......@@ -15,22 +13,19 @@ import java.util.SortedSet;
public class DirectoryNode implements Comparable<DirectoryNode> {
/** Path (i.e. directory name) is exposed in JSON. */
@Expose
public final String path;
/** The file list is exposed in JSON. Sorted according to path. */
@Expose
public final SortedSet<FileNode> files;
/** The directory list is exposed in JSON. Sorted according to path. */
@Expose
public final SortedSet<DirectoryNode> directories;
/* Added to satisfy Gson. */
/* Added to satisfy Jackson. */
private DirectoryNode() {
path = null;
files = null;
directories = null;
this.path = null;
this.files = null;
this.directories = null;
}
/** A directory for the JSON structure. */
......
......@@ -3,8 +3,7 @@
package org.torproject.descriptor.index;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
import com.fasterxml.jackson.annotation.JsonIgnore;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
......@@ -25,18 +24,15 @@ public class FileNode implements Comparable<FileNode> {
private static Logger log = LoggerFactory.getLogger(FileNode.class);
/** Path (i.e. file name) is exposed in JSON. */
@Expose
public final String path;
/** The file size is exposed in JSON. */
@Expose
public final long size;
/** The last modified date-time string is exposed in JSON. */
@Expose
@SerializedName("last_modified")
public final String lastModified;
@JsonIgnore
private long lastModifiedMillis;
/* Added to satisfy Gson. */
......
......@@ -5,19 +5,20 @@ package org.torproject.descriptor.index;
import org.torproject.descriptor.internal.FileType;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
import com.fasterxml.jackson.annotation.JsonAutoDetect;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonPropertyOrder;
import com.fasterxml.jackson.annotation.PropertyAccessor;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.PropertyNamingStrategy;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.Reader;
import java.net.URL;
import java.net.URLConnection;
import java.nio.file.Files;
......@@ -34,6 +35,7 @@ import java.util.TreeSet;
*
* @since 1.4.0
*/
@JsonPropertyOrder({ "created", "revision", "path", "directories", "files" })
public class IndexNode {
private static Logger log = LoggerFactory.getLogger(IndexNode.class);
......@@ -48,29 +50,30 @@ public class IndexNode {
public static final IndexNode emptyNode = new IndexNode("", "",
new TreeSet<FileNode>(), new TreeSet<DirectoryNode>());
private static ObjectMapper objectMapper = new ObjectMapper()
.setPropertyNamingStrategy(PropertyNamingStrategy.SNAKE_CASE)
.setSerializationInclusion(JsonInclude.Include.NON_EMPTY)
.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.NONE)
.setVisibility(PropertyAccessor.FIELD, JsonAutoDetect.Visibility.ANY);
/** The created date-time is exposed in JSON as 'index_created' field. */
@Expose
@SerializedName("index_created")
@JsonProperty("index_created")
public final String created;
/** The software's build revision JSON as 'build_revision' field. */
@Expose
@SerializedName("build_revision")
@JsonProperty("build_revision")
public final String revision;
/** Path (i.e. base url) is exposed in JSON. */
@Expose
public final String path;
/** The directory list is exposed in JSON. Sorted according to path. */
@Expose
public final SortedSet<DirectoryNode> directories;
/** The file list is exposed in JSON. Sorted according to path. */
@Expose
public final SortedSet<FileNode> files;
/* Added to satisfy Gson. */
/* Added to satisfy Jackson. */
private IndexNode() {
this.created = null;
this.revision = null;
......@@ -119,11 +122,7 @@ public class IndexNode {
* Returns an empty IndexNode in case of an error.
*/
public static IndexNode fetchIndex(InputStream is) throws IOException {
Gson gson = new GsonBuilder().excludeFieldsWithoutExposeAnnotation()
.create();
try (Reader reader = new InputStreamReader(is)) {
return gson.fromJson(reader, IndexNode.class);
}
return objectMapper.readValue(is, IndexNode.class);
}
/** Return a map of file paths for the given directories. */
......@@ -185,10 +184,8 @@ public class IndexNode {
}
/** Write JSON representation of the given index node to a string. */
public static String makeJsonString(IndexNode indexNode) {
Gson gson = new GsonBuilder().excludeFieldsWithoutExposeAnnotation()
.create();
return gson.toJson(indexNode);
public static String makeJsonString(IndexNode indexNode) throws IOException {
return objectMapper.writeValueAsString(indexNode);
}
/** For debugging purposes. */
......
......@@ -7,6 +7,8 @@ import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import com.fasterxml.jackson.core.JsonParseException;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.TemporaryFolder;
......@@ -114,7 +116,7 @@ public class IndexNodeTest {
IndexNode.fetchIndex(indexUrl.toString());
}
@Test(expected = com.google.gson.JsonSyntaxException.class)
@Test(expected = JsonParseException.class)
public void testWrongJson() throws Exception {
URL indexUrl = getClass().getClassLoader().getResource("index1.json.gz");
IndexNode.fetchIndex(indexUrl.openStream());
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment