ООО «Ивент Хаб» · Москва · работаем по всей России
Пн—Пт, 10:00—19:00hello@gusi-lebedi.comРеквизиты
Практическое руководство

OAuth 2.0: как работает доступ к сервисам без передачи пароля

На примере CRM и календаря разбираем разрешения, код авторизации, PKCE и токены: как подключить сервис без передачи пароля и проверить прекращение доступа.

OAuth: предоставление приложению ограниченного доступа к ресурсу

CRM нужно видеть встречи в календаре сотрудника. Но передавать ей пароль от его аккаунта ради этой задачи слишком много: вместе со встречами можно открыть доступ к данным, которые вообще не нужны интеграции. OAuth 2.0 позволяет предоставить приложению отдельное разрешение и обращаться к сервису с токеном вместо пароля пользователя.

В Гуси-Лебеди предлагаем разбирать такое подключение с простого вопроса: что именно должно получить приложение и как человек сможет прекратить доступ? Покажем это на условном примере CRM и календаря, затем разберём код авторизации, PKCE, токены и проверку готовой интеграции.

Что такое OAuth 2.0 и кому мы разрешаем доступ

Участники OAuth и выбор разрешений для приложения

OAuth 2.0, или OAuth2, это стандарт делегирования ограниченного доступа к защищённым ресурсам. Пользователь разрешает одному приложению выполнять определённые действия в другом сервисе. Приложение получает access token и предъявляет его API. Границы доступа задают выданные разрешения и правила сервиса. Такая модель описана в базовой спецификации RFC 6749.

В нашем примере сотрудник подключает календарь к CRM. Он входит в свой аккаунт у поставщика календаря и разрешает читать встречи. CRM получает возможность обратиться к нужному API, но пароль сотрудника ей не передают. Если для работы достаточно чтения, право удалять события запрашивать незачем.

У этого обмена четыре роли. Владелец ресурса разрешает доступ, здесь это сотрудник. Клиент запрашивает его, здесь это CRM, а не человек. Сервер авторизации обрабатывает разрешение и выдаёт токен. Сервер ресурсов обслуживает запросы к календарю и проверяет доступ. Последние две роли могут находиться в одной системе, но решают разные задачи.

Почему OAuth не равен входу на сайт

Аутентификация отвечает на вопрос «кто вошёл?», авторизация определяет доступные действия. OAuth описывает вторую задачу. Поэтому наличие токена доступа само по себе не заменяет проверку личности и не даёт готовой схемы привязки аккаунта на вашем сайте.

Если нужен именно вход через стороннего провайдера, рассмотрите OpenID Connect, или OIDC. Это слой аутентификации поверх OAuth 2.0: приложение получает ID token с утверждениями о пользователе и проверяет его по правилам OIDC. Подключение календаря и вход в CRM могут быть двумя отдельными действиями. Их не стоит объединять только потому, что оба начинаются с перехода к провайдеру.

Scope: что разрешено делать

Scope обозначает область доступа. Названия и смысл разрешений определяет конкретный сервер авторизации. Условные названия calendar.read и calendar.write в нашем примере означают чтение и изменение встреч; это пояснение, а не универсальные параметры для любого календаря.

До разработки сформулируйте права обычным языком: «читать события выбранного календаря», «создавать новые встречи», «изменять существующие». Затем сопоставьте их с документацией API. Один scope может охватывать больше действий, чем требуется продукту. Ограничения нужно проверять на стороне сервиса и в логике приложения, а не только обещать на экране подключения.

Как работает Authorization Code с PKCE

Согласование последовательности подключения и обмена кодом авторизации

Authorization Code Flow предусматривает промежуточный код: сначала приложение получает код авторизации, затем обменивает его на токен. Для нашего примера возьмём CRM с серверной частью. В такой архитектуре обмен кода и хранение токенов можно организовать на сервере, не выдавая их интерфейсу браузера.

  1. CRM начинает подключение. Она создаёт отдельную операцию авторизации и направляет браузер сотрудника к провайдеру. В запрос входят идентификатор приложения client_id, адрес возврата redirect_uri, запрашиваемые права scope, response_type=code и параметры защиты.
  2. Сотрудник подтверждает права. Провайдер проверяет его вход, если это требуется, и обрабатывает разрешение. При отказе CRM должна показать, что календарь не подключён. Отказ не является технической аварией.
  3. Браузер возвращается с кодом. Приложение проверяет, что ответ относится к начатому подключению. Код имеет ограниченный срок действия и предназначен для однократного обмена, а не для запросов к календарю.
  4. Сервер CRM запрашивает токен. Он передаёт код в token endpoint провайдера, предъявляет необходимые данные клиента и PKCE. После проверки сервер авторизации возвращает access token и, если предусмотрено, refresh token.
  5. CRM обращается к API календаря. Сервер ресурсов проверяет токен и допустимость операции. Успешное получение токена ещё не означает, что разрешены любые действия с любыми событиями.

Адрес возврата регистрируют у провайдера заранее. Его проверка не должна превращаться в «подходит любой адрес нашего домена». В современных рекомендациях применяется точное сопоставление зарегистрированного redirect URI, с отдельно описанным исключением для порта локального адреса некоторых нативных приложений.

Зачем нужен PKCE

PKCE, Proof Key for Code Exchange, связывает начало авторизации с последующим обменом кода. Приложение создаёт случайный секрет code_verifier. В первом запросе отправляет полученный из него code_challenge с методом S256. При обмене кода предъявляет исходный verifier. Сервер пересчитывает challenge и проверяет соответствие. Перехваченного кода без этого секрета недостаточно для успешного обмена.

Механизм описан в RFC 7636. По актуальным рекомендациям безопасности RFC 9700 публичные клиенты обязаны использовать PKCE; для конфиденциальных клиентов он рекомендован. Это защита конкретного этапа, а не замена HTTPS, проверки адреса возврата или контроля доступа к данным.

Для защиты от подделки межсайтового запроса также нужно связать ответ с операцией пользователя. Часто для этого применяют одноразовый state, привязанный к сессии. Стандарт допускает и другие предусмотренные схемой защиты механизмы при соблюдении их условий. Важно проверить весь выбранный вариант в библиотеке и у провайдера, а не просто добавить параметр с постоянным значением.

Client ID, секрет и выбор потока

client_id является публичным идентификатором, а не паролем приложения. client_secret служит одним из способов аутентификации конфиденциального клиента. Его нельзя прятать в JavaScript-файле и считать защищённым: код браузерного приложения доступен пользователю. Публичный клиент не способен надёжно хранить такой общий секрет. Authorization Code с PKCE применим и к публичным клиентам, но размещение токенов и остальные меры защиты зависят от архитектуры.

Для взаимодействия сервисов от имени самого приложения может подходить Client Credentials. Он не заменяет согласие конкретного сотрудника на чтение его календаря. Исторический Implicit Flow с выдачей токена через ответ авторизации сейчас не рекомендуется. Resource Owner Password Credentials, где клиент получает пароль пользователя, запрещён актуальными рекомендациями RFC 9700.

При разработке серверной части интеграции стоит согласовать схему обмена до настройки кнопки «Подключить». Готовая библиотека помогает реализовать протокол, но конфигурация клиента, разрешения и обработка отказов остаются частью проекта.

Токены: хранение, обновление и прекращение доступа

Хранение токенов, истечение и прекращение доступа

Access token предъявляют серверу ресурсов для выполнения разрешённой операции. Для bearer-токена типичный вариант передачи описан в RFC 6750: заголовок Authorization: Bearer ACCESS_TOKEN. Значение здесь условное. Настоящий токен нельзя помещать в публичный пример, переписку с поддержкой или открытый журнал запросов.

Refresh token используют для получения нового токена доступа на сервере авторизации. Его не отправляют API календаря вместо access token. Выдача refresh token необязательна: правила зависят от провайдера, клиента и настроек доступа. Поэтому нельзя обещать, что любое подключение будет обновляться без участия человека.

ID token относится к OpenID Connect и сообщает об аутентификации. Он не является универсальным пропуском к API. OIDC требует проверять токен, в том числе издателя, получателя и срок действия, а также другие условия выбранного потока. Правила приведены в OpenID Connect Core.

OAuth не предписывает всем токенам формат JWT. Access token может быть непрозрачной строкой, смысл которой знает сервер. Если используется JWT, формат сам по себе не доказывает подлинность или достаточность прав. Подробности проверки разбираем отдельно в статье о JWT и проверке токенов.

Что происходит, когда токен истёк

Универсального срока «один час для всех» нет. Ориентируйтесь на ответ сервера и документацию провайдера. Если refresh token доступен и действителен, приложение может запросить новый access token. Если обновление невозможно, сотруднику нужно предложить повторное подключение, сохранив понятное объяснение.

В нашей серверной схеме токены следует хранить отдельно от публичного кода и выдавать доступ к ним только нужным компонентам. Исключите секреты из журналов, мониторинга ошибок и резервных выгрузок для диагностики. Когда провайдер выдаёт новый refresh token взамен старого, приложение должно корректно сохранить его; параллельные запросы обновления не должны случайно перезаписывать актуальное значение.

Выход из CRM и отключение календаря не одно и то же

Выход завершает пользовательскую сессию CRM. Сам по себе он не отзывает разрешение у поставщика календаря. Кнопка «Отключить календарь» должна прекратить работу интеграции и запустить предусмотренный провайдером порядок отзыва, если он доступен. Удалить токен из интерфейса недостаточно, если фоновая задача продолжает пользоваться его копией.

RFC 7009 описывает отзыв токенов. При этом эффект для связанных токенов зависит от политики сервера, а распространение отзыва может занимать время. Для JWT, проверяемого локально, особенно важно выяснить, как ресурсный сервер узнает о прекращении доступа. Не обещайте мгновенную остановку всех запросов без проверки конкретной системы.

Как проверить OAuth-интеграцию перед запуском

Проверка успешного подключения, отказа и отключения OAuth

Успешная кнопка подключения показывает только один путь. Для приёмки нужны и ситуации, когда человек отказал, прав не хватило или связь прекратилась. Ниже пример плана проверки для нашей условной CRM, а не результаты тестирования реального продукта.

СценарийЧто должно быть проверено
Разрешено только чтениеCRM читает разрешённые события, попытка изменения не проходит.
Сотрудник отказалПодключение не объявляется успешным, есть понятный способ вернуться к настройке.
В ответе чужой state или неверный PKCEНесоответствие обнаруживается на предусмотренном этапе, токен не принимается как результат этой операции.
Код использован повторноПовторный обмен отклоняется, ошибка не открывает чужой аккаунт.
Access token истёкДоступ обновляется по правилам провайдера либо требуется повторное подключение.
Разрешение отозвано у провайдераИнтеграция обнаруживает прекращение доступа и не показывает ложное состояние «работает».
Календарь отключён в CRMФоновые обращения прекращены, предусмотренный отзыв выполнен, сохранённые данные обрабатываются по правилам продукта.
Подключены два сотрудникаТокены и ресурсы не перепутаны, каждый получает только допустимые для него данные.

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

В документации подключения полезно сохранить поставщика, тип клиента, адреса возврата, запрашиваемые scopes, правила хранения и обновления токенов, порядок отключения и ответственных за настройки. Секреты в этот общий документ не включают. Если параллельно проектируется сам обмен данными, пригодится наш разбор ресурсов и запросов REST API.

В Гуси-Лебеди советуем оценивать OAuth-интеграцию по тому, насколько понятно управляется доступ. Какие действия разрешены? Кто их выполняет? Что произойдёт после отказа или отключения? Когда ответы подтверждены настройками и тестами, подключение становится управляемой частью продукта.

Начать проект

Обсудим вашу задачу

Ответим в течение рабочего дня. Можно без технического задания — достаточно цели и вводных.

Заполнить короткий бриф ↗
Навигация по экспертизе

Ещё направления для вашего проекта

Все 86 услуг →