RESTful Serialization with Flexjson

XML is too fat for a mobile RESTful API. Therefore, I’m using JavaScript Object Notation (JSON) to exchange data between mobile devices and a cloud service I’m developing. My server environment is J2EE-based, so I chose Flexjson to serialize Java object fields as JSON. This post is a quick overview of my implementation and a lesson learned.

Flexjson is a lightweight Java library that enables object filtering during serialization. If you have a complex object model, serializing the entire object graph is undesirable. Flexjson allows you to pick and choose which objects or fields to serialize.

Here’s simple example of excluding a password field in serialized JSON.

String result =
         new JSONSerializer().
         exclude("password").serialize("user", this);
/*
Client's JSON result
{
   "user": {
   "class": "com.mycompany",
   "email": "somebody@email.com",
   "firstName": "John",
   "lastName": "Doe",
   "phone": "555-1212"
   }
}
*/

The shallow deserialization is limited to: String, Date, Number, Boolean, Character, Enum, Object and null. Subclasses of Object will be serialized except for Collection or Arrays. Consequently, if the deserializer is unable to construct the object, an exception will be thrown.

All objects are built using an ObjectFactory during deserialization and each object must have a constructor that takes no arguments. Users can write their own factories and the library comes with many factories for types such as bytes, characters, dates, and so on. However, an integer object factory is nonexistent. Here’s mine:

public class IntObjectFactory implements ObjectFactory {

	/* (non-Javadoc)
	 * @see flexjson.ObjectFactory#instantiate(flexjson.ObjectBinder,
                                                  java.lang.Object,
                                                  java.lang.reflect.Type,
                                                  java.lang.Class)
	 */

	public Object instantiate(ObjectBinder context,
                                  Object value,
                                  Type targetType,
                                  Class targetClass) {
		 if( value instanceof Number ) {
	            return ((Number)value).intValue();
	        } else {
	            throw context.
                          cannotConvertValueToTargetType(
                                                  value,
                                                  Integer.class
                                                        );
	        }
	    }
}

It was so easy to write, I’m not sure why is wasn’t included in the shipped version.

Lastly, here’s how to use the factory during deserialization:

JSONDeserializer<Map<String, List<SomeObject>>> deserializer =
       new JSONDeserializer<Map<String, List<SomeObject>>>();

Map<String, List<SomeObject>> members =
       deserializer.use(Number.class,
       new IntObjectFactory()).deserialize(returnValue);

For more info check out the Flexjson home page here: http://flexjson.sourceforge.net/

Advertisements
RESTful Serialization with Flexjson

Troubleshooting remote connections to MySQL on Linux

If you encounter a problem when trying to remotely connect to MySQL on Linux, make sure that the bind-address property in the configuration file (/etc/mysql/my.cnf) is set to the machine’s host name. I wasted a considerable amount of time before resolving this issue.

“If the server was started with –bind-address=127.0.0.1, it will listen for TCP/IP connections only locally on the loopback interface and will not accept remote connections.”

source: MySQL documentation

I hope this saves somebody some time.

Troubleshooting remote connections to MySQL on Linux