OAuth step by step

OAuth протокол бывает двух версий: 1.0 и 2.0.

Большинство сервисов сегодня используют версию 2.0, вероятно потому что ее проще реализовать. Так же версию 2.0 можно относительно безопасно использовать в standalone-приложениях (те, которые без сервера).

Для понимания протоколов очень полезно взглянуть на их реализацию. Тут я приведу несколько скриптов, которые общаются с OAuth-провайдерами разных версий. Т.е. все скрипты реализуют функционал клиента (не сервера). Используются только стандартные python библиотеки. Вот почему глядя на них лучше понимаешь сам протокол OAuth - все перед глазами и все более-менее знакомое. Конечно, для реальной работы нужно использовать только готовые и проверенные временем пакеты. Эти скрипты только для понимания процесса. Разбираться с готовыми библиотеками порой бывает сложно, они разбиты на много модулей, могут использоваться разные сторонние пакеты, и в итоге общая картина ускользает из виду.

Для начала немного теории. Наверняка вы знаете, что есть два понятия - аутентификация (authentication) и авторизация (authorization). Они вроде бы об одном и том же, но все-таки немного о разном. На всякий случай напомню:

  • аутентификация - это процесс подтверждения подлинности. Т.е. нам нужно просто узнать, что данный человек действительно владеет аккаунтом google с таким id и нам этого достаточно. Просто залогинить пользователя, не получая никаких прав на какие-либо действия с аккаунтом google’а. Этим занимается например протокол OpenID (хотя сейчас google предлагает другой способ, OpenID - deprecated).
  • авторизация - процесс предоставления полномочий что-то делать с аккаунтом. Авторизация уже включает в себя аутентификацию, но дает дополнительные возможности. Например, не просто подтвердить, что пользователь действительно является владельцем аккаунта с определенным id, но еще и узнать его email. А возможно и написать что-то на его стене. Вот это предоставляет протокол OAuth.

Чтобы легче запомнить я использую слово “автор”. Если есть “автор” - значит речь идет о правах (авторстве). Если нет - значит просто проверка подлинности.

OAuth 1.0

Спецификация: http://tools.ietf.org/html/rfc5849

Самое главное, что нужно запомнить - в OAuth 1.0 все запросы подписываются секретным ключом. Секретный ключ нужно хранить только в безопасном месте, единственное такое место - это сервер. Благодаря этому протокол обеспечивает полную безопасность, даже если не используется https. Безопасность в том плане, что даже подслушав запрос злоумышленник не сможет сделать другой валидный запрос. Подслушать сами передаваемые данные он конечно сможет, чтобы их скрыть нужен https.

OAuth 1.0 less-legged (2-legged, 1-legged, 0-legged)

Это модификация протокола OAuth 1.0, в котором пользователь никак не зайдествован. Формально это уже не OAuth протокол, т.к. в спецификции такая последовательность не описана. Просто используются те же приемы, поэтому и называют так же. В этом случае клиентское приложение является пользователем, оно может запрашивать либо общедоступные ресурсы, либо ресурсы, доступные самому клиентскому приложению (даже приватные).

OAuth 2.0 с участием сервера

Спецификация: http://tools.ietf.org/html/rfc6749

Интересно, что в заглавии спецификации OAuth 2.0 назван фреймворком. В то время как в заглавии спецификации OAuth 1.0 назван протоколом.

Для обеспечения полной безопасности OAuth 2.0 необходимо отправлять запросы по https (https должен обеспечивать service provider, например facebook). Получив access_token уже не нужно подписывать запросы секретным ключом. Т.е. если кто-то подслушает запрос и увидит access_token, то он сможет сделать валидный запрос. Вот зачем нужен https. Кроме того при получении access_token, секрет передается по http в открытом виде.

У полученного access_token всегда есть ограниченное время жизни.

В связи с этими особенностями (и некоторыми другими), один из проектировщиков протокола OAuth 1.0 даже отказался от участия в разработке OAuth 2.0, ведь последний очень легко реализовать неправильно и в результате безопасность не будет гарантирована. Подробности можно почитать по ссылке.

Последовательность шагов для получения access_token по OAuth 2.0, которая включает сервер. Сервер для получения access_token отправляет секретный код. Обратите внимание, не используется ни одна крипто-библиотека.

OAuth 2.0 без участия сервера

С OAuth 2.0 можно работать и без сервера по упрощенной схеме. В этом случае мы тоже получаем access_token, но для его получения не нужно знать секрет приложения! Обычно время жизни у access_token, полученного таким способом, маленькое (1-2 часа), в то время как время жизни, полученного с участием сервера больше (может быть несколько десятков дней).