Get the Friends of my friend using the Graph API

2019-01-18 15:30发布

I am trying to do a very basic thing with the new Graph API.

I already know how to get my friends: "https://graph.facebook.com/me/friends?access_token=4333ed34d..."

But if I have a friend who's ID is 123456, then I want to get his friends : "https://graph.facebook.com/123456/friends?access_token=4333ed34d..."

But I get an exception:

"The remote server returned an error: (500) Internal Server Error."

Why can't I do that? It's a very trivial task to ask from the API.

4条回答
手持菜刀,她持情操
2楼-- · 2019-01-18 16:05

you can actualy steal the information from public facebook. It's not pretty, takes a couple seconds, but works.

I have a JS code that runs from console and makes AJAX request - the same facebooks makes when requesting more friends in the regular facebook UI when you scroll down (http://www.facebook.com/profile.php?sk=friends). Then I parse the result. So far it works flawlessly. I just ask for more friends and when I don't get a match, I know I have them all.

I don't want to share the whole code, but this is the essential part:

// Recursively load person friends 
function getMoreFriends(job, uid, fb_dtsg, post_form_id, offset, callback, finished ){
    var url = "http://www.facebook.com/ajax/browser/list/friends/all/?uid="+uid+"&offset="+offset+"&dual=1&__a=1&fb_dtsg="+fb_dtsg+"&lsd=&post_form_id="+post_form_id+"&post_form_id_source=AsyncRequest";  
    var request = { type: 'POST', url: url, data: { __a: 1, dual: 1, offset: offset, uid: uid }, dataType: "text", complete: function(data){
    var response = data.responseText.match(/HTML.*$/)[0];
        response = response.replace(/u003c/gi,"<");
        response = response.replace(/\\u([a-f0-9]{4})/gm, "&#x$1;").replace(/\\\//g,"/").replace(/\\/g,'');
        response = response.match(/^.*<\/div><\/div><\/div>/);
        if(response != null){
            response = response[0].replace("HTML(","");
            var people = [];
        $jq(response).find(".UIImageBlock").each( function(){
            var newPerson = new Person( $jq(this).find('.UIImageBlock_Content a').text(), $jq(this).find('a').first().attr('href'), $jq(this).find('img').attr('src'), jQuery.parseJSON( $jq(this).find('a').last().attr('data-gt') ).engagement.eng_tid );
            people.push( newPerson );
            });
            callback(people);
            getMoreFriends(job, uid, fb_dtsg, post_form_id, offset+60, callback, finished);
        }
    } };
    job.addToQueue( request );
    if(job.state != "processing"){
        if (typeof finished != "function" ){ finished = function(){}; }
        job.startProcessing({ finished: function(){ finished(); } } );
    }
}

You can get the neccesary variables from a currently logged in user like this:

function loadFriends(person, onInit, store, callback){
    info("loading friends of "+person.name+" initiated");
    //addStatus("loading friends of "+person.name+" initiated");

    if (typeof onInit == "function" ){
        onInit();
    }

    if(person.id == -1){
        error("Person "+person.name+" doesn't have an id.!");
        addStatus("Person "+person.name+" doesn't have an id.!","error");
        return false;
    }
    else {
        // Load friends 
        var fb_dtsg = $jq('input[name="fb_dtsg"]').eq(0).val();
        var post_form_id = $jq('#post_form_id').val();
        var loadFriendsJob = ajaxManager.addJob({limit: 1});
        getMoreFriends(loadFriendsJob,person.id, fb_dtsg, post_form_id, 0,     function(people){ // callback on each iteration
            d( "Loaded "+people.length+" friends of " + person.name );
            store(people);
        },function(){ // callback on finish
            info("loading friends of "+person.name+" finished");
            //addStatus("loading friends of "+person.name+" finished");
            if (typeof callback == "function" ){ callback(); }
        });
    }

}

I understand this is probably useless for your case since this is JS. Anyway, someone might find this usefull.

P.S.: $jq = jQuery. P.P.S.: those job objects take care of sequential ajax requests. I found out I need them since my FF didn't feel like making 2000+ AJAX request at the same time :-D

查看更多
闹够了就滚
3楼-- · 2019-01-18 16:08

If I try to get friends of a random user I get HTTP 500 but it contains this response:

{
   "error": {
      "type": "Exception",
      "message": "(#604) Can't lookup all friends of <UID>. Can only lookup for the logged in user (<MY_UID>), or friends of the logged in user with the appropriate permission"
   }
}

which is pretty self-explanatory.

If I try to get friends of my friend who allows viewing his other friends it works fine. If my friend chose to not allow viewing his other friends I get the same error.

查看更多
forever°为你锁心
4楼-- · 2019-01-18 16:27

I got friends of friends(limited). I had same problem. Though it is very late for answering question, it will help somebody. That's why answering this question.

We can get friends of friends those are app users. It needs following requirements:

  1. Your friend needs to be using application(accepted permissions for app).
  2. Permission from application read_stream, publish_stream, publish_checkins.

$fb_id= user id whose friends of friends required.

Try this fql query.

$query="SELECT uid, name, work_history FROM user WHERE uid IN (SELECT uid2 FROM friend WHERE uid1 IN (SELECT uid FROM user WHERE uid IN (SELECT uid2 FROM friend WHERE uid1 = $fb_id ) and is_app_user=1) )";

查看更多
霸刀☆藐视天下
5楼-- · 2019-01-18 16:30

You just can't do that.

If you require the appropriate extended permission when the users authorize your app, you can access some data of the currently logged user's friends, but that's all you get (http://developers.facebook.com/docs/authentication/permissions see: friends_xxxx permissions), but not his/her friends.

查看更多
登录 后发表回答