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

в 14:01, , рубрики: oauth, oauth 2.0, Блог компании Likeastore, Вконтакте API, метки: , ,

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

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

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

OAuth, OAuth2 и другие

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

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

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

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

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

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

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

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

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

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

Я зарегистировал первое тестовое Standalone приложение и скоро у меня в руках был 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.

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

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

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

Автор: alexbeletsky

Источник

* - обязательные к заполнению поля


https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js