Facebook Graph API - how to get user country?

I'm developing a Facebook application using their Graph API. I have previously developed an app using the deprecated REST API.

I've come across a problem in that I can't retrieve the user's country, only their 'location' - which is just the city and state / region in a combined format (such as 'Houston, Texas').

How is it possible to retrieve the user's country using the Graph API? If this isn't directly possible, what workarounds might there be to achieve this?

Answers


https://api.facebook.com/method/fql.query?format=json&query=SELECT%20current_location%20FROM%20user%20WHERE%20uid=4&access_token=<ACCESS_TOKEN>

[
  {
    "current_location": {
      "city": "Palo Alto",
      "state": "California",
      "country": "United States",
      "zip": "",
      "latitude": 37.4441,
      "longitude": -122.163,
      "id": 104022926303756,
      "name": "Palo Alto, California"
    }
  }
]

FQL Documentation


One solution I have found, which is merely a workaround, is to use the GeoNames API - http://www.geonames.org/export/web-services.html

Using something like:

http://api.geonames.org/search?q=houston%2C%20texas&featureClass=P&username=myusername

Returns results in an xml object, with the country as part of the data.

I'm not particularly happy with this as a solution however, as it adds an unnecessary layer of complications on to my application - plus requests to this free services are limited to 2000 per hour and 30,000 per day.


Use the php sdk:

require 'facebook.php';

$facebook = new Facebook(array( 'appId' => 'APPID', 'secret' => 'APPSECRET', 'cookie' => true, ));

Then ask for a signed request:

  $signed_request = $facebook->getSignedRequest();
  $country = $signed_request["user"]["country"];

Now $country has a string such as "us" for United States and "uk" for United Kingdom etc.


That is a good question.

The problem is that any application run under facebook has to go through facebook servers - fb proxy and because of this the IP you get is not that of visitors but facebook's servers' instead which is of no use.

I have not seen any solution for this yet except for getting user's country from his profile which again is only possible if user had made it public or authorized the permission for it.

Here is useful link you might want to check out there too:


You should try like this:

/* make the API call */
[[FBRequest requestForMe] startWithCompletionHandler:^(FBRequestConnection *connection,
                                                           NSDictionary<FBGraphUser> *user,
                                                           NSError *error)
    {
        if (!error)
        {
            self.countryName    = [[[user objectForKey:@"location"] valueForKey:@"name"] componentsSeparatedByString:@", "][1];
            self.countryCode    = [self getCountryCodeForCountry:STUser.countryName];
        }
}];

-(NSString *)getCountryCodeForCountry:(NSString*)country
{
    NSMutableArray *countries = [self getCountries];
    NSArray *countryCodes = [NSLocale ISOCountryCodes];

    NSDictionary *codeForCountryDictionary = [[NSDictionary alloc] initWithObjects:countryCodes forKeys:countries];

    return [codeForCountryDictionary objectForKey:country];
}

+(NSMutableArray *)getCountries
{
    NSMutableArray *countries = [NSMutableArray array];

    NSArray *countryCodes = [NSLocale ISOCountryCodes];
    countries = [NSMutableArray arrayWithCapacity:[countryCodes count]];

    for (NSString *countryCode in countryCodes)
    {
        NSString *identifier = [NSLocale localeIdentifierFromComponents:[NSDictionary dictionaryWithObject: countryCode forKey: NSLocaleCountryCode]];
        NSString *country = [[NSLocale currentLocale] displayNameForKey: NSLocaleIdentifier value: identifier];
        [countries addObject: country];
    }

    return countries;
}

use the official Facebook Graph API /me?fields=hometown it will return you e.g. "Prague, Czech Republic"

I believe you can explode the string by needle ',' and the last element should be the country


for iframe apps, then ip is not hidden by FB servers, meaning you can do ip address lookup

http://phpweby.com/software/ip2country

the script was a bit buggy for me but did the job.


According to Facebook's documentation, you can get the 2-letter ISO 3166-1 country code from the user's locale.

Facebook locales follow ISO language and country codes respectively, concatenated by an underscore. The basic format is ''ll_CC'', where ''ll'' is a two-letter language code, and ''CC'' is a two-letter country code. For instance, 'en_US' represents US English.

Example FQL:

SELECT locale FROM user WHERE uid = me()

Response:

{
  "data": [
    {
      "locale": "en_US"
    }
  ]
}

You can see the lifetime number of followers (by likes to your FB page) by country using an FQL query. Set up a JSON query using the tokenized session value, and send an FQL query through via PHP with the object_ID of the page you are targeting and period of lifetime. select metric, and set the metric to page_fans_country - and dump the data into a CSV file. You should get back a list of total lifetime followers (by likes) by country code (multiple rows). Setup a pivot table to get an aggregated index across multiple pages of data, and rank by country code. Here's example of the FQL query:

SELECT metric, value FROM insights WHERE object_id=[your page ID goes here] AND metric='page_fans_country' AND end_time=end_time_date('2013-04-28') AND period=period('lifetime')


Answer posted by Valerchik is the right one indeed, but in case someone would look for PHP solution, then I ended up with something like this:

$token = Yii::app()->facebook->getAccessToken();
$fqlRequest = 'https://api.facebook.com/method/fql.query?query=' .
              'SELECT%20' . $fqlAttributeName . '%20FROM%20user%20WHERE%20' .
                    'uid=' . $fbUserId . '&access_token=' . $token;
$ret = file_get_contents($fqlRequest);

if (!empty($ret)) {
    ...

List of all user's attributes can be found here: https://developers.facebook.com/docs/reference/fql/user/

I hope it will help someone :)


Need Your Help