Nav
You are viewing an older version of this section. Click here to navigate to the latest version.

JSON Support Reference

JSON, short for JavaScript Object Notation, is a lightweight data interchange format. It is a text-based, human-readable format for representing simple data structures and associative arrays (called objects).

Object Bindings

Mule supports binding JSON data to objects and marshaling Java objects to JSON using the Jackson Framework. Jackson uses annotations to describe how data maps to a Java object model. For example, let’s say we have an JSON file that describes a person. When we receive that JSON data, we convert it into a Person object. The JSON looks like this:


         
      
1
2
3
4
5
6
7
8
9
10
11
12
13
14
{
    "name":"John Doe",
    "dob":"01/01/1970",
    "emailAddresses":[
        {
            "type":"home",
            "address":"john.doe@gmail.com"
        },
        {
            "type":"work",
            "address":"jdoe@bigco.com"
        }
    ]
}

And we have an object Person we want to create from the JSON data. We use annotations to describe how to perform the mapping. We use the @JsonAutoDetect to say that field member names map directly to JSON field names:


         
      
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
@JsonAutoDetect
public class Person
{
    private String name;
    private String dob;
 
    private List<EmailAddress> emailAddresses;
    public String getName() { return name; }
    public void setName(String name) { this.name = name; }
    public String getDob() { return dob; }
    public void setDob(String dob) { this.dob = dob; }
    public List<EmailAddress> getEmailAddresses() { return emailAddresses; }
 
    public void setEmailAddresses(List<EmailAddress> emailAddresses) { this.emailAddresses = emailAddresses; }
}

The EmailAddress object that is used in the emailAddresses is just another JavaBean with the @JsonAutoDetect annotation.

At this point Mule can figure out whether to perform a JSON transforms based on the parameters of the method being called. For example:


         
      
1
2
3
4
5
6
public class PersonComponent {
    public void processPerson(@Payload Person person)
    {
    //tickle
    }
}

This example receives the contents of the people.json file above on an endpoint, Mule sees that Person.class is an annotated JSON object, we receive JSON data from the JMS queue, and perform the conversion.

Global JSON Mapper

Jackson performs mappings through the ObjectMapper. This is an object that can be configured with other configuration about how to serialise data and define mixins that add annotations to objects that you cannot change directly. It is possible to define a global ObjectMapper; a single mapper that will be used for all JSON transforms in your application. This is not required since Mule will automatically create a mapper for a transformer, but using a global mapper can be useful if you need to configure specific properties on the mapper or use mixins. To create a shared ObjectMapper, add the following to your Mule configuration file:


          
       
1
2
3
4
5
6
<json:mapper name="myMapper">
    <json:mixin mixinClass="org.mule.module.json.transformers.FruitCollectionMixin"
                        targetClass="org.mule.module.json.transformers.FruitCollection"/>
    <json:mixin mixinClass="org.mule.module.json.transformers.AppleMixin"
                        targetClass="org.mule.tck.testmodels.fruit.Apple"/>
</json:mapper>

Intercepting JSON Transforms

So far we have discussed how Mule performs automatic JSON transforms. Sometimes you may want to intercept the transform, to do this just create a transformer with a method return or parameter type of your JSON class:


          
       
1
2
3
4
5
@Transformer(sourceTypes = {InputStream.class})
public Person toPerson(String json, ObjectMapper mapper) throws JAXBException
{
    return (Person)mapper.readValue(in, Person.class);
}

The ObjectMapper instance either is created for you or the global context for your application is used. One reason for doing this is to strip out some JSON elements and create objects from a subset of the JSON received. For more information about transforms see the Using Transformers section.

JsonPath

There is no standard language currently for querying JSON data graphs in the same way XPATH can query XML documents. Mule has created a simple query syntax for working with JSON data in Java, called JsonPath.

This query syntax provides a simple way to navigate a JSON data structure. The following JSON data demonstrates how JSON Path queries can be used:


         
      
1
2
3
4
5
6
7
8
9
10
11
12
13
14
{
    "name":"John Doe",
    "dob":"01/01/1970",
    "emailAddresses":[
        {
            "type":"home",
            "address":"john.doe@gmail.com"
        },
        {
            "type":"work",
            "address":"jdoe@bigco.com"
        }
    ]
}

To select a child entry, use:


         
      
1
name

To access array data, use square braces with an index value:


         
      
1
emailAddresses[0]/type

Or where the route element is an array:


         
      
1
[0]/arrayElement

Also, multi-dimensional arrays can be accessed using:


         
      
1
filters[1]/init[1][0]

This is rare, but if a JSON property name contains a '/', the name needs to be single quoted:


         
      
1
results/'http://foo.com'/value

JsonPath in Expressions

JSON Path can be used in Mule expressions to query JSON message payloads for filtering or enrichment.

For example, to use JSON Path to perform content based routing:


          
       
1
2
3
4
5
6
7
8
9
10
11
<choice>
  <when expression="emailAddresses[0]/type = 'home'" evaluator="json">
    <append-string-transformer message="Home address is #[json:emailAddresses[0]/address]" />
  </when>
  <when expression="emailAddresses[0]/type = 'work'" evaluator="json">
    <append-string-transformer message="Work address is #[json:emailAddresses[0]/address]" />
  </when>
  <otherwise>
    <append-string-transformer message=" No email address found" />
  </otherwise>
</choice>

The expression evaluator name is 'json', the expression is any valid JSON Path expression. Note that when doing boolean expressions such as in the example above, these operators are supported:

Operator Example

=

emailAddresses0/type = 'foo' or emailAddresses0/flag = true

!=

emailAddresses0/type != null or emailAddresses0/flag != false

String comparisons need to be in single quotes, 'null' is recognised as null, and boolean comparisons are supported. If checking numeric values, just treat them as a string.

Configuration Reference

JSON Module

The JSON module contains a number of tools to help you read, transform, and write JSON.

Transformers

These are transformers specific to this transport. Note that these are added automatically to the Mule registry at start up. When doing automatic transformations these will be included when searching for the correct transformers.

Name Description

json-to-object-transformer

A transformer that will convert a JSON encoded object graph to a java object. The object type is determined by the ' returnClass ' attribute. Note that this transformers supports Arrays and Lists. For example, to convert a JSON string to an array of org.foo.Person, set the returnClass=org.foo.Person[]. The JSON engine can be configured using the jsonConfig attribute. This is an object reference to an instance of: net.sf.json.JsonConfig. This can be created as a spring bean.

json-to-xml-transformer

Converts a JSON string to an XML string

xml-to-json-transformer

Converts an XML string to a JSON string

json-xslt-transformer

Uses XSLT to transform a JSON string

object-to-json-transformer

Converts a java object to a JSON encoded object that can be consumed by other languages such as Javascript or Ruby. The JSON Object mapper can be configured using the mapper-ref attribute. This is an object reference to an instance of: org.codehaus.jackson.Mapper. This can be created as a spring bean. Usually the default mapper is sufficient. Often users will want to configure exclusions or inclusions when serializing objects. This can be done by using the Jackson annotations directly on the object (see http://fasterxml.github.io/jackson-core/javadoc/1.9/org/codehaus/jackson/annotate/package-summary.html) If it is not possible to annotate the object directly, mixins can be used to add annotations to an object using AOP. There is a good description of this method here: http://www.cowtowncoder.com/blog/archives/08-01-2009_08-31-2009.html. To configure mixins for you objects, either configure the mapper-ref attribute or register them with the transformer using the <serialization-mixin> element. The returnClass for this transformer is usually java.lang.String, byte[] can also be used. At this time the transformer does not support streaming.

Filters

Filters can be used to control which data is allowed to continue in the flow.

Name Description

is-json-filter

A filter that will determine if the current message payload is a JSON encoded message.

json-schema-validation-filter

Validate JSON against an XML schema

Mapper

The Jackson mapper to use with a JSON transformer. This isn’t required but can be used to configure mixins on the mapper.

Attributes of <mapper…​>

Name Type Required Default Description

name

string

yes

The name of the mapper that is used to make a reference to it by the transformer elements.

Child Elements of <mapper…​>

Name Cardinality Description

mixin

0..1