First thing first. You will need a key to run this application so sign up for Google Maps API and get your key https://developers.google.com/maps/documentation/geocoding/intro
You can download the full source code from GoogleGeocode.GoogleMapsAPI Source
Setup your app.config file
In AppSettings section add
<add key="IsGoogleMapsAPIPaid" value="0"/> <add key="URL" value="https://maps.googleapis.com/maps/api/geocode/json?address="/> <add key="APIClient" value="yourclientId"/> <add key="APIKey" value="yourcryptokey"/>In your code you will get a list of addresses you want to validate from your database. In this demo I have put some addresses in a list.
ListlstAddresses = new List () { "UNIT 7, 7 ERINDALE ROAD BALCATTA WA 6021", "226 MCINTYRE ROAD SUNSHINE VIC 3020", "UNIT 1 & 2, 12 PREMIER COURT WARANA QLD 4575", "PETERSHAM NSW 2049", "UNIT 7, 7 ERINDALE ROAD BALCATTA WA 6021", "226 MCINTYRE ROAD SUNSHINE VIC 3020", "UNIT 1 & 2, 12 PREMIER COURT WARANA QLD 4575", "WENTWORTHVILLE NSW 2049", "UNIT 7, 7 ERINDALE ROAD BALCATTA WA 6021", "MCINTYRE ROAD SUNSHINE VIC 3020", "UNIT 1 & 2, 12 PREMIER COURT WARANA QLD 4575", "PETERSHAM NSW 2049" };
There is a limit of 10 API calls per second when you are calling Google Maps APIs so I am passing 10 addresses to Parallel.ForEach loop and calling Google Geocode API. This will parallalize API calls. Also there is a check if all API calls finish within one second wait for 1 second before calling next batch to avoid getting QUERY_OVER_LIMIT error.
Parallel.ForEach(selected, new ParallelOptions() { MaxDegreeOfParallelism = 10 }, sel =>
{
try
{
string address = sel.ToString();
Console.WriteLine("Address = " + address);
GeoDetail objResult = GeoDetail.GetGeoDetails(key, address);
lock (lockMe)
{
lstResult.Add(objResult);
}
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
});
GetGeoDetails() method calls Google Maps API using HttpRequest and Get HttpResponse object back which then being converted to JSON object using JSON.Net library.
public static GeoDetail GetGeoDetails(string APIKey, string address)
{
string uri = ConfigurationManager.AppSettings["URL"];
GeoDetail objResult = new GeoDetail() { Address = address, Latitude = -1, Longitude = -1, AddressType = "", Error = "" };
try
{
string requestURL = "";
if (ConfigurationManager.AppSettings["IsGoogleMapsAPIPaid"].Trim() == "0")
{
requestURL = uri + address + "&key=" + APIKey; // No need to sign URL and there is no APIClient ID to pass.
}
else
{
requestURL = GoogleSignedUrl.Sign(uri + address + "&client=" + ConfigurationManager.AppSettings["APIClient"].Trim(), APIKey);
}
HttpWebRequest request = WebRequest.Create(requestURL) as HttpWebRequest;
request.Accept = "application/json";
// Get response
using (HttpWebResponse response = request.GetResponse() as HttpWebResponse)
{
if (response.StatusCode == HttpStatusCode.OK)
{
StreamReader readert = new StreamReader(response.GetResponseStream());
string x = readert.ReadToEnd();
JObject jObject = JObject.Parse(x);
//Console.WriteLine(x);
if (jObject["status"].ToString() == "OK")// successful API call
{
if (jObject["results"].Count() > 0)
{
string locationType = jObject["results"][0]["geometry"]["location_type"].ToString();
string lat = jObject["results"][0]["geometry"]["location"]["lat"].ToString().Trim();
string lng = jObject["results"][0]["geometry"]["location"]["lng"].ToString().Trim();
Console.WriteLine("Geolocation lat lng : {0} {1} Type : {2}", lat, lng, locationType);
double? latValue = null;
double? lngValue = null;
if (!string.IsNullOrWhiteSpace(lat))
{
latValue = double.Parse(lat);
}
if (!string.IsNullOrWhiteSpace(lng))
{
lngValue = double.Parse(lng);
}
objResult.Latitude = latValue;
objResult.Longitude = lngValue;
objResult.AddressType = locationType; //locationType == "ROOFTOP")//exact address match
}
else
{
Console.WriteLine("No result found");
objResult.Error = "No result found";
}
}
else
{
Console.WriteLine(jObject["status"].ToString());
objResult.Error = jObject["status"].ToString();
}
}
}
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
objResult.Error = ex.ToString();
}
return objResult;
}