9 September 2008

Facebook, Perl и WWW:: Facebook:: API

Lumber room
В этой статье попытаюсь описать те неочевидные для меня проблемы и вопросы, с которыми я столкнулся при попытке создания простейшего приложения для Facebook.

Итак, поступила задача написать web-приложение для Facebook. Для изучения API и принципов разработки, решил написать тестовое приложение, которое будет выводить список моих друзей и их статусы.
Так как данной социальной сетью я активно не пользовался, пришлось начинать с самого начала.

Изучение предметной области

Первым делом был изучен раздел «Get Started» на Facebook (далее FB). В нем я нашел ответ на вопрос «как писать приложение», но не совсем понял, что и для чего нужно. Следующим шагом было изучение раздела «Anatomy of an App» с описанием видов приложений. И, наконец, я прочитал статью «Как создавать приложения для Facebook» на Хабре.
Все прочитанное сложилось у меня в голове в виде следующей картины:
  1. Web-приложение в FB находится на определенной странице вида apps.new.facebook.com/your_app_name (Canvas Page URL), на которой приложению отводится большая часть страницы.
  2. При запросе страницы приложения FB вызывает с указанного адреса (Callback URL) скрипт с некими параметрами, необходимыми для работы с API. Ответ от вашего скрипта FB отображает на странице в рабочей области.
  3. Ваше приложение может генерировать информационные блоки (profile box) для вставки в профиль пользователя
Выбор средств реализации

В Facebook Developers Wiki есть описание фреймворков для большого количества языков. Сам FB предлагает библиотеку на PHP5.
Поскольку в задании язык реализации не оговаривался, я выбрал Perl, как наиболее изученный и любимый мной. В дальнейшем планирую «потрогать» либы на Python и JS «just for fun».

Реализация

Для начала разработки ставим на сервер модуль WWW::Facebook::API с cpan.org.

Следующим шагом была попытка запустить адаптированный тестовый скрипт из примера. Эта попытка оказалась неудачной, так как FB не присылал session_key моему приложению, который необходим для нормальной работы с FB API. После изучения примеров на php было установлено, что требуемые параметры присылаются только в том случае, если пользователь разрешил вашему приложению доступ к своим данным.
В перловом модуле это реализует метод

$fb->require_login($q);

которому передается CGI объект. В случае отсутствия авторизации метод возвращает текст на FBML , который редиректит пользователя в нужном направлении.
После проверки на авторизацию пользователя проверяем корректность переданных данных и устанавливаем session_key для общения с FB API.

	my $params = $fb->canvas->validate_sig($q);

	if ( $params->{'user'} )
	{
	        $fb->session_key( $params->{'session_key'} );
	}

После этих действий тестовый скрипт у меня успешно заработал и с использованием FBML на странице приложения появился список моих друзей и их статусов.

Продолжаем разговор

Следующая задача — поместить profile box на страницу профиля пользователя.
В FB API за это отвечает метод Profile.setFBML, которому надо передать в параметре «profile» текст, который будет отображаться в box'e на вкладке «Блоки», а в параметре «profile_main» текст, который будет показываться в блоке на главной странице.
Я добросовестно передал эти параметры:
	$fb->profile->set_fbml( 
	                  uid => $params->{'user'},
	                  profile => 'blocks',
	                  profile_main => 'main page'
	);

После чего начались мои мучения, которые побудили написать данную статью. Дело в том, что устанавливался только параметр 'profile' и profile box появлялся только на вкладке «Блоки», а пункт меню, который позволял бы поместить блок на основную страницу профиля был недоступен.


Изучение вики и форума разработчиков приложений для FB ничего не дало. Информация по решению проблемы была, но советы ограничивались передачей обязательного параметра «profile_main», который у меня уже и так передавался. Потом было много гугла и исходных кодов ).
Решение нашлось в баге к модулю.
Дело в том, что FB в июле 2008 года изменил свой дизайн и сделал для нового интерфейса новый REST server api.new.facebook.com/restserver.php, а в используемом модуле был указан старый адрес api.facebook.com/restserver.php.
После строчки:

$fb->server_uri('http://api.new.facebook.com/restserver.php') ;

все заработало как надо.

Материалы
Tags:facebookfacebook APIperl
Hubs: Lumber room
+3
396 6
Leave a comment