Jersey + Google Gson Example

This tutorial explains how to use google Gson with Jersey 2.x. There are some other java libraries also capable of doing this conversion e.g. MOXy, Jackson or JSONP; but Gson stands among very few which do not require any pre-annotated java classes OR sourcecode of java classes in any way.

Table of Contents

Maven dependencies/changes
Create Gson Provider
Register Gson Provider
Extending Gson Functionality
Demo

Jersey does not provide any inbuilt support for Gson, as it provide for MOXy and JSONP etc. But Jersey provides discovery mechanism to scan various configurable components of application, via implementing some interfaces and registering implementations to application configuration.

Gson can be used with Jersey as JSON serializer/deserializer by implementing interfaces javax.ws.rs.ext.MessageBodyWriter and javax.ws.rs.ext.MessageBodyReader, and register to configuration either using @Provider annotation OR using ResourceConfig.register() method.

Let’s see all steps one by one.

Maven dependencies

First include Gson dependencies.

<dependency>
	<groupId>com.google.code.gson</groupId>
	<artifactId>gson</artifactId>
	<version>2.2.4</version>
</dependency>

Create Gson Provider

Now create a class implementing interfaces javax.ws.rs.ext.MessageBodyWriter and javax.ws.rs.ext.MessageBodyReader, and override it’s methods.

package com.howtodoinjava.jersey.provider;

import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.UnsupportedEncodingException;
import java.lang.annotation.Annotation;
import java.lang.reflect.Type;

import javax.ws.rs.WebApplicationException;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.MultivaluedMap;
import javax.ws.rs.ext.MessageBodyReader;
import javax.ws.rs.ext.MessageBodyWriter;

import com.google.gson.FieldNamingPolicy;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

public class GsonMessageBodyHandler implements MessageBodyWriter<Object>,
		MessageBodyReader<Object> {
	private static final String UTF_8 = "UTF-8";

	private Gson gson;

	//Customize the gson behavior here
	private Gson getGson() {
		if (gson == null) {
			final GsonBuilder gsonBuilder = new GsonBuilder();
			gson = gsonBuilder.disableHtmlEscaping()
					.setFieldNamingPolicy(FieldNamingPolicy.UPPER_CAMEL_CASE)
					.setPrettyPrinting()
					.serializeNulls()
					.create();
		}
		return gson;
	}

	@Override
	public boolean isReadable(Class<?> type, Type genericType,
			java.lang.annotation.Annotation[] annotations, MediaType mediaType) {
		return true;
	}

	@Override
	public Object readFrom(Class<Object> type, Type genericType,
			Annotation[] annotations, MediaType mediaType,
			MultivaluedMap<String, String> httpHeaders, InputStream entityStream) {
		InputStreamReader streamReader = null;
		try {
			streamReader = new InputStreamReader(entityStream, UTF_8);
		} catch (UnsupportedEncodingException e) {
			e.printStackTrace();
		}
		try {
			Type jsonType;
			if (type.equals(genericType)) {
				jsonType = type;
			} else {
				jsonType = genericType;
			}
			return getGson().fromJson(streamReader, jsonType);
		} finally {
			try {
				streamReader.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

	@Override
	public boolean isWriteable(Class<?> type, Type genericType,
			Annotation[] annotations, MediaType mediaType) {
		return true;
	}

	@Override
	public long getSize(Object object, Class<?> type, Type genericType,
			Annotation[] annotations, MediaType mediaType) {
		return -1;
	}

	@Override
	public void writeTo(Object object, Class<?> type, Type genericType,
			Annotation[] annotations, MediaType mediaType,
			MultivaluedMap<String, Object> httpHeaders,
			OutputStream entityStream) throws IOException,
			WebApplicationException {
		OutputStreamWriter writer = new OutputStreamWriter(entityStream, UTF_8);
		try {
			Type jsonType;
			if (type.equals(genericType)) {
				jsonType = type;
			} else {
				jsonType = genericType;
			}
			getGson().toJson(object, jsonType, writer);
		} finally {
			writer.close();
		}
	}
}

Register Gson Provider

Now register above class with application resource config.

package com.howtodoinjava.jersey;

import org.glassfish.jersey.filter.LoggingFilter;
import org.glassfish.jersey.server.ResourceConfig;
import com.howtodoinjava.jersey.provider.GsonMessageBodyHandler;

public class CustomApplication extends ResourceConfig 
{
	public CustomApplication() 
	{
		packages("com.howtodoinjava.jersey");
		register(LoggingFilter.class);
		register(GsonMessageBodyHandler.class);
	}
}

Extending Gson Functionality

You can extend/customize Gson behavior anytime inside GsonMessageBodyHandler.getGson() method.

private Gson getGson() {
	if (gson == null) {
		final GsonBuilder gsonBuilder = new GsonBuilder();
		gson = gsonBuilder.disableHtmlEscaping()
				.setFieldNamingPolicy(FieldNamingPolicy.UPPER_CAMEL_CASE)
				.setPrettyPrinting()
				.serializeNulls()
				.create();
	}
	return gson;
}

Demo

Now if you access any REST resource through any REST client, you will get desired JSON output.

Hit the URL : http://localhost:8080/JerseyDemos/rest/employees

Now the output will be:

{
  "EmployeeList": [
    {
      "Id": 1,
      "Name": "Lokesh Gupta"
    },
    {
      "Id": 2,
      "Name": "Alex Kolenchiskey"
    },
    {
      "Id": 3,
      "Name": "David Kameron"
    }
  ]
}

Happy Learning !!

Leave a Reply

0 Comments
Inline Feedbacks
View all comments

About Us

HowToDoInJava provides tutorials and how-to guides on Java and related technologies.

It also shares the best practices, algorithms & solutions and frequently asked interview questions.

Our Blogs

REST API Tutorial