Facebook API v2.0で、フレンド数やフレンド一覧を取得する方法

8.7
2014
friend_1

Facebook公式のFAQより引用

FacebookのAPIのバージョン変更に伴い、アプリ経由の投稿権限「publish_actions(旧publish_stream)」使用の際には審査必須となった件に代表されるようにv2.0では結構クリティカルな仕様変更があります。

個人的にpublish_actions周りの次に大きな仕様変更だと思っているのが、ユーザーのフレンドリスト取得周りのAPIの縮小・廃止です。
事実上、2014/4/30以降に新たに作成されたアプリではFacebookの全フレンド一覧は取れません。また、それ以前に作られたアプリでも、2015/4/30以降は取れなくなります。
※一応取る方法あります(後述)が、おそらく限定的な用途でのみ使えます。

なお、全フレンド数は、v2.0でも取ることが出来ます。あまりこの情報は見ないので、まとめときます。

ちなみに、フレンドリスト周りの仕様変更はあまり日本では騒がれてませんでしたが、5月ごろ海外のフォーラムでは相当大騒ぎになっていたようです。

Facebook Graph Api v2.0 me/friends returns empty, or only friends who also use my app
http://stackoverflow.com/questions/23417356/facebook-graph-api-v2-0-me-friends-returns-empty-or-only-friends-who-also-use-m

それを受けてか、Facebookも各所にかなりしつこくこの件を書いています。

FAQ: API v2.0 and the New Facebook Login
https://developers.facebook.com/docs/apps/faq

Facebook Platform Upgrade Guide
https://developers.facebook.com/docs/apps/upgrading#upgrading_v2_0_user_ids

おさらい

FacebookのAPIは2015/4/30にv1.0→v2.0へとバージョン変更されます。
それに伴い、2014/4/30以降に新たに作成されたアプリについては、既に強制的にv2.0への移行が行われており、古いアプリでなければv1.0は使えない、というのが現状です。

すなわち、2014/4/30よりも以前に作成されたアプリは、1年間は問題なく稼働しますが、2014/4/30以降に作成されたアプリに関しては、各種の仕様変更に対応しないと正常に動かない、ということになります。

従来のユーザーのフレンド数やフレンドリストの取得方法

v1.0では、「/me/friends」というAPIを叩くことで、ユーザーの全ての友達一覧が取得できました。特別なパーミッションは不要(公開プロフィールのみ)です。
そして、(おそらく私がおぼえている限りでは)「フレンド数」という値を取得するAPIは無かったはずなので、友達の数についてはこの友達一覧のデータの数を数えることで取得していました。

実際に、Graph API Explorerで確認してみます。
任意のアプリケーションを選び、公開プロフィールのみでアクセストークンを発行して、「/v1.0/me/friends」を叩くと、自分の全ての友達一覧が取得できているのがわかると思います。

friend3

v2.0以降のユーザーのフレンド数やフレンドリストの取得方法

ところがこの「/me/friends」ですが、v2.0からは仕様が変わります。

まず、アプリ経由でこのAPIを利用する場合、ユーザーに対して「user_friends」という権限を承認させる必要があります。
この権限自体は、「publish_actions」のように審査が必要なわけではなく、アプリを作成すればデフォルトで付与されるscopeですが、当然ユーザーが意図的に承認しない場合もあるので、注意が必要です。

そして、最も大きな仕様変更は、「/me/friends」で取得できる友達のリストが「全ての友達一覧」ではなく、「友達のうち、同じアプリを承認している人だけ」しかとれなくなったという点です。当然、ケースによっては一人もいない場合も出てきます。

これも実際にGraph API Explorerで確認してみましょう。
任意のアプリケーションを選び、「user_friends」パーミッションを入れたアクセストークンを発行して、「/v2.0/me/friends」を叩くと、自分の全ての友達一覧は出ずに、「友達のうち、同じアプリを承認している人だけ」しか出てこないことがわかると思います。

friend4

まあ、運よく「同じアプリを承認してる友達」がいなければテストすらできませんけどね。

さて、上の画像をよく見てください。
一番下に・・・

"summary": {
  "total_count": 194
}

なんということでしょう。
友達の数が取れてます。

ということは、v2.0以降はこの値を使えば、友達の数だけは取得できますね。
てなわけで早速ためしてみましょう。

「友達の数を取得」デモページ

↑のデモページでログインしてみてもらえば、友達の数が表示されるはずです。
(※もちろん、ログイン時にアプリの承認をした場合、です。)

実際のログイン及びデータの取得周りのスクリプトは以下。
ご自由にデモページのソース見てください。

<script type="text/javascript">
window.fbAsyncInit = function() {
	FB.init({
		appId   : '*********',
		xfbml   : true,
		version : 'v2.0',
		status  : true,
		cookie  : true,
		oauth   : true
	});
};

function btnClick() {
	FB.login(function (response) {
		if (response.authResponse) {
			var body = 'Reading JS SDK documentation';

			FB.api('/me/friends', function(response) {
				if (!response || response.error) {
					var read_err_text = 'Error';
					$("#read_result").text(read_err_text);
				} else {
					var read_ok_text = response.summary.total_count;
					$("#read_result").text(read_ok_text);
				}
			});

		} else {
			alert('User is logged out');
		}
	}, {scope: 'public_profile,user_friends'});
};

</script>

v2.0以降でユーザーの全フレンドリストを取得するにはどうすればいいか

Facebookの公式ドキュメントによれば、下記の2つのケースにおいてのみ、別の方法で取得できるようです。

1.ユーザーに対して「友だちをタグ付けして」投稿などを行う機能を提供したい場合

「/me/taggable_friends」という新しいAPIで、「タグ付けできる友達」の一覧を取得できます。

Graph API /user/taggable_friends
https://developers.facebook.com/docs/graph-api/reference/v2.0/user/taggable_friends

このAPIも、「user_friends」パーミッションの取得が必要です。
なお、実際にタグ付け機能を提供するアプリで利用する場合は、「user_friends」パーミッションは審査不要なのですが「Taggable Friends」機能の審査が必要になりますので、注意が必要です。
(※パーミッションの審査ではなく、提供機能の審査、のようです。審査通さないとどうなるんだろ。BANされるのかな。)

さてここからは本音と建前という感じですが、この「/me/taggable_friends」を使えば、従来通りユーザーの友達一覧リストが取れそうな気がします。
実際に試してみました。

「友達の一覧を取得」デモページ

確かに取れますね・・。
コードは下記です。こちらも、デモページのソースはご自由にご覧ください。

<script type="text/javascript">
window.fbAsyncInit = function() {
	FB.init({
		appId   : '*********',
		xfbml   : true,
		version : 'v2.0',
		status  : true,
		cookie  : true,
		oauth   : true
	});
};

function btnClick() {
	FB.login(function (response) {
		if (response.authResponse) {
			var body = 'Reading JS SDK documentation';

			FB.api('/me/taggable_friends?fields=name', function(response) {
				if (!response || response.error) {
					var read_err_text = 'Error';
					$("#read_result").text(read_err_text);
				} else {
					var read_ok_text = jsonParser(response);
					$("#read_result").html(read_ok_text);
				}
			});

		} else {
			alert('User is logged out');
		}
	}, {scope: 'public_profile,user_friends'});
};

function jsonParser(response) {
    var message = "";
    var dataArray = response.data;
    for(var count in dataArray){
        message = message + dataArray[count].name;
        message = message + '<br/>';
    }
    return message;
};

</script>

※訂正!追記
すみません、Taggable Friends APIは、デフォルトだとアプリの「管理人」「開発者」「テスター」でしか利用できないようです。
それ以外のRoleのユーザーが利用するためには、Reviewをして申請通す必要があります。
(なので、↑のデモは動かないですね・・。失礼しました。)

ただし、一応このAPIはあくまでもタグ付け機能を提供するために用意されているので、それ以外の用途で使った場合、アプリに対してペナルティがあり得ますのでご了承ください。

2.ユーザーに対して「友だちを招待する」機能を提供したい場合 ※ただし、ゲームアプリのみ

ゲームアプリなどにおいて、「友だちを招待する」機能を提供する場合は、専用のAPIがあります。

Graph API /user/invitable_friends
https://developers.facebook.com/docs/graph-api/reference/v2.0/user/invitable_friends

「/me/invitable_friends」を使えば、「招待可能な友人一覧」が取得できます。
ただし、ゲームアプリのみ利用可能。

間違えやすいAPI「/me/friendlists」

ちなみに、「/me/friendlists」なるそれっぽいAPIが存在しますが、これは「リスト」のことです。
使ってない人はぴんと来ないかもしれませんが、Facebookでは友達をいくつかの分類で好きなようにリスト化できます。
デフォルトでは「親しい友達」「家族」など。他に例えば「会社」「サークル」とかね。Twitterのリストと同じです。

で、この「/me/friendlists」ってのはそのリストの情報を取得するAPIなので、「友だちの一覧」を取得するものではありません。