- PVSM.RU - https://www.pvsm.ru -

Почему у нас нет поддержки ВКонтакте

После нашего первого анонса [1] на Хабре к нам пришло много новых пользователей из России и одна из самых часто запрашиваемых фич была — поддержка Вконтакте. Почему нет, ведь пользователей сети Вконтакте очень много и наконец с «лайками» из этой соц. сети можно сделать что-то полезное для работы.

У нас уже накопился приличный опыт интеграции с различными API: Twitter, Facebook, Github, Behance и т.д. плюс у нас уже выделился некий boilerplate код, с помощью которого новые интреграции делаются в кратчайшие сроки. Поставив себе цель, порадовать наших пользователей на этой неделе, я вынуждуен признать — это оказалось невыполнимой задачей.

Про причины и то, каким недостатком обладает Вконтакте API, читаем далее.

OAuth, OAuth2 и другие

Первое, на что я смотрю в документации нового сервиса это вид авторизации. OAuth2 стал дефакто стандартом на данный момент и многие поддерживаемые Likeastore [2] сервисы реализуют именно его (отличие составляет лишь Twitter, который реализует OAuth1 и Dribbble, который не реализуюет протокола вовсе, а поддерживает лишь дедовский login/password протокол).

Для тех, кто не знаком суть OAuth2 протокола состоит в том, что вы регистрируете клиенское приложение, которое может быть авторизованно пользователем и через обратные вызовы к серверу, сначала издается т.н. code, который «обменивается» на токен доступа — access_token.

Обладая токеном доступа, приложение получает возможность делать запросы от имени пользователя. Это очень удобно, так как все популярные API имееют ряд ограничений (т.н. rate limit) и зная количество разрешенных реквестов на единицу времени, компонент ответсвенный за сбор «лайков» (collector) может правильно расчитывать время следующего реквеста избегая уйти в бан.

Я был рад видеть, что Вконтакте поддерживает [3] именно OAuth2 протокол.

Методы и лайки

Следующее, что нужно было найти это методы которые позволяют получить пользовательские «лайки».

В отличии от всех других API, которые поддерживаются у нас и имееют как правило один метод, типа /favorites, /likes и т.п. у Вконтакте их оказалось 5 (любимые пользователи [4], фотки [5], посты [6], видео [7] и линки [8]). Делать 5 реквестов вместо одного, казалось не самой лучше идеей для производительности, более ответы разных методов имели самых разный формат, что немного выпадало из общей архитектуры collector-а.

Позже я заметил, что ВК предлагает т.н. «хранимые процедуры» [9], в которой можно собрать все нужные данные и вернуть их за один HTTP реквест. Вполне рабочее решение, но после опыта с Facebook API batching [10] мне показалось не таким элегантным.

Тем не менее, методы были — все остальное дело техники.

Регистрация приложения и первый реквест

Я зарегистировал первое тестовое Standalone [11] приложение и скоро у меня в руках был access_token. Все шло как по старой, накатанной схеме. Дело оставалось за кодом, который делает HTTP реквест и разбирает результат (connector).

Но, каково же было мое разочарование, когда в консоли вместо данных я увидел следующий ответ.

{ error:
   { error_code: 5,
     error_msg: 'User authorization failed: method is unavailable with server auth.',
     request_params: [ [Object], [Object], [Object], [Object], [Object] ] } }

Сначала мне показалось, что что-то не так с кодом обращаения к API но 10 раз пересмотревши код и URL реквеста, я понял — все нормально. Гугл по этому вопросу дал очень мало информации… в документации спецификацию ошибки я не увидел, а результаты поиска вели в древние форумы, ответа в которых небыло.

Меня еще раз насторожило вот это предупрежединие:
image
Но права доступа были правильные и сознанное мной приложение было Standalone.

Открыв глаза пошире и внимательней прочитавши документацию по Standalone приложениям, я увидел, что они поддерживают только клиентсткую авторизацию!
image
Разница с серверной, заключается в том, что в качестве response_type передается значение token, а шага с «обменом» code на access_token, вообще нет, так как в обратоном вызове сразу присутвует access_token переданный как хеш параметр, т.е. доступный только с клиента и не доступный с сервера. Т.к. обе они называются OAuth2, я не сразу обратил внимание на эту разницу.

Львиная доля API методов ВК, доступны только с клиентской авторизацией. Это открытие ввело меня в реальный ступор, зачем?

И правда, зачем?

Что сподвигло разработчиков Вконтакте на введение подобного ограничения, и почему ВК это единствинный API, который его реализует?

Конечно же, в голову приходят всякие методы обхода данного ограничения (например, вычитывать access_token на клиенте и делать AJAX POST на сервер и после этого его свободно использовать). Я думаю, что при продуктивном брейнсторме может родится еще пару идей, т.е. метод на самом деле ничего не защищает, а лишь добавляет головной боли разработчикам. Но всевозможные «обходы» и «хаки» это не то, как бы мы хотели строить свой продукт.

Не смотря на все мелочи — именно проблема серверного доступа к API поставила крест на поддержке Вконтакте в Likeastore [2].

ЗЫ. Первичной целью этого поста было обращение к пользователям, а также сообществу с просьбой помочь советом тех кто возможно был в подобной ситуации. Уже в процессе написания, я нашел замечательный пост kimrgrey [12] который описывает туже самую проблему [13], а также ответ antanubis [14] который объясняет [15] почему это сделано именно так. Его аргументация очень понятна, как по мне, не так убедительна.

Я очень надеюсь, что Вконтакте пересмотрит политику в отношении веб приложений или как минимум откроет серверный доступ к такой информации, как «лайки».

ЗЫЫ. Еще одним вариантом может быть использование Прямой авторизации [16], но лично я никогда бы не ввел свой пароль от ВК на другом сайте + требуется утвержение администрации, которое можно и не получить или это займет много времени. Но если кто-то пользовался этим способом, был бы рад услышать опыт.

Автор: alexbeletsky

Источник [17]


Сайт-источник PVSM.RU: https://www.pvsm.ru

Путь до страницы источника: https://www.pvsm.ru/vkontakte-api/55595

Ссылки в тексте:

[1] анонса: http://habrahabr.ru/company/likeastore/blog/209328/

[2] Likeastore: https://likeastore.com

[3] поддерживает: http://vk.com/dev/auth_sites

[4] пользователи: http://vk.com/dev/fave.getUsers

[5] фотки: http://vk.com/dev/fave.getPhotos

[6] посты: http://vk.com/dev/fave.getPosts

[7] видео: http://vk.com/dev/fave.getVideos

[8] линки: http://vk.com/dev/fave.getLinks

[9] «хранимые процедуры»: https://vk.com/dev/execute

[10] Facebook API batching: https://developers.facebook.com/docs/graph-api/making-multiple-requests

[11] Standalone: http://vk.com/dev/auth_mobile

[12] kimrgrey: http://habrahabr.ru/users/kimrgrey/

[13] проблему: http://habrahabr.ru/post/179953/

[14] antanubis: http://habrahabr.ru/users/antanubis/

[15] объясняет: http://habrahabr.ru/post/179953/#comment_6268391

[16] Прямой авторизации: http://vk.com/dev/auth_direct

[17] Источник: http://habrahabr.ru/post/213467/