-
Notifications
You must be signed in to change notification settings - Fork 2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Временные коды для приложений (oAuth для бедных) #9
Comments
Сценарий 1 можно переделать так, что доверять приложению не нужно (помимо выдачи ему идентификатора):
NB Что именно означают слова «уже логинился в приложение», надо уточнить [кажется, сценарий 2 оригинального предложения тоже этим грешит]. Например: понадобится ли генерить новый временный код при каждом слёте сессии? (Представить себе двух альтер эго пользователя, знающих с независимые наборы кодов.) |
Насколько я понимаю, сценарий 2 нужен только для поддержки legacy и недоверенных приложений. Второе при моём решении пропадает, первого у нас нет (ну почти), и сценарий 2 становится не нужен. Дополнительно UX-соображение: при отсутствии сценария 2 пользователю вообще не нужно знать, что временные коды — это коды, можно их показывать как-то по-другому (ср. Authorized apps в Твиттере, например) |
Да, это больше похоже на честный oAuth, для каких-то приложений мы его сделаем, но не для всех. Какие есть соображения?
Т.е., конечно, вариант, который я описал, - это не oAuth никакой. Он решает такую задачу:
Чем-то это напоминает не oAuth, а процессинг кредитных карточек:
Т.е. предлагаю пока сделать полузащищенную версию, а потом попланировать полноценную. |
Это просто OAuth минус перманентные авторизации и криптография, именно. Остаётся всего ничего (и мне кажется, что реализация и «полузащищённого», и «честного» примерно одинаково сложна). Аргумент про болезненность не покупаю, все видели Гугл/Фейсбук/Твиттер и привыкли; либо ничего не видели, но тогда ручное копирование временных кодов — ещё большая жесть. А какие именно требования у гуглоформ? Редирект через js-то сделать легко, а вот как их заставить принять ответные данные (что в сценарии 1, что в моём)? Хорошо бы это в ТЗ написать. |
По модели данных:
|
Чтобы лучше понимать условия задачи:
|
Да, поэтому я и предложил совместить вход в auth и авторизацию приложения. |
Про is_temporary_for - я сначала думал вообще id-приложения положить в стрелку, чтобы его было проще искать. Ибо временный код - это "интерфейс" или "декоратор" к основному коду. Но потом понял, что в коде тоже нужно хранить приложение для ограничения и убрал. Наверное, подобный вид выписки означает какую-то определенную связь между кодами, которую можно учитывать в графе траста. Поэтому я бы оставил, чтобы не выводить косвенно эту информацию не из стрелок. |
Я исхожу из того, что большинство проголосовавших пользователей будут "листовыми" в графе, т.е. они ни разу не зайдут в auth, не будут забивать себе голову смыслом этого приложения и пр. Их сценарий простой:
Постарайся этот сценарий не сломать без какой-то понятной цели. |
По поводу модели данных: я не понимаю, зачем кодам expiry date. Что будет, если это время наступит? |
expire date - я думаю, что это ограничение на время использования в этом качестве, например, для голосования. Нужно, чтобы утекшие коды нельзя было использовать бесконечно в отсутствии мастер-кода. При повторном запросе кода того же типа мы возвращаем тот же код, даже, если срок действия истек, но увеличиваем время экспирации (максимум старого и запрошенного). Но для этого действия нужен "исходный" код. Дальше, если мы использовали временный код, он записывается в табличку вместе с датой использования. При повторной валидации мы передаем флажок "был ли действителен на момент использования", а не сейчас. Если мы узнаем, что код был украден в начале февраля, а голосование было в середине, мы можем поставить дату экспирации в прошлое и тем самым инвалидировать использования кода в прошлом. |
У нас есть "вечные" приложения типа директории. Но для кодов, выданных под эти приложения, нужна экспирация. |
Вот это совсем не понимаю пока : ( Про директорию тоже непонятно: во-первых, она наша тоже, во-вторых, правильно ли я понимаю, что ты хочешь переделать её на использование временных кодов? То есть пользователь первый раз вводит настоящий код, получает временный, и далее в директории используется всегда временный? Если пользователь отходил надолго, то ему опять нужно ввести настоящий, чтобы продлить врееменный дальше? Но сейчас мы не проверяем валидность кода на каждый заход в директорию — только на авторизацию |
Голосование устроено так: в базе рядом с голосом сохраняется код, использованный при голосовании, а также дата-время использования. Дальше есть некое API валидации (пакетное), которое передает в auth код приложения и массив (код, время использования). Это API про каждый код отвечает, валиден ли он был на момент использования, а также какие-то характеристики доверия (уже текущие). Что может произойти? Собрали голоса, посчитали. Дальше нашли аномалии, оттрейсили историю появления кода, поняли, что код угнали или неправильно выписали. Корректируем базу auth, указав, что код угнали, предположительно, такого-то числа. Дальше идет опять пакетный вызов, который про этот код, использованный такого-то числа, уже говорит "плохой". При этом, предыдущие использования с датой меньшей даты угона по-прежнему считаются хорошими. |
С директорией - люди логинятся либо мастер-кодом, либо кодом для этого приложения, который они самостоятельно получают в auth.alumni57.ru. В первом случае скрипт или что-то автоматически по мастер-коду запрашивает код для приложения в момент логина. В директорию правки записываются с кодами для приложения. Во втором мы валидируем код через API, проверяя текущую валидность и то, что он разрешен для использования в этом приложении. Дальше, в директории сохраняются "голосования" за правки, у каждого, опять же, дата и время использования. В результате перепроверки старые правки вандалов могут быть инвалидированы, как и для голосования. |
Ок, у нас есть временный код на 2 дня, что означает, что мы ему доверяем так же как исходному для всех действий в этом приложении в течение этих 2х дней. Дальше он заканчивается. Чтобы его продлить, директория должна об этом узнать. В целом решаемо, конечно. Теперь если этот код стал известен кому-то ещё. Код временный, он не может им делать ничего в auth. Но внутри того же приложения он может делать что угодно. Как только настоящий пользователь перепродлит свой код, все прошлые действия ненастоящего пользователя станут валидными. Мне кажется, при такой схеме надо не продлять код, а выписывать новый |
Технически. Мы меняем оригинальный код на временный если: Если для этого оригинального кода для этого приложения есть активный временный — мы его просто возвращаем Если передан временный код и он от переданного приложения и активный — мы его просто возвращаем Остальное — bad request Так? А зачем возвращать маскированный оригинальный? И в любых ответах его возвращать или нет? |
Мы инвалидируем коды в прошлом, если явно поняли, что его угнали. Например, видим правку с кодом, а человек, кому он должен принадлежать, говорит, что правку не делал. Если код угнали, мы должны инвалидировать все действия с момента угона, а не сортировать сессии на хорошие и плохие. Экспирация кода нужна, чтобы если человек перестал пользоваться приложением, но код утек задним числом, чтобы им нельзя было ничего сделать. Это просто уменьшает вероятность манипуляций, но не исключает их, конечно. |
Если человек заново ввел мастер-код и мы генерируем временный, а приложение запрашивает 2 недели, мы должны обеспечить, чтобы временный код работал минимум 2 недели. Итого, если код уже был, нужно посчитать max(expiration-time, now + 2weeks) и записать его в expiration-time. В остальном - все так. |
Выкатил |
В данных появляется новый вид кодов "временные коды для приложений". Эти коды можно использовать каждый только в своем приложении, с их помощью нельзя обращаться к другим, приглашать выпускников и пр.
Подробное описание на wiki:
https://github.com/fedor57/alumni-auth/wiki/TempAppCodesSpec
The text was updated successfully, but these errors were encountered: