30

Is there a way to find a clients location on a website using just jQuery. For example, if a user comes to my site, how could I find out what their approximate location is just using jQuery. For example, if a user came from San Francisco CA it would have some type identifier to let me know the user came from San Francisco CA. I wouldn't really need their exact location just the county or general area of origin.

edit: How is the information on http://flourishworks-webutils.appspot.com/req generated?

Thanks

user1530249
  • 1,047
  • 3
  • 19
  • 28
  • Sure, use jQuery's [`ESP` plugin](http://jquery.com/esp). Seriously though, the answer is "no", you can't do this with just client-side code. – nnnnnn Jan 05 '13 at 23:41
  • You could use GeoLocation but they would have to approve it and still it's not accurate. Beyond that there's no full-proof client-side method that I'm aware of. – Syon Jan 05 '13 at 23:42
  • If you don't want to use the geolocation API, you could get a *very* rough estimate based on their IP address, but you can't get that from just jQuery (you'll need server cooperation). – Matt Jan 05 '13 at 23:45
  • 1
    @nnnnnn, although it won't work with all browsers and OS, there *are* [standard Javascript, client-side only APIs for geolocation](http://dev.w3.org/geo/api/spec-source.html). However, they require user approval and are generally precise, so for this question, they might not be appropriate. – zneak Jan 05 '13 at 23:45
  • @zneak - True. Perhaps I should've said "...you can't _reliably_ do this with just client-side code...". Though in fact as I understand it browsers may implement the geolocation API via a network service (e.g., Chrome uses Google Location Services) so they're not strictly "client-side only" though the only code you need to include on your webpage is client-side JS... – nnnnnn Jan 06 '13 at 05:39
  • Hi, how is the information on http://flourishworks-webutils.appspot.com/req generated? Also is there a way that I can use a jQuery that pings a different server to get the location information? Suppose I have A.com which has some javascript, and it pings B.com to get the location information. – user1530249 Jan 06 '13 at 19:09
  • @nnnnnn Page NOT Found – GusDeCooL Nov 23 '13 at 16:31

7 Answers7

40

To get the client IP address & country name in jQuery:

$.getJSON("http://freegeoip.net/json/", function(data) {
    var country_code = data.country_code;
    var country = data.country_name;
    var ip = data.ip;
    var time_zone = data.time_zone;
    var latitude = data.latitude;
    var longitude = data.longitude;

    alert("Country Code: " + country_code);
    alert("Country Name: " + country);
    alert("IP: " + ip); 
    alert("Time Zone: " + time_zone);
    alert("Latitude: " + latitude);
    alert("Longitude: " + longitude);   
});

$.get("http://freegeoip.net/json/", function (response) {
    $("#ip").html("IP: " + response.ip);
    $("#address").html("Location: " + response.city + ", " + response.region_name);
    $("#details").html(JSON.stringify(response, null, 4));
}, "jsonp");
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<h3>Client side IP geolocation using <a href="http://freegeoip.net">freegeoip.net</a></h3>

<hr/>
<div id="ip"></div>
<div id="address"></div>
<hr/>Full response: <pre id="details"></pre>
Durgesh Pandey
  • 2,314
  • 4
  • 29
  • 43
24

You can use a web service that supports JSONP, such as my service http://ipinfo.io. It'll provide you with the client's IP address, hostname, geolocation information and network owner. Here's an example of it in action with jQuery:

$.get("http://ipinfo.io", function(response) {
    $("#ip").html(response.ip);
    $("#address").html(response.city + ", " + response.region);
}, "jsonp");

Here's a more detailed JSFiddle example that also prints out the full response information, so you can see all of the available details: http://jsfiddle.net/zK5FN/2/

Ben Dowling
  • 17,187
  • 8
  • 87
  • 103
  • 3
    This works, but there's a problem if you have more than 1,000 API requests per day. If you need to make more requests you will need to pay. – Marko Letic Apr 06 '14 at 10:39
13

The HTML5 Geolocation API allows you to get a user's Latitude/Longitude with some JavaScript (if the browser is compatible, and if the user allows access to his/her location).

You can then reverse-geocode the location to get an address, there are several free reverse-geocoding services other than Google's API.

However, if you don't need accurate location, and if you want all your users to take advantage of the feature (no matter the browser), and if you don't want to ask them whether they allow your site to have their location, I would recommend to use your user's IP to get the location.

Community
  • 1
  • 1
Julien
  • 9,312
  • 10
  • 63
  • 86
9

I created the ipdata.co API to provide a solid solution to this, see the below fiddle to play with. It returns numerous useful datapoints, such as - location: country (name and code), region, city etc., ecommerce - currency_code, currency symbol, timezone, mobile carrier data and it detects whether the IP address is a Proxy or a Tor user.

Ipdata has 10 global endpoints each able to handle >10,000 requests per second.

This answer uses a 'test' API Key that is very limited and only meant for testing a few calls. Signup for your own Free API Key and get up to 1500 requests daily for development.

$.get("https://api.ipdata.co?api-key=test", function (response) {
    $("#ip").html("IP: " + response.ip);
    $("#city").html(response.city + ", " + response.region);
    $("#response").html(JSON.stringify(response, null, 4));
}, "jsonp");
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<h1><a href="https://ipdata.co">ipdata.co</a> - IP geolocation API</h1>

<div id="ip"></div>
<div id="city"></div>
<pre id="response"></pre>

See the fiddle at https://jsfiddle.net/ipdata/6wtf0q4g/922/

Jonathan
  • 10,792
  • 5
  • 65
  • 85
3
**jQuery(document).ready(function($) {
    jQuery.getScript('http://www.geoplugin.net/javascript.gp', function()
{
    var country = geoplugin_countryName();
    var zone = geoplugin_region();
    var district = geoplugin_city();
    console.log("Your location is: " + country + ", " + zone + ", " + district);
});
});
<script language="JavaScript" src="http://www.geoplugin.net/javascript.gp" type="text/javascript"></script>
<script type="text/javascript">
jQuery(document).ready(function($) {
    alert("Your location is: " + geoplugin_countryName() + ", " + geoplugin_region() + ", " + geoplugin_city());
});
</script>
/*--------------------------------detailed function list not necessarily to be included---------
function geoplugin_city() { return 'Dobroyd Point';}
function geoplugin_region() { return 'New South Wales';}
function geoplugin_regionCode() { return '02';}
function geoplugin_regionName() { return 'New South Wales';}
function geoplugin_areaCode() { return '0';}
function geoplugin_dmaCode() { return '0';}
function geoplugin_countryCode() { return 'AU';}
function geoplugin_countryName() { return 'Australia';}
function geoplugin_continentCode() { return 'OC';}
function geoplugin_latitude() { return '-33.873600';}
function geoplugin_longitude() { return '151.144699';}
function geoplugin_currencyCode() { return 'AUD';}
function geoplugin_currencySymbol() { return '&amp;#36;';}
function geoplugin_currencyConverter(amt, symbol) {
    if (!amt) { return false; }
    var converted = amt * 0.9587170632;
    if (converted &lt;0) { return false; }
    if (symbol === false) { return Math.round(converted * 100)/100; }
    else { return '&amp;#36;'+(Math.round(converted * 100)/100);}
    return false;
} 
*/
//----------------example-----------------------//
<html>
 <head>
  <script language="JavaScript" src="http://www.geoplugin.net/javascript.gp" type="text/javascript"></script>
 </head>
 <body>
  <script language="Javascript">
    document.write("Welcome to our visitors from "+geoplugin_city()+", "+geoplugin_countryName());
  </script>
 </body>
</html>
1

Any client side option is not a good idea, because they are provided by the computer based on the wireless networks around. I bet that 90% of desktop users don't have this feature activated. When you get to a website that want your location, you have to click a button to agree to. If they just got on your website, then they want to know first why you need their location.

A good way is to show them a page to inform them why you need their location and that you will never use it for any other purposes than the specified one, and the location will not be saved in your database.

If there is a script that runs server side, then there is a connection from the client to the server. In this case the Server must know the IP Address. There is a trick that you can do to get the IP Address first.

Make a php script on your server, that will return only the IP Address. Since the jquery is processed locally, when a connection is made to the server, the client IP Address will be disclosed. It will take some additional time to make the required connections but soon the IP Address will be available in jQuery.

Then, you can call trough jquery an external API that will give you information for that specific IP Address. Either you buy an IP Database and install it on your websserver so you can call it, either you use another API. You can check http://www.ipgp.net/ip-address-geolocation-api/

Lucian
  • 67
  • 2
1

This is possible with https://ip-api.io geo location API. It provides country, city, zip code, coordinates, network, ASN, timezone. For example with jQuery:

$(document).ready( function() {
    $.getJSON("http://ip-api.io/api/json",
        function(data){
            console.log(data);
        }
    );
});

Also https://ip-api.io checks TOR, public proxy and spammer databases and provides this information as well.

Example response:

{
  "ip": "182.35.213.213",
  "country_code": "US",
  "country_name": "United States",
  "region_code": "CA",
  "region_name": "California",
  "city": "San Francisco",
  "zip_code": "94107",
  "time_zone": "America/Los_Angeles",
  "latitude": 32.7697,
  "longitude": -102.3933,
  "suspicious_factors": {
    "is_proxy": true,
    "is_tor_node": true,
    "is_spam": true,
    "is_suspicious": true // true if any of other fields (is_proxy, is_tor_node, is_spam) is true
  }
}
Andrey E
  • 605
  • 4
  • 8