How can I find a user’s country using HTML5 geolocation?
Asked Answered
A

7

34

I'm familiar with HTML5 geolocation for returning rough coordinates of the user’s location.

However, how can I return the name of the country that their coordinates are in?

Astatine answered 19/7, 2011 at 13:23 Comment(4)
Duplicate question ? #6159574Erupt
See perhaps the answers to #4498228.Delly
Geolocation is not part of HTML5: isgeolocationpartofhtml5.comKomsomol
Well this is awkward w3schools.com/html/html5_geolocation.aspRuff
L
31
    var geocoder = new google.maps.Geocoder();
    geocoder.geocode({'latLng': <YOURLATLNGRESPONSEFROMGEO>}, function(results, status) {
            if (status == google.maps.GeocoderStatus.OK) {
                if (results[0]) {
                    var loc = getCountry(results);
                }
            }
        });

    function getCountry(results)
    {
        for (var i = 0; i < results[0].address_components.length; i++)
        {
        var shortname = results[0].address_components[i].short_name;
        var longname = results[0].address_components[i].long_name;
        var type = results[0].address_components[i].types;
        if (type.indexOf("country") != -1)
        {
            if (!isNullOrWhitespace(shortname))
            {
                return shortname;
            }
            else
            {
                return longname;
            }
        }
    }

}

function isNullOrWhitespace(text) {
    if (text == null) {
        return true;
    }
    return text.replace(/\s/gi, '').length < 1;
}

This is what I use :)

Lockjaw answered 19/7, 2011 at 13:29 Comment(4)
This is almostt perfect, but google returns 'United Kingdom' rather than 'England' or 'Scotland' etc.. Ideally it needs to return 'England' etc as the purpose of the app I'm building is to identify between them two! :/Astatine
Look through the different types and see if you can grab what you want. code.google.com/apis/maps/documentation/geocoding/#TypesLockjaw
Just to be super picky here but it is safer to use '===' instead of '==' for comparing null values.Issie
Just a heads up: "Geocoding Service: You must use an API key to authenticate each request to Google Maps Platform APIs. For additional information, please refer to g.co/dev/maps-no-account"Bung
P
37

If you just want the country, here's a much simpler approach using ws.geonames.org rather than Google:

if (navigator.geolocation) {
    navigator.geolocation.getCurrentPosition(function(position) {
        $.getJSON('http://ws.geonames.org/countryCode', {
            lat: position.coords.latitude,
            lng: position.coords.longitude,
            type: 'JSON'
        }, function(result) {
            alert(result.countryName);
        });
    });
}​

Normally I would say that using a Google service would mean greater reliability, but with so many Google services being retired lately it's probably a good idea to look at some other solutions.


By the way, I did some experiments using all the free geocoding services I could find. It returns the country and the name of the service responsible as soon as one of them finds an acceptable result.

Feel free to play with it via JSFiddle: Deferred look up country code via multiple geolocation webapis

Pidgin answered 2/8, 2012 at 11:16 Comment(6)
I really like the simplicity of this answer ... and its the more open answer ;)Ungula
The best answer for countries that block Google :)Anet
Error : lease add a username to each call in order for geonames to be able to identify the calling application and count the creditsPolypus
@zloctb: Yes it seems geonames has changed its webservice to now require a registered username: "The parameter 'username' needs to be passed with each request. The username for your application can be registered here. You will then receive an email with a confirmation link and after you have confirmed the email you can enable your account for the webservice on your account page"Pidgin
Great solution. Just need to change http:// to https:// in each URL. ;)Salliesallow
ws.geonames.org now appears to be deadNomism
L
31
    var geocoder = new google.maps.Geocoder();
    geocoder.geocode({'latLng': <YOURLATLNGRESPONSEFROMGEO>}, function(results, status) {
            if (status == google.maps.GeocoderStatus.OK) {
                if (results[0]) {
                    var loc = getCountry(results);
                }
            }
        });

    function getCountry(results)
    {
        for (var i = 0; i < results[0].address_components.length; i++)
        {
        var shortname = results[0].address_components[i].short_name;
        var longname = results[0].address_components[i].long_name;
        var type = results[0].address_components[i].types;
        if (type.indexOf("country") != -1)
        {
            if (!isNullOrWhitespace(shortname))
            {
                return shortname;
            }
            else
            {
                return longname;
            }
        }
    }

}

function isNullOrWhitespace(text) {
    if (text == null) {
        return true;
    }
    return text.replace(/\s/gi, '').length < 1;
}

This is what I use :)

Lockjaw answered 19/7, 2011 at 13:29 Comment(4)
This is almostt perfect, but google returns 'United Kingdom' rather than 'England' or 'Scotland' etc.. Ideally it needs to return 'England' etc as the purpose of the app I'm building is to identify between them two! :/Astatine
Look through the different types and see if you can grab what you want. code.google.com/apis/maps/documentation/geocoding/#TypesLockjaw
Just to be super picky here but it is safer to use '===' instead of '==' for comparing null values.Issie
Just a heads up: "Geocoding Service: You must use an API key to authenticate each request to Google Maps Platform APIs. For additional information, please refer to g.co/dev/maps-no-account"Bung
T
2

If you have problem getting geolocation to work like I had in Chrome, then I can recommend this alternative way (example with jQuery):

$.getJSON("https://freegeoip.net/json/", function(data) {
    const countryCode = data.country_code;
    const countryName = data.country_name;
    const ip = data.ip;
    const timezone = data.time_zone;
    const latitude = data.latitude;
    const longitude = data.longitude;

    alert("Country Code: " + countryCode);
    alert("Country Name: " + countryName);
    alert("IP: " + ip); 
    alert("Time Zone: " + timezone);
    alert("Latitude: " + latitude);
    alert("Longitude: " + longitude);   
});
Turbine answered 24/3, 2017 at 6:33 Comment(3)
neat solution with very few lines! also it doesn't require user interaction to find out his location.Loutitia
Note as of 2020 this does not work. Service is now premium (though there is a limited free account).Lewan
It redirects to ipstack.com, that has pricing.Teacup
S
1

pay attention you need set 'username' property for using this api,otherwise you'll get error.

setTimeout(function() {
                if (navigator.geolocation) {
                    navigator.geolocation.getCurrentPosition(function(position) {
                        $.getJSON('http://api.geonames.org/countryCode', {
                            lat : position.coords.latitude,
                            lng : position.coords.longitude,
                            type : 'JSON',
                            username : 'demo'
                        }, function(result) {
                            alert(result.countryName);
                        });
                    });
                }

            }, 1000);
Spoilage answered 5/7, 2015 at 7:31 Comment(0)
D
0

Similar answer as from @hippietrail but with another service without registration.

if ( navigator.geolocation ) {
  navigator.geolocation.getCurrentPosition(function(position) {

  $.ajax('http://www.datasciencetoolkit.org/coordinates2politics/'
    + position.coords.latitude + ','
    + position.coords.longitude, {dataType: 'jsonp'})
  .done(function(data, textStatus, jqXHR) {
    if ( textStatus === 'success' ) {
      var country = data[0].politics[0].name
      alert(country)
    }
  })
}
Dafodil answered 27/6, 2015 at 18:36 Comment(0)
C
0

Without using geoloc or IP lookup APIs (are free for dev use only)

Using Intl.DateTimeFormat().resolvedOptions().timeZone and file extracted from moment-timezone

Link to demo (user region code), you can download a file.

Cline answered 18/8, 2023 at 7:31 Comment(0)
O
-1

You will need a Reverse Geocoder service.

Olfactory answered 19/7, 2011 at 13:24 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.