GeoCoder
Initial module work done by by Zubin Mithra (zubin71) Front-end UI done by Michael Matthews
A python module for a geolocator using
- Google API
- Yahoo API
- GeoNames
Input: service_name, location name
Output format: JSON (easy front end parsing)
Status
Basic Google/Yahoo webservice calls are in modules/s3gis.py
.
These have been tied to the front-end Location Selector in a basic form. Using the service requires entering part of an address in the Street Address text area, and optionally including a country in the hierarchical control, then clicking the "Geocoder Search," link. The geocoder service will be queried, and results will be displayed to the user in a popup. The user can select an address from the list, and the selected address will be used to populate the Street Address and zipcode in that text area, as well as the latitude and longitude lines.
At the moment this workflow means that when "Geocoder Search" link is clicked, the Google service is queried and the results are shown to the user. Sometimes the Google results will only include latitude and longitude values that are useful, and will not include a "ThoroughfareName" (street address), or a "Postal code." When no thoroughfare name is present, the user is alerted, but the latitude and longitude values are populated. When a thoroughfare name is in the results, the user is alerted to a success. When a postal code is present, that fact is included in the successful alert.
GeoNames support needs adding (there is some GeoNames functionality in S3GIS or another example in jQueryUI AutoComplete: http://jqueryui.com/demos/autocomplete/remote-jsonp.html).
Nominatim support needs adding
- http://wiki.openstreetmap.org/wiki/Cdauth%E2%80%99s_map has a good search widget for this which could be incorporated
Notes
There have been a few avenues explored for this project that have proven to be dead ends. Great pains were taken in order to get the right information out of the geocode() controller's return, which, at the moment, happens to be raw returns from Google. The problem with those efforts is that Yahoo returns a completely different data structure. These obviously have to be standardized.
It was originally thought that the 3rd party geopy python module would be useful to achieve this standardization, however there are two problems. The geopy module still returns different data structures for both Google and Yahoo. Additionally, for Google it only returns the long form of the address, and the lat/lon values, which are both trivial to parse out of the Google returns anyway (using "address" and "Point" as keys into the returned placemark). Using this module proved to be a bit of a dead end. It may be possible to use this module as a basis, however, with some slight modifications.
At present, the geocode() controller calls the s3gis GoogleGeocoder get_kml() method, which works only in strings, not with an easily modifiable data structure. It is actually possible to do an eval() on the JSON "page" variable in this method, but obviously that should be avoided in with web returns (or anything, for that matter).
API
Output most likely to be used in: OpenLayers
ToDo
A simple controller function would be nice to access the module classes
- functionality for BBOX
- provision to get results from all services
- provision to get results in multiple formats(xml, JSON, kml)
- support caching
- administration option to selection the geocoding service (Google, Yahoo, or both).
- GeoNames tie-ins in the location selector
- better hierarchical selector fill-in for selected results. That is, fill in the country and province/state. Filling in the country will require translating the two or three-letter country code to the real country name that appears int the hierarchy.
- Make the Google and Yahoo controller services merely wrappers around the more robust geocoding classes (per a comment in those controller).
Also see:
- http://nominatim.openstreetmap.org
- Review of Geocoders: http://lin-ear-th-inking.blogspot.com/2010/03/open-source-geocoders.html