Monday, October 17, 2016

Working with Cross Origin Scripting to POST data



Cross Domain Web Services


Creating a Web service that can be used by a JavaScript enabled Web page is not as easy as it should be due to security concerns. After reading a lot about JSONP, CORS, and pre-flight transactions. I was finally able to get a solution that works for a POST transaction. A GET transaction seemed to be a little simpler and I found more examples of that online.

This solution can be deployed to WebSphere or IBM BlueMix to a Liberty container and it should work in other environments as well.

The following Java code uses JAX-RS to create a simple REST service.


package jd;



import javax.ws.rs.Consumes;

import javax.ws.rs.OPTIONS;

import javax.ws.rs.POST;

import javax.ws.rs.Path;

import javax.ws.rs.Produces;

import javax.ws.rs.core.MediaType;

import javax.ws.rs.core.Response;





@javax.ws.rs.ApplicationPath("resources")

@Path("/service")

public class Post extends javax.ws.rs.core.Application{

    

    @POST

    @Consumes(MediaType.APPLICATION_JSON)

    @Produces(MediaType.APPLICATION_JSON)

    

    public Response echo(String data) {

    

             return Response.ok(data).header("Access-Control-Allow-Origin", "*").build();  

        

    }

    

    @OPTIONS

    public Response handleOptions(String data) {



              return Response.ok().header("Access-Control-Allow-Origin", "*")

                .header("Access-Control-Allow-Headers",

                      "Content-type,X-Custom-Header,Access-Control-Allow-Origin")

                .header("Access-Control-Allow-Methods", "GET, POST").build();

    }    

}


HTML

The following HTML code must be deployed to a Web server. This does not work to simply load it locally from the file system.

<html>
<body>

<div id="id01">Working...</div>
<script>
function createCORSRequest(method, url){
    var xhr = new XMLHttpRequest();
    if ("withCredentials" in xhr){
        xhr.open(method, url, true);
    } else if (typeof XDomainRequest != "undefined"){
        xhr = new XDomainRequest();
        xhr.open(method, url);
    } else {
        xhr = null;
    }
    return xhr;
}

var request = createCORSRequest("POST", "http://test.mybluemix.net/resources/service");

if (request){
    request.onload = function(){
        document.getElementById("id01").innerHTML = request.responseText
    };
    var data = "{\"a\":{\"b\":{\"c\":\"a\"}}}";
    request.setRequestHeader("Content-type", "application/json");
    request.send(data);
}
</script>
</body>
</html>

The AJAX Version

<!DOCTYPE html>
<html>
  <head>
    <script src="http://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
    <script>
$(document).ready(function () {
  $('#get-data').click(function () {
    var showData = $('#show-data');

    var data1 = "{\"a\":{\"b\":{\"m\":\"G\"}}}";

    
     $.ajax({
            url: "http://power-8-cost-estimator.mybluemix.net/resources/service",
            type: "POST",
             headers: {
                "Content-type":"application/json",
            },
            crossDomain: true,
            data: data1,
            dataType: "json",
         
           
            success: function (response) {
                  str = JSON.stringify(response);
                  showData.text(str)
               
            },
            error: function (xhr, status) {
                showData.text(status);
            }
        });

  
    showData.text('Loading the JSON file.');
  });
});

  </script>
    <meta charset="utf-8">
    <title>Request JSON Test</title>
  </head>
  <body>
    <a href="#" id="get-data">Get JSON data</a>
    <div id="show-data"></div>
   
  
  </body>
</html>