Some geo love

Mashing up single sign on and the CWD wasn’t enough. I’ve added to our Nucleus ‘location’ service some new geo APIs that will allow us to make location aware websites and applications.

There is both a server side version which can be called via cURL/file_get_contents/etc:

http://nucleus.online.lincoln.ac.uk/locations/geo/format/xml (your IP address)
http://nucleus.online.lincoln.ac.uk/locations/geo/format/xml?ip=86.6.170.144 (my current IP address)

(if you want JSON/JSONP/CSV then replace the format/xml with format/your choice)

and a JavaScript client side version:

http://nucleus.online.lincoln.ac.uk/locations/geojs (your IP address)
http://nucleus.online.lincoln.ac.uk/locations/geojs?ip=86.6.170.144 (my current IP address)

Both services return the following information:

  • which campus network the IP address is associated with (or ‘non’ if they aren’t using a campus network)
  • which campus they’re on (e.g. Brayford or Hull or ‘non’ if they aren’t on a campus)
  • the building (we can only do this currently for wired networks and some wireless networks)
  • the postcode of the building (where possible)
  • latitude and longitude (if the IP address isn’t on a University network then it uses the Maxmind GeoCity database)
  • the closest library to the library (GCW, Holbeach, Hull, or if they’re on a campus network, the Theology Reading Room)

So how does it work?

I’ve collected a huge list of IP ranges for the wired and wireless networks at the University and then I use the this function to loop over these ranges until it returns TRUE that an IP is in a range, or that it isn’t (i.e. they aren’t on a University network).

The ranges look like this:

$zones = array(
    'HBW'    => array(
        'network'=>'Holbeach wireless',
        'campus'=>'Holbeach',
        'postcode'=>'PE12 7PT',
        'building'=>'Minerva House',
        'latitude'=>'52.810004',
        'longitude'=>'0.01696'
    ),

If it results that an IP address is from a network then I’ve a simple multidimensional array for each network that contains the meta:

$zones = array(
'HBW'	=> array(
	'network'=>'Holbeach wireless',
	'campus'=>'Holbeach',
	'postcode'=>'PE12 7PT',
	'building'=>'Minerva House',
	'latitude'=>'52.810004',
	'longitude'=>'0.01696'
),
...

Finally it outputs in the required format (i.e. json/xml (server) or JavaScript (client)).

When mashed up with another Nucleus location API we could easily make a FourSquare like app that finds buildings around a location:

http://nucleus.online.lincoln.ac.uk/locations/buildings_near/format/xml?lat=53.228482&long=-0.547847&distance=0.5&limit=10

I’ll make sure that all of these location APIs are properly documented soon so people can go have fun with them. Also, none of these location APIs require any sort of authentication (though we are rate limiting so don’t try and kill our servers please!).