For one of our clients we needed to create multiple JSONP services with SOAP-backends in Datapower. JSON is supported by default in het Multi-Protocol gateway, and with JSONx, Datapower can handle it quite well. This post describes the fixes we did to extend JSONx and make it easy to create a JSONP-response in the same way you would do for a JSON-response.

For those of you who never heard of JSONP (JSON with Padding): it’s JSON wrapped in round brackets, preceded with a prefix. This makes it possible for javascript to use it as if it where a javascript function. It is used to allow a web page to request data from a server in a different domain (our datapower device).

Back to our case: the strenght of Datapower is its ability to handle XML content. Since JSON is no xml, IBM provided us with a language called JSONx. It is an XML-model that represents JSON-content. The idea is to work as long as possible with JSONx and after all mappings and validations are done the conversion to a proper JSON response can be done using the provided ‘jsonx2json.xsl’ style sheet. This stylesheet is by default available in the ‘store://’ directory on the Datapower appliance.

Since we wanted to use JSONP instead of JSON, we complemented the JSONX-language with an extra element <jsonp:callback> that will serve as a root for the normal JSONX content. The new name we used for it is JSONPx. It has one property: ‘name’. The value of this property will be used as the prefix for our JSONP-response. If ‘name’ is empty, the output will be normal JSON.
Here you can see of a sample of a JSONPx-file:

  xmlns:jsonp=”” name=”TestPrefix”>
     <json:number name=”testValue”>123</json:number>
     <json:string name=”testName”>Foo</json:string>

Just like for a JSONx-file it is possible to validate this file against an XSD-schema. Instead of the default jsonx.xsd (located under ‘store://‘in Datapower), you now can use the XSD below and we called it jsonpx.xsd;
<?xml version=”1.0″ encoding=”UTF-8″?>

  elementFormDefault=”qualified”   attributeFormDefault=”unqualified”>
<xs:import namespace=””
<xs:element name=”callback” type=”tns:callback”/>                       

   <xs:complexType name=”callback”>          
         <xs:any namespace=””

            minOccurs=”0″ maxOccurs=”unbounded”/>
      <xs:attribute name=”name” type=”xs:string”/>        

For the transformation we use the XSLT called ‘jsonpx2json.xsl’ which imports the transformations from the ‘jsonx2json.xsl’ file, but adds the transformation for the jsonp:calback element to it.
<?xml version=”1.0″ encoding=”UTF-8″?>
<xsl:stylesheet xmlns:xsl=””

<xsl:output method=”text” encoding=”utf-8″ 
  indent=”no” media-type=”application/javascript”/>          
  <xsl:import href=”store:///jsonx2json.xsl”/>
  <xsl:template match=”jsonp:callback”>
     <xsl:if test=”string-length(@name)>0″>
        <xsl:value-of select=”@name”/>

     <xsl:apply-templates select=”*”/>
     <xsl:if test=”string-length(@name)>0″>

Author: Tim