Retrieving Country Info from GeoNames via CORS - Exercise

Contact Us or call 1-877-932-8228
Retrieving Country Info from GeoNames via CORS - Exercise

Retrieving Country Info from GeoNames via CORS

Duration: 15 to 25 minutes.

In this exercise, you will make an Ajax call to a cross-origin site which includes appropriate response headers to enable CORS.

  1. Geonames.org offers a wide range of geographical data, returned in both XML and JSON format. Visit http://api.geonames.org/countryInfoJSON?formatted=true&lang=en&country=US&username=webucator&style=full to view the response from the resource we will access.
  2. Note that the response includes the Access-Control-Allow-Origin: * header: Country Info
  3. Note, too, the schema of the response: a field geonames contains an array (n this case with a single element) which contains fields with information about the given country: countryName, population, etc.
  4. Open XHR/Exercises/cors-geonames.html in your editor; you'll write the code here:
    • Get the value of the #countryabbr input field: this is the two-character country abbreviation - "US" for the United States, "CN" for China, "DE" for Germany, etc.
    • Use XMLHttpRequest to retrieve date from Geonames:
      • The type of this Ajax call should be get.
      • The call should go to http://api.geonames.org/countryInfoJSON?formatted=true&lang=en&country=XX&username=webucator&style=full, where "XX" is the two-character country abbreviation supplied by the user.
      • Parse the response: check if the country code was valid by checking the length of the returned response; if there was a response with valid data, then display on the page the country's name, population, and any other fields you wish. If not - that is, if JSON.parse(xmlhttp.responseText).geonames.length == 0, then display an error message.
  5. Test your solution in a browser by visiting XHR/Exercises/cors-geonames.html

Solution:

XHR/Solutions/cors-geonames.html
<!DOCTYPE HTML>
<html>
<head>
<meta charset="UTF-8">
<title>CORS - Geonames</title>
<style>
	#responseContent {
		width:66%;
		padding:1% 2%;
		background-color:#ccc;
		margin-top:20px;
	}
	h2 {
		margin:0;
		padding:0;
	}
</style>
<script>
	window.onload = function() {
		var btn = document.getElementById('btn');
		var responseContent = document.getElementById('responseContent');

		btn.addEventListener('click', function(e) {
			responseContent.innerHTML = '<h2>Response Content</h2>';
			var country = document.getElementById('countryabbr').value;

			var xmlhttp = new XMLHttpRequest();

			xmlhttp.open("GET", "http://api.geonames.org/countryInfoJSON?formatted=true&lang=en&country=" + country + "&username=webucator&style=full", true);
			xmlhttp.onreadystatechange = function() {
				if (xmlhttp.readyState == 4) {
					if (xmlhttp.status == 200) {
						var jsonResponse = JSON.parse(xmlhttp.responseText);
						if (jsonResponse.geonames.length > 0) {
							responseContent.innerHTML += '<p>';
							responseContent.innerHTML += 'Name: ' + jsonResponse.geonames[0].countryName + '<br>';
							responseContent.innerHTML += 'Currency Code: ' + jsonResponse.geonames[0].currencyCode + '<br>';
							responseContent.innerHTML += 'Capital City: ' + jsonResponse.geonames[0].capital + '<br>';
							responseContent.innerHTML += 'Population: ' + jsonResponse.geonames[0].population + '<br>';
							responseContent.innerHTML += '</p>';
						} else {
							responseContent.innerHTML += '<p><em>Country not found</em></p>';
						}
					} else {
						alert("failed!");
					}
				}
			}
			xmlhttp.send(null);
		});
	};
</script>
</head>
<body>
	<input type="text" id="countryabbr" placeholder="US">
	<button id="btn">Fetch Country Info</button>
	<br>
	<div id="responseContent"></div>
</body>
</html>

Code Explanation

Our Ajax calls goes out to

http://api.geonames.org/countryInfoJSON?formatted=true&lang=en&country='+country+'&username=webucator&style=full'

where country is the user-entered value from the text field.

We check that the country code we send along in our Ajax call results in a valid response; if so, then we append to the #responseContent div some information about the country. If the response is empty, then we display "Country not found".

Next