In the project we were dealing with geolocalization of bike stations in Washington DC (data from Capital Bikeshare http://www.capitalbikeshare.com/). We had bike station names, addresses, and latitude and longitude coordinates. We wanted to add elevation.
Google Maps API Web Services
Like latitude, longitude and many other map related features, elevation can be retrieved from the Google Maps API Web Services. The introductory page of the Google Maps API Web Services (https://developers.google.com/maps/documentation/webservices/) describes the API available (https://developers.google.com/maps/documentation/api-picker), how to build a request qith a valid URL, and how to process the response. One of these services is the Google API Elevation Service (https://developers.google.com/maps/documentation/elevation/) which is the one we are going to use for this example.
The REST request for the elevation value, given latitude and longitude, has the following form:
http://maps.googleapis.com/maps/api/elevation/json\?locations=<latitude value>, <longitude value>&sensor=false
which returns a JSON formatted response.
REST Nodes for KNIME (KREST Extension)
A community Extension of KNIME, named KREST, provides REST services utility nodes (http://tech.knime.org/book/krest-rest-nodes-for-knime-trusted-extension). This extension can be installed via "File" -> "Install KNIME Extensions...", then "KNIME Community Contributions - Other" -> "REST Client". The extension contains two types of nodes: submitters and helpers. Submitters communicate with the RESTful service, while helpers convert REST resources representations into KNIEM data tables and vice versa.
Building and submitting the Request String
In our example, we start with station name, latitude and longitude coordinates read in a KNIME workflow. We then build the REST request, as indicated above, for each row using a "String Manipulation" node, with the following command:
where $lat$ and $long$ are the station's latitude and longitude coordinates.
At this point, the "GET Resource" node from the KREST extension submits the request to the REST server. However, the "GET Resource" node works on only one data row, this forces us to use a chunk loop ("Chunk Loop Start" node with "rows per chunk" = 1 to submit all requests for all input data rows to the REST server.
Intepreting the REST Response
After running the chunk loop we end up with a list of responses from the REST service in a data column named "Representation". After cleaning up possible response errors with a "Row Splitter" node , removing all data cells containing wild carded pattern "*error_message*", we need to still intepret these responses and extract the elevation value. The node to interpret REST responses is the "Read REST Representation" node.
The "Read REST Representation" node asks for the representation column in the input data table and for its format (JSON, XML, ATOM, CSV). Then it converts a REST resource representation into a data table. Even this node processes one data row only and this forces us to use a chunk loop to process all rows one by one.
We need a first "Read REST Representation" node to separate the array of results from the response status. Then we need a second "Read REST Representation" node to separate all results in the array: latitude, longitude, elavation, and resolution.
The final workflow is shown below with the chunk loop to submit the requests and the chunk loop to interpret the responses hidden inside two different metanodes.