Авторизация по ЭП. Общая схема

 

 

Введение

Сразу оговоримся, что электронная подпись (ЭП) – это тоже самое, что и электронная цифровая подпись (ЭЦП), пока дело не касается официальных документов. В законодательном плане понятие ЭП появилось в законе от 8 апреля 2011 г ‘Об электронной подписи’ и фактически стало использоваться вместо ЭЦП. Мы будем использовать термин ЭП, хотя в некоторых ссылках будет появляться аббревиатура ЭЦП.

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

Общие сведения об ЭП

Для понимания происходящего, конечно, надо рассказать о том, что такое ЭП.  Написано по этому поводу достаточно, приведем некоторые ссылки: википедия, статьи на хабре с художественными и менее художественным текстами. Для полноты изложения мы выделим основные моменты, которые обязательно пригодятся для понимания составляющих частей системы авторизации по ЭП. Если здесь что-то непонятно или неизвестно, то лучше всего пробежаться хотя бы по статье из википедии.

  • Надо понимать, что такое закрытый и открытый ключи. ЭП реализуется на основе ассиметричных алгоритмов шифрования. Общая особенность этих алгоритмов в том, что у каждого объекта, который хочет что-то подписывать, есть закрытый ключ и открытый ключ, являющиеся просто одним или несколькими числами. Закрытый ключ известен только одному лицу, а открытый может свободно распространятся. В алгоритме электронной подписи закрытый ключ используется, чтобы подписывать информацию, а открытый — чтобы проверять корректность подписи.
  • Сертификат открытого ключа. ЭП становится подписью тогда, когда по ней можно узнать, кому принадлежит эта подпись. Для этого существуют сертификаты открытых ключей. В сертификат включается общая информация о лице, которому принадлежит открытый ключ, информация, которая идентифицирует это лицо (например, для физического лица это могут быть фамилия, имя, отчество, номер паспорта, адрес электронной почты), а также электронная подпись этой информации третьей стороны – удостоверяющего центра (УЦ). Именно подпись УЦ гарантирует корректность и целостность сертификата, т.е. принадлежность подписи лицу, указанному в сертификате.
  • Цепочка сертификатов, корневой сертификат. Сертификат открытого ключа подписывается закрытым ключом УЦ. Чтобы проверить эту подпись надо иметь открытый ключ этого УЦ, который распространяется с помощью сертификата. Если в системе, которая проверяет подпись, установлен этот сертификат, то считается, что мы доверяем этому УЦ. Если же такого сертификата нет, то мы должны проверить этот сертификат, который подписан следующим УЦ. В итоге мы получаем цепочку сертификатов открытых ключей, каждый из которых должен быть проверен, а в конце цепочки должен присутствовать сертификат, который уже установлен в нашей системе и мы ему доверяем. Такие сертификаты называются корневыми.
  • Списки отозванных сертификатов. Обычно выпускаемые сертификаты имеют ограниченный период действия, и кроме того, сертификаты могут потерять актуальность в силу потери секретности закрытого ключа. Поэтому УЦ должен уведомлять пользователей о том, какие сертификаты не являются действительными. Такие сертификаты называются отозванными и распространяются в виде, называемом список отозванных сертификатов. УЦ периодически публикует эти списки, и система, которая проверяет подлинность подписи, должна обладать актуальными данными об этих списках.

Алгоритм авторизации по ЭП. Теория.

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

Итак, в общих чертах алгоритм выглядит следующим образом:

  1. пользователь открывает страничку нашего сайта с авторизацией;
  2. мы посылаем ему форму, содержащую кнопку “подписать”, список доступных личных сертификатов и скрытые, случайно сгенерированные данные, которые будут подписаны;
  3. пользователь выбирает сертификат, с помощью которого он хочет аторизоваться на сайте, и нажимает кнопку “подписать”, отправляя на сервер подписанные данные и свой сертификат;
  4. на сервере мы проверяем, что подпись корректна, и что подписанные данные соответствуют данным, отправленным пользователю; если обе проверки выполнены, то мы авторизуем пользователя, как пользователя, за которым закреплен присланный сертификат, или просто создаем нового пользователя с данным сертификатом.

Ясно, что 1ый и 2ой пункты просты в реализации. Однако, пункт 1 содержит ключевые слова “нашего сайта”, которые говорят о том, что аутентификация нашего сервера прошла успешно. В этой статье мы частично расскажем о реализации пункта 4 и остановимся перед использованием конкретных криптографических приложений, остальное отложим до следующей статьи.

Авторизация по ЭП. Практика.

Поскольку авторизация по ЭП нам требовалась в проекте, где уже используется Django, мы и будем его использовать.

Данные для подписи

Начнем по порядку. Сперва нам надо передать пользователю для аутентификации данные, которые он подпишет. Для этого мы пишем представление, которое будет отвечать пользователю на запросы. В этом представлении указываем шаблон и генерируем случайную строку для подписи.

Обязательно сохраняем эту строку в сессии, чтобы можно было в дальнейшем сверить ее с подписанными данными. Здесь используется стандартная джанговская ‘SessionMiddleware’.

Аутентификация пользователей в Django

Теперь перейдем к моменту получения от пользователя подписанных данных. Прочитав документацию по аутентификации в Django, мы знаем следующее. Чтобы заменить или дополнить аутентификацию пользователя в Django, достаточно написать свой аутентификационный бэк-енд. В нашем случае по подписанным данным нам надо осуществить проверку корректности подписи и получить пользователя в системе, которому принадлежит сертификат соответствующего открытого ключа.

Наш бэк-енд может выглядеть, например, так:

Здесь signed_data — подписанные данные в формате, crt_info — сертификат открытого ключа пользователя, raw_data — данные, которые отсылались сервером для подписи. Функция _check_sign говорит нам о корректности подписи и возвращает ключ, по которому мы находим в своей базе данных пользователя, она является ключевой и мы уделим ей внимание позже. Ключ может быть, например, самим сертификатом открытого ключа. Реализацию функции _get_users_by_key мы опускаем. Мы можем, например, использовать стандартную джанговскую модель пользователя и хранить в ней дополнительное поле для ключа. Тогда _get_users_by_key будет просто поиском по жтому полю.

Чтобы воспользоваться написанным бэк-ендом, надо добавить его в настройки проекта и вызвать функцию authenticate. Наш класс LoginView мы можем дополнить обработкой пост-запроса:

Как видно, в запросе, кроме подписанных данных, мы получаем еще сертификат открытого ключа, несмотря на то, что подписанные данные содержат информацию об этом и других сертификатах в цепочке сертификатов (забегая вперед, данные подписываются в формате CAdES). Такие параметры возникли из-за того, что интерфейс CryptoPro CSP 3.6 (а это то, о чем пойдет речь в дальнейшем) не позволяет простым способом извлечь сертификат, которым подписаны данные.

Проверка подписи

Теперь вернемся к функции _check_sign, которая должна выполнять проверку подписи. Как было сказано, она делает 2 вещи: проверяет корректность подписи и совпадение подписанных данных с отправленными пользователю.

Первую проверку осуществляет функция verify, которая уже использует стороннее ПО для проверки подписи. В нашей реализации в роли такого ПО выступает CryptoPro CSP 3.6. Функция возвращает результат проверки и подписанное сообщение в случае успеха или текст ошибки в случае некорректной подписи. Дальше сверяем подписанные данные и сохраненные в сессии.

Что дальше?

В этой статье мы узнали коротко про ЭП и набросали несколько примеров кода, которые, благодаря Django, делают немало работы. Дальнейший путь реализации сильно зависит от постановки задачи. Так, для реализации проверки подписи можно воспользоваться готовыми наработками для проверки подписи. Однако, наша цель всего лишь проверить подпись, поэтому здесь можно и написать свой код, используя OpenSSL.

Если же от нас требуется использование только сертифицированного ПО, то здесь уже надо читать документацию такого ПО и писать побольше кода. Как можно уже понять, нам нужен был именно такой вариант, и в качестве сертифицированного ПО мы использовали CryptoPro CSP 3.6. Поэтому мы в дальнейшем и расскажем об его использовании, но и не обойдем стороной OpenSSL.

 


+7 (495) 646-87-45

info@chtd.ru

125252, г. Москва, пр. Берёзовой Рощи, д. 12, оф. 56

На карте