Wednesday, May 16, 2012

Places API and Jackson JSON

This is the first in the series of posts I plan to write on my application FunDo, which was introduced in my last post. The backbone of the application is the Google Places API. Though I have had extensive experience working with XML, the API recommended using JSON. I thus started a search for a Java library that would help me easily convert the API JSON response to Java objects. Jackson JSON was where my search ended.

So to convert the Places API JSON response to Java Beans aka Value Objects (VO), you just have to follow these simple steps -
  1. Create a VO corresponding to the top level element in the JSON response, wrapping the element's children. 
  2. Each child element should be represented by Java reference variable within the parent VO with a name matching the element name in JSON. Depending on the JSON being processed, the child elements could either be simple or user defined types.
    For our example, we would create a parent VO called PlaceServiceReponseVO. The VO class name can be arbitarily selected. Needless to say, this being a Java bean, should have the getters and setters for all the member variables to be mapped.
  3. Instantiate the ObjectMapper class from Jackson API.
  4. Invoke the mapper.readValue(connection.getInputStream(), PlaceServiceResponseVO.class) and assign the returned value to a PlaceServiceReponseVO reference. Here the 'mapper' is the instance from step 3 and 'connection' is a javax.net.ssl.HttpsURLConnection object pointing to the Places API request URL.
  5. Add @JsonIgnoreProperties(ignoreUnknown = true) Jackson annotation to VO classes where you do not want to have all the fields from JSON mapped.
The following sample class has all the code you would need to invoke the Places API and map the response to Java objects -

import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;

import javax.net.ssl.HttpsURLConnection;

import com.fasterxml.jackson.databind.ObjectMapper;


public class PlacesAPISampleInvoker {
 
 /**
  * Places API URL request. Please replace the API_ACCESS_KEY with the your specific key from the Google API Console.
  */
 private static final String PLACES_API_SEARCH_REQUEST_URL = "https://maps.googleapis.com/maps/api/place/search/json?" +
   "sensor=false&location=19.03304880,73.02966250&radius=10000&types=bar&key=API_ACCESS_KEY";
 
 /**
  * @param args
  */
 public static void main(String[] args) {
  try {
   URL url = new URL(PLACES_API_SEARCH_REQUEST_URL);
   HttpsURLConnection connection = (HttpsURLConnection) url.openConnection();
   ObjectMapper mapper = new ObjectMapper();
   PlaceSearchResponseVO searchResponseVO = mapper.readValue(connection.getInputStream(), PlaceSearchResponseVO.class);
   System.out.println(searchResponseVO.getStatus());
  } catch (MalformedURLException e) {
   e.printStackTrace();
  } catch (IOException e) {
   e.printStackTrace();
  } 
 }
}

For more on the VO definitions and to run this class, download the full eclipse project Java project.

Saturday, May 12, 2012

FUN things to DO - FunDo

So I am back after a long hiatus - time when I was so busy and stressed at work that I did not have the energy and inclination to write about programming when not working. But, finally, I am about to move out of this project and looking forward to a fresh beginning at a new place.

With work being less hectic in the past month and an interesting internal contest being launched my company, I had the opportunity to put on my thinking cap and go back to a framework I fell in love right at the beginning of my IT career - GWT. The result is an interesting little web application I have called FunDo.

As part of the contest, I was supposed to use OpenShift, Red Hat's PaaS service on the cloud which is where the application is currently hosted. The app is basically a mashup using the Google Places, Autocomplete and Geocoding APIs along with Google Maps v3.

The first version of the application code in the form of an Eclipse Helios project can be downloaded from here. Please note that this version of the project was called 'vacspothunter'. GWT v2.4 would be needed along with the GWT Plugin for Eclipse for compiling the project.

Keep watching this space for more posts detailing the main aspects of the design.

Saturday, October 30, 2010

Different behavior of mqsicreatebar in MB v7

Though am essentially from a Java background, my last project was for integrating distinct applications and hence, involved the usage of IBM's Websphere MQ and Message Broker. And, this forms the base for the following post.

'mqsicreatebar' command that ships with the Message Broker Toolkit, though not widely used, is indispensible when automating the building of Broker Archives (BARs). With the recent release of V7 of the broker, I was involved in the process of migrating all our build scripts to use the latest version of the command. Not all our BARs were building successfully when the V6 scripts were used without any modifications. The reasons turned out to be following -

1. All the projects referenced from the message flows, message sets and message maps in the projects being added to the BAR need to be present in the workspace being used by the command. For example, if flows 'a' and 'b' are present in the same project 'A' and the BAR being built needs to have only flow 'a', even a project 'B' that is referred only from the message flow 'b' should be present in the workspace. It should also be passed in the values specified for the attribute 'p' required by the mqsicreatebar command. This unreferenced project was never needed in the workspace in V6.

2. There should be no error at all in the workspace on which the command is ran. Though this requirement is valid if the error is in the files being directly needed in the BAR (for e.g. in the message flows or maps), it also applies to files like the WSDL being used for creating the message sets. Though you might argue why such a thing would ever happen as the message set needs to be created from an "error-free" WSDL, I ran into a case where the WSDL inside the message set project was accidentally modified in the code repository after the message set was created. BAR building using V6 never failed even with such an error in the WSDL!

Sunday, August 23, 2009

Listen to file changes

Ever wanted your program to register changes happening to a file without writing much code? Apache VFS is here to help you with that!

public class SampleFileListener {

 
 public static void main(String[] args) {
  try {
   
   // FileSystemManager manages the file system
   FileSystemManager fsm = VFS.getManager();
   // FileSystemManager instance is used to get a FileObject instance
   // for the file to which you wish to listen. Here, the changes on 
   // the file temp.txt directly under D: would be registered.
   FileObject fileObject = fsm.resolveFile("D:\\temp.txt");
   
   // DefaultFileMonitor is the object which would monitor the file. 
   // The javadoc says that the class is a Thread based polling system 
   // monitor with 1 second delay. This means when the start method on
   // an instance of DefaultFileMonitor is invoked, a new Thread is 
   // started in the background which checks the file for changes after
   // every second. An instance of an anonymous inner class extending the
   // FileListener is passed to the constructor of DefaultFileMonitor. Its
   // the methods of this class that gets triggered every time a change
   // is detected by the file monitor.
   DefaultFileMonitor dfm = new DefaultFileMonitor(new FileListener() {
    
    // Method invoked when the file is changed and saved.
    public void fileChanged(FileChangeEvent arg0) throws Exception {
     System.out.println("File changed");
    }

    public void fileCreated(FileChangeEvent arg0) throws Exception {
     System.out.println("File created");
    }

    public void fileDeleted(FileChangeEvent arg0) throws Exception {
     System.out.println("File deleted");
    }
    
   });
   
   // Add the file object to the monitor and start the process of listening
   // for changes.
   dfm.addFile(fileObject);
   dfm.start();
   
   // Setup the main thread to run infinitely for live monitoring of changes 
   // on the file.
   while(true) {}
   
  } catch (FileSystemException e) {
   e.printStackTrace();
  }
 }
}


The above program is all that you need for registering changes on a file in your file system. No need for writing your own custom thread or file monitors. For the above class to compile and run successfully, you would need to add the VFS jar to the CLASSPATH. Download it from here. You would also need to add commons-logging.jar (version 1.0.4 or later) to the CLASSPATH.

Friday, August 21, 2009

BackItUp!

This is a simple utility which people working on a lot of data everyday may find quite useful. Once when I had just started coding professionally, I had the misfortune of losing some code due to a hard drive crash. Since then, me and my team members started following the routine of backing up the days' code to the shared drive (network attached storage) as committing un-reviewed stuff to version control was not desirable. Doing this thing manually everyday was something I disliked. Besides, people (including me [:)]) used to forget it on most days. So, I thought of automating this with a simple Java project.

The BackItUp project which has a single Java file DataBacker.java can be downloaded here.

The program accepts two command line input arguments, namely the directory/ file to be backed up and the path of the zip file (including its name) to which the contents need to be saved to. It uses classes from the Java I/O package for the file operations. After downloading and unzipping the project, open the run-program.bat and modify the paths succeeding the class name to point to ones you require. The first path points to the directory/ file to be backed up and the second is that of the zip file ending with its name. If the file path contains spaces, remember to surround it with quotes as Java reads a space as an argument separator. A pre-requisite for the program to run successfully is that JDK or JRE's bin should be added to the Windows PATH variable.

To automate the process of running the program when required, create a Windows scheduled task and associate it with the run-program.bat file. Creation of scheduled task is described in detail here.