Mountain Weather

One of the many projects that I worked on during my time at CodeClan was a group project to create a website showing all the Munros that would be sunny today, tomorrow and the day after. The idea being that most people would want to avoid bad weather on the hills and would gravitate to sunny weather if they could easily work out which Munros would have a share of the sunshine. For those unfamiliar with the term, a Munro is a mountain in Scotland that is over 3000ft. tall. I’ve attached a screenshot to give you some idea of what I’m talking about.

The implementation uses JavaScript/React/Rails and has gone through many revisions but is now hosted by Heroku and you can find it at this address: http://www.munrobagger.scot.

 

The first version of the website used the OpenWeatherMap API to collect forecasts for the Munros. The API allows forecasts to be retrieved for a specified latitude and longitude which seems ideal because each Munro has a known latitude and longitude. However, analysis revealed that there were only 26 forecasts to cover a grand total of 282 Munros and the forecasts were all for low altitude so unlikely to be of any real value.

The current version of the website uses the UK Met Office API. This API does not allow you to request a forecast by latitude and longitude. Instead, the Met Office use their own location ids to identify the forecasts for around 5000 separate locations within the UK. The first challenge is to find which Met Office locations are closest to the Munros. Thankfully the Met Office API provides a site-list which contains the lat. and long. of each location so it is possible to find which of the 5000 Met Office location relate to which Munro and therefore which location id to use to fetch the Munro’s forecast.

To get the list of sites I used this API call (API key ommitted):
http://datapoint.metoffice.gov.uk/public/data/val/wxfcs/all/json/sitelist

Once I had the list of sites, I used the the Haversine formula to calculate the distance between a mountain and a weather site. Here’s a code snippet to do that (I love the way that Javascript handles the Greek characters):

Mountain.prototype.calculateDistanceTo = function( latLng ) {

  // Haversine formula:
  // a = sin²(Δφ/2) + cos φ1 ⋅ cos φ2 ⋅ sin²(Δλ/2)
  // c = 2 ⋅ atan2( √a, √(1−a) )
  // d = R ⋅ c
  // where φ is latitude, λ is longitude, R is earth’s radius
  // note that angles need to be in radians to pass to trig functions!

  function toRadians(x) {
    return x * Math.PI / 180;
  }

  var R = 6371e3; // in metres
  var φ1 = toRadians(this._latLng.lat);
  var φ2 = toRadians(latLng.lat);
  var Δφ = toRadians(latLng.lat - this._latLng.lat);
  var Δλ = toRadians(latLng.lng - this._latLng.lng);

  var a = Math.sin(Δφ/2) * Math.sin(Δφ/2) +
    Math.cos(φ1) * Math.cos(φ2) *
    Math.sin(Δλ/2) * Math.sin(Δλ/2);
  var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));
  var d = R * c;

  return d;
}

When I ran the code I found that the nearest weather site was always right on top of the mountain so there was never any doubt about which location id to use. Exactly what was needed! No other weather service provides this level of coverage for Scottish peaks.

To give an example: Ben Nevis (the highest Munro of them all) has a latitude of 56.796849 and a longitude of -5.003525. Using the site list retrieved from the Met Office and the Haversine formula we find that the nearest location id is 350377.  A five-day forecast for Ben Nevis is retrieved using a request like this (where the API key and forecast type have been omitted): http://datapoint.metoffice.gov.uk/public/data/val/wxfcs/all/json/350377

To have access to the API free of charge, utilisation must stay within the fair use limits which are:

  • No more than 5000 data requests per day and
  • No more than 100 data requests per minute

There are 282 forecasts which are updated at most once per hour so 6768 requests would be needed to stay in sync with the Met Office. This would break the fair use limits so we need to reduce the frequency of update and we need the server, rather then the client, to get the forecasts; multiple clients using the same API key would break the fair use limit very quickly. In practice the Rails server updates the forecasts once every two hours and, while updating, requests a new forecast once a second to ensure that it only ever makes 60 requests per minute.

The Met Office API is a little tricky to use when compared with something like OpenWeatherMap but for an application like this you can’t beat it.

Leave a Reply

Your email address will not be published. Required fields are marked *