Добавить MFA в прототип, не ломая входы
Добавьте MFA в прототип с минимальным риском: выберите TOTP или passkeys, настройте recovery‑коды и выкатывайте по фазам с понятными фолбэками.

Почему MFA так часто ломает прототипные входы
Добавление MFA в прототип — это не «ещё один экран». Это меняет правила: кто может войти, что происходит при ошибке и сколько крайних случаев должен обрабатывать ваш поток входа.
Кодовые базы прототипов часто имеют хрупкую аутентификацию: смешанные сессии и токены, неясный источник правды для пользователя и упрощения вроде пропуска подтверждения почты или повторного использования одноразовых кодов. MFA быстро обнажает эти упрощения. Небольшое несоответствие (смещение времени для TOTP, дублированные записи пользователя или гонка между «проверить пароль» и «создать сессию») может заблокировать реальных пользователей.
«Не ломать входы» — это больше, чем «работает счастливый путь». Люди должны всё ещё заходить со старых устройств и браузеров, должен быть безопасный путь назад, если они потеряли второй фактор, и нагрузка поддержки не должна взрываться сообщениями «я не могу войти».
Перед изменениями измерьте базовую картину, чтобы знать, помогло ли MFA или навредило. Отслеживайте несколько показателей в течение нескольких дней: скорость успешных входов, отток по шагам (введён пароль, показан запрос кода, код принят), события блокировок и завершённые сбросы пароля, и медианное время входа.
Также решите, кого вы защищаете в первую очередь. Принудительное требование MFA для всех сразу максимум повышает трение и нагрузку поддержки. Безопаснее начать с аккаунтов с высоким риском: админы, доступ к биллингу и те, кто может менять настройки безопасности. Это даёт данные из реального мира без превращения всего входа в пожарную тревогу.
Основы MFA и где оно встраивается в поток входа
MFA (многофакторная аутентификация) означает доказать, что это действительно вы, с помощью двух разных видов доказательств. Обычно это пароль (что вы знаете) плюс код или подтверждение устройства (что у вас есть). «Второй фактор» — это дополнительная проверка. «Step‑up auth» означает, что MFA запрашивают только для рискованных действий, например изменение почты или просмотр биллинга. «Recovery» — это спасательный путь, если вы потеряли фактор.
Самое безопасное место для MFA в прототипе — после успешного первого шага входа. Это сохраняет существующий поток пароля или OAuth.
Где MFA располагается в потоке
Для входа по паролю: пользователь вводит email и пароль, вы их проверяете, затем проверяете, включено ли MFA. Если да — показываете запрос для TOTP или подтверждение passkey перед созданием полноценной сессии.
Для входа через OAuth (Google, GitHub и т.п.): завершаете callback провайдера, сопоставляете или создаёте пользователя, затем требуете MFA до выдачи вашей сессионной куки или токена.
Ключевая идея: не делайте «полу‑вход» и не надейтесь восстановиться, если MFA не сработает. Решите однозначно, когда пользователь считается полностью аутентифицированным, и включите MFA в это решение.
Что меняется в базе данных
Храните данные MFA отдельно от паролей и относитесь к ним как к чувствительным.
Обычно нужен простой флаг enabled и отметка времени регистрации, выбранный метод (TOTP, passkey, none) и методо‑специфичная метадата, и минимальные данные для проверки будущих вызовов (например, зашифрованный секрет TOTP или ID учетных данных passkey). Добавьте хеши recovery‑кодов (не в открытом виде), маркер «использован» для каждого кода и опционально поле вроде last_mfa_verified_at, если планируете правила step‑up.
Что логировать для отладки
Хорошие логи позволяют дебажить блокировки без утечки секретов. Логируйте события: «создан вызов MFA», «проверка MFA не прошла», «использован recovery‑код», вместе с ID пользователя, временной меткой, IP и user agent. Не логируйте коды TOTP, секреты, сырые recovery‑коды или полные OAuth‑токены.
Выбор TOTP vs passkeys для прототипа
Если добавляете MFA в прототип, выбор обычно между TOTP (коды из аутентификатора) и passkeys (биометрия или подтверждение устройства). Оба работают, но ломаются по‑разному.
TOTP — классический «введите 6‑значный код». Пользователь сканирует QR‑код приложением аутентификатора, затем вводит код. На вашей стороне хранится общий секрет на пользователя (зашифрованный) и несколько полей аудита. Частые причины проблем: пользователь потерял телефон, время устройства ушло вразнос, пользователь зарегистрировался дважды и перезаписал секрет, или приложение случайно позволяет вход без проверки второго фактора.
Passkeys кажутся проще. Пользователь подтверждает Face ID, отпечатком или PIN устройства. Вы храните публичный ключ и credential ID, а не общий секрет. Проблемы смещаются: зависимость от устройства (нет доступа к устройству), путаница при настройке на нескольких устройствах или «работало на ноуте, но не на телефоне», если passkeys не синхронизируются так, как пользователь ожидает.
Практическое правило простое. Выбирайте TOTP, когда нужен предсказуемый кросс‑девайс доступ (админы, служба поддержки, B2B‑инструменты) и нельзя полагаться на современные устройства. Выбирайте passkeys, когда хотите самый гладкий вход для потребителей и готовы, что восстановление потребует дополнительного внимания. Поддерживайте оба, если у вас смешанная аудитория, но держите интерфейс сфокусированным: рекомендуйте один вариант по умолчанию («Использовать passkey на этом устройстве») и предложите другой как ясный запасной путь («Используйте приложение‑аутентификатор вместо этого»).
Пример: двухчеловеческий стартап может выбрать TOTP для внутренней панели админа (работает везде), а потом добавить passkeys для удобства без изменения политики для админов.
Поток регистрации фактора, который не приводит к блокировкам
Главный риск при регистрации — включить MFA слишком рано. Если вы переключаете флаг «MFA включено» до того, как пользователь доказал, что фактор у него работает, прототип может запереть его в цикле: запрашивается код, но аутентификатора нет; prompt passkey не появляется; сессия теряется.
Безопасный паттерн — считать регистрацию тестом и включать MFA только после успешной верификации. Это правило предотвращает большинство блокировок.
Паттерн регистрации, защищающий от блокировок
Держите поток линейным и снисходительным. Начните регистрацию, пока пользователь полностью вошёл (свежая сессия). Позвольте ему настроить фактор (скан QR для TOTP или создать passkey), затем сразу же выполните одну проверку (ввести код TOTP или завершить подтверждение passkey). Сразу после этого покажите recovery‑коды и требуйте явного подтверждения, например «Я сохранил их». Только потом помечайте MFA как включённое и показывайте экран успеха.
Хорошие подсказки уменьшают обращения в поддержку. Говорите конкретно: «Сканируйте этот QR в Google Authenticator или 1Password. Затем введите 6‑значный код для подтверждения. Если вы закроете вкладку до подтверждения, MFA не включится.»
Краевые случаи, которые стоит учесть заранее
TOTP часто ломается из‑за сдвига времени. Если код отклонён, подскажите пользователю проверить автоматическую установку времени на телефоне и разрешите повторную попытку перед перезапуском процесса.
Passkeys могут не сработать, если устройство отсутствует или prompt заблокирован. Предложите запасной путь при регистрации: «Не можете использовать passkey сейчас? Используйте приложение‑аутентификатор.» Убедитесь, что recovery‑коды работают даже при потере устройства passkey.
Recovery‑коды: создание, хранение и регенерация
Recovery‑коды — это «сломать стекло» вариант, когда MFA не срабатывает: потерян телефон, приложение‑аутентификатор удалено или нет доступа к passkey. Это запасные ключи, не метод для ежедневного входа. Показывайте их сразу после успешной регистрации MFA и ясно говорите, что это единственный момент для сохранения.
Держите набор небольшим, чтобы люди действительно его сохранили. Десять одноразовых кодов — распространённый выбор для прототипа: достаточно для нескольких плохих дней и не превращается в длинный список, который игнорируют. Предложите копирование и скачивание, но требуйте сильной повторной проверки (пароль или текущий MFA) перед показом или регенерацией кодов.
Самая большая ошибка — хранить recovery‑коды в открытом виде. Храните только хеши (как пароли) и ведите понятный учёт использованных/неиспользованных кодов, чтобы каждый код работал один раз и «сгорал» после использования.
Безопасная модель хранения проста: сгенерируйте 8–10 случайных кодов, сохраните каждый как хеш плюс used_at (null до использования), ограничьте частоту попыток и временно блокируйте форму восстановления после повторных неудач, и логируйте использование recovery‑кодов как событие безопасности.
Регенерация должна быть жёсткой. При создании новых кодов немедленно инвалидируйте все старые, даже неиспользованные. Ясно предупреждайте: «Ваши предыдущие recovery‑коды перестанут работать сейчас.» Для большей безопасности разрешайте регенерацию только после сильной проверки (текущий MFA или недавно подтверждённый вход), чтобы злоумышленник с украденным паролем не мог тихо заменить коды.
Развёртывание MFA по фазам с ясными путями возврата
Попытка форс‑включить MFA одним переключателем обычно создаёт волну блокировок. Фазовый развёртывание снижает риск и показывает, где реальные пользователи застревают.
План фаз, подходящий для большинства небольших приложений:
- Опционально: предлагайте пользователям включить MFA после входа с ясной кнопкой «пропустить».
- Обязательно для админов и персонала: сначала защитите самые рисковые аккаунты.
- Обязательно для всех: только после того, как регистрация и восстановление станут рутинными и надёжными.
- Step‑up only: используйте MFA только для рискованных операций (смена почты, экспорт данных, просмотр биллинга), даже если сам вход остаётся только по паролю.
Каждая фаза нуждается в безопасном фолбэке, иначе поддержка завалит тикетами. Стремитесь иметь как минимум два пути обратно: самообслуживание и человек в поддержке.
Пути возврата, которые предотвращают блокировки
Спланируйте их до начала принудительного включения. Recovery‑коды — минимум. Дополнительный запасной фактор тоже помогает (TOTP плюс passkey или два passkey). Если предлагаете сброс через поддержку, определите чёткие проверки личности и период охлаждения перед удалением MFA. Небольшой льготный период после регистрации может снизить ложные блокировки, но держите его узким (например, «один пропуск»), чтобы не превратить его в постоянный обход.
Фичи‑флаги и коммуникация
Используйте feature flag, чтобы сначала раскатить на внутренних аккаунтах, затем на маленьких когортах (5%, 20%, 50%). Следите за процентом завершённых регистраций, частотой ошибок при вызовах MFA и тикетами «не могу получить доступ».
Сообщите пользователям, что меняется и что делать, если они потеряют доступ. Короткое внутри‑приложенное сообщение лучше длинного анонса: «На следующей неделе вас попросят ввести дополнительный код. Сохраните recovery‑коды сейчас.»
Делайте сбросы и изменения аккаунта безопасными для MFA
Проще всего обойти MFA, пробежать мимо него через изменения аккаунта. Относитесь к сбросам и редактированию профиля как к событию безопасности, а не простому обновлению формы.
Сброс пароля не должен отключать MFA
Сброс пароля дружелюбен к злоумышленникам, потому что почтовые ящики компрометируются. После успешного сброса сохраняйте MFA включённым и требуйте step‑up проверки при следующем входе. Если вы позволяете сброс MFA, делайте это отдельным действием, требующим MFA‑вызова (или recovery‑кода) после установки нового пароля.
Хорошее правило: смена пароля может помочь пользователю восстановить доступ, но не должна давать право убрать MFA.
Защищайте рискованные изменения шагом подтверждения
Некоторые изменения всегда должны требовать «доказать, что это действительно вы»: смена почты, добавление нового устройства, удаление/замена MFA, смена номера телефона (если SMS используется как запасной), и обновление платёжных реквизитов.
Если пользователь меняет почту, отправьте подтверждение на старую почту и сохраняйте старую почту активной до подтверждения. Если старая почта недоступна, требуйте recovery‑коды и короткую проверку поддержки.
Сессии, запомненные устройства и токены
«Запомнить это устройство» допустимо, но ограниченно. Устанавливайте явные сроки (обычно 14–30 дней), требуйте повторной аутентификации для рискованных операций даже на запомненных устройствах и делайте отзыв сессий предсказуемым: глобальный выход после смены пароля, повторная проверка или отзыв сессий при включении/замене MFA, и простой список «активных сессий» с кнопкой отзыва.
Для API‑токенов и интеграций решите, привязаны ли они к пользовательской сессии (тогда MFA должен ограничивать создание и изменение области действия) или это долгоживущие ключи (тогда полагайтесь на узкие права, срок жизни и ротацию, а не на MFA для каждого вызова).
Обычные ошибки, которые вызывают блокировки и шквал обращений
Большинство проблем с MFA не в математике. Они происходят потому, что пути «а что если я не могу войти?» не были доведены до конца.
Ошибка 1: Включение MFA до реального восстановления
Команды выкатывают запрос MFA, но оставляют recovery‑коды не протестированными, труднонаходимыми или сломанными на мобильных. В результате — мгновенные блокировки.
Перед переключением тестируйте восстановление end‑to‑end с новым аккаунтом и сценарием «потерял телефон»: сгенерируйте коды, используйте один, регенерируйте и убедитесь, что старые коды больше не работают.
Ошибка 2: Обращение с секретами как с обычными данными
Сеансы TOTP‑секретов и recovery‑кодов — не как имя пользователя. Если хранить их в открытом виде, копировать в логи или снова показывать, одна утечка превращается в захват аккаунтов.
Храните только необходимое, защищайте как пароль и никогда не показывайте recovery‑коды снова после настройки. Если пользователю нужны коды — пусть регенерирует их.
Ошибка 3: «Поддержка просто обходит это»
Ручной обход MFA кажется полезным, пока не станет самым простым путём в аккаунты. Если нужен обход, делайте его с лимитом по времени, требуйте проверки и оставляйте аудиторный след для ревью.
Ошибка 4: Слабая обработка TOTP
Проблемы TOTP часто из‑за сдвига часов, повторного использования и отсутствия rate‑лимитов. Принятие того же кода дважды или слишком широкое окно времени облегчает брутфорс и реплей.
Держите всё просто: разрешите небольшое окно времени, но блокируйте повторное использование кода в этом окне, ограничьте попытки, используйте временные блокировки (не постоянные «кирпичи») и показывайте понятные ошибки для «неверно» и «истёк срок».
Ошибка 5: Ожидание, что passkeys одинаково работают везде
Passkeys могут не сработать из‑за смены устройств, различий в поддержке браузеров или потому, что у пользователей нет синхронизированных учётных данных. Если вы требуете passkeys и не даёте запасной путь, вы запертите людей.
Держите ясный фолбэк (TOTP или recovery‑коды) и тестируйте на хотя бы одном iOS‑устройстве, одном Android и настольном браузере.
Короткий чек‑лист перед выпуском MFA
Одна скучная привычка спасает вас позже: убедитесь, что вы видите, что происходит, и можете быстро откатить изменения.
Проверки перед запуском (чтобы можно было быстро восстановиться)
Подтвердите, что можете откатить изменение MFA (feature flag, конфиг‑переключатель или быстрый деплой). Включите аудит логов для ключевых событий: enroll, verify, fail, lockout, использование recovery‑кода и disable. Сделайте бэкап таблицы пользователей (и любых связанных таблиц MFA) и потренируйтесь восстанавливать безопасную копию. Убедитесь, что трекинг ошибок ловит ошибки аутентификации с достаточной информацией для дебага без логирования секретов или кодов. Протестируйте отзыв сессий так, чтобы при изменении настроек MFA старые сессии проверялись или выходили.
Затем протестируйте пользовательские сценарии end‑to‑end. Не останавливайтесь на «код принят». Пройдите весь путь до первого экрана после входа.
Пользовательские сценарии и проверки безопасности
Разыграйте небольшой набор сценариев:
- Новый пользователь регистрирует MFA, затем входит на втором устройстве.
- Существующий пользователь включает MFA, выходит, затем заходит снова с запомненного устройства включённого и выключенного.
- Потерянный телефон: recovery‑код работает один раз, затем пользователь регенерирует коды и повторно настраивает фактор.
- Смена почты и сброс пароля требуют MFA (или безопасного step‑up) перед применением.
- Сопротивляемость злоупотреблениям: rate‑лимиты на попытки пароля и кода MFA, временные блокировки, которые не калечат аккаунт.
Подготовьтесь к первому тикету поддержки простым сценарием: что спросить, что проверить в логах и когда эскалировать.
Пример развёртывания для простого прототипа
Представьте небольшой SaaS‑прототип: вход по email/паролю и админская часть для биллинга, управления пользователями и инструментов поддержки. Вы хотите лучше защититься, но не можете рисковать блокировками.
Начните с защиты самых рискованных аккаунтов (админов), затем расширяйтесь до всех, когда поток станет рутинным и надёжным.
Фаза 1: Опциональный TOTP для админов
Включите TOTP только для админов и сделайте его опциональным сначала. Поместите запрос в настройках админа, а не в середине срочного входа.
Простая настройка: админ регистрирует TOTP, приложение показывает recovery‑коды один раз, админ подтверждает один TOTP‑код, и при следующем входе просят пароль плюс TOTP. Если TOTP не сработал — recovery‑код допускает вход.
Убедитесь, что всегда есть путь назад. Если админ не может завершить MFA, он всё ещё должен иметь возможность войти по паролю и связаться с поддержкой (временно), вместо жёсткой блокировки.
Фаза 2: Passkeys для обычных пользователей, TOTP как запасной
Когда админы стабилизируются, предложите passkeys обычным пользователям как самый простой вариант. Оставьте TOTP как запасной для тех, кто не может использовать passkeys (старые устройства, общие компьютеры).
Разворачивайте осторожно: сначала предложите «Добавить passkey» после входа, потом позже сделайте MFA дефолтом для новых регистраций.
Реальная неудача, обработанная корректно
Пользователь теряет телефон и не может получить TOTP. Он входит по email/паролю, выбирает «Использовать recovery‑код» и попадает в систему. Сразу после этого вы предлагаете ему зарегистрировать новый passkey (или новый TOTP) и регенерировать recovery‑коды. Снимайте старый метод MFA только после подтверждения нового.
Следующие шаги и когда просить помощи
Если вы хотите MFA без сломанных входов, начните с короткого плана, которым поделится команда: кто получает MFA первым, как человек попадает в систему, если MFA не работает, и как выглядит успех (меньше рискованных входов, а не больше тикетов поддержки).
Проведите небольшой внутренний релиз, используя реальные аккаунты, реальные устройства и реальные условия (смена телефона, потеря телефона, сдвиг времени, приватный режим браузера). Держите пилот достаточно маленьким, чтобы вы могли просмотреть каждую ошибку и быстро её исправить.
Задокументируйте несколько вещей письменно прежде, чем переключать что‑то: область фазы 1, опции возврата, что логируется и просматривается, кто может сбрасывать или переопределять и какие доказательства нужны, и когда начнётся принудительное требование (и как пользователям об этом сообщат). После развёртывания следите за ранним трением. Всплески ошибок «неверный код» часто указывают на сдвиг времени, запутанный текст или пользователей, регистрирующих неверное устройство. Всплески использования recovery‑кодов могут означать, что passkey или TOTP не приживаются.
Ищите помощь, когда видите повторяющиеся блокировки, неочевидную ответственность за процесс сброса, или признаки, что ваша логика аутентификации хрупка (жёстко закодированные секреты, непоследовательные сессии или странные обходы). Если вы унаследовали AI‑сгенерированный прототип, FixMyMess (fixmymess.ai) может провести бесплатный аудит кода, чтобы выявить риски блокировок и конкретные места, где текущий поток аутентификации может обходить или ломать MFA до того, как вы его включите для всех.
Часто задаваемые вопросы
Куда вставить MFA в поток входа, чтобы не сломать аутентификацию?
Помещайте MFA после успешной первой проверки (пароль или OAuth), но до создания окончательной сессионной куки/токена. Считайте «полностью вошёл в систему» одним моментом, который включает MFA — так вы не получите полувходы, которые тяжело откатить при ошибках MFA.
Какие метрики измерять до и после добавления MFA?
Отслеживайте коэффициент успешных входов, отток по шагам (введён пароль, показан запрос кода, код принят), события блокировок, завершённые сбросы пароля и медианное время входа. Если эти показатели ухудшаются после внедрения, это признак трения или ошибок, а не просто «пользователи не любят безопасность».
Кому подключать MFA в прототипе первым?
Не навязывайте MFA всем сразу. Сначала требуйте его для аккаунтов с высоким риском: админы, доступ к биллингу и те, кто меняет настройки безопасности. Расширяйте охват, когда enrolment и восстановление станут надёжными и обращения в поддержку останутся низкими.
Что лучше использовать — TOTP или passkeys для прототипа?
TOTP выбирайте, если нужен предсказуемый доступ на разных устройствах и старых средах, особенно для админов и B2B. Passkeys — когда хотите максимально плавный вход на современных устройствах и готовы вложиться в надёжное восстановление, потому что при смене устройств и синхронизации часто возникают проблемы.
Как избежать блокировки пользователей при подключении MFA?
Отмечайте MFA как включённое только после того, как пользователь успешно подтвердит фактор в процессе регистрации (ввести код TOTP или завершить подтверждение passkey). Если флаг включён до проверки, можно попасть в цикл, где требуют MFA, но фактор не настроен.
Как безопасно хранить и управлять recovery‑кодами?
Показывайте коды восстановления сразу после успешной настройки MFA и объясняйте, что их нельзя будет просмотреть снова. Храните только хеши кодов, отмечайте каждую одноразовую операцию как использованную и аннулируйте старые коды при регенерации.
Как развернуть MFA без лавины обращений в поддержку?
Фазовый rollout безопаснее: сначала опционально, затем обязателен для админов/сотрудников, и только после этого — для всех. Обеспечьте минимум два пути возврата: коды восстановления плюс запасной фактор или поддержка с жёсткой верификацией и периодом ожидания.
Должен ли сброс пароля отключать MFA?
Не давайте сбросу пароля автоматически отключать MFA. После сброса парольной фазы MFA остаётся включённой и требуется при следующем входе. Удаление или замена MFA — отдельное рискованное действие, требующее MFA или recovery‑кода.
Что логировать, чтобы дебажить MFA без утечки секретов?
Логируйте события: создание вызова MFA, неудачная проверка, использование recovery‑кода и отключение MFA вместе с user ID, временной меткой, IP и user agent. Никогда не пишите в лог TOTP-коды, секреты, сырые recovery‑коды или полные OAuth‑токены.
Когда стоит просить помощь по MFA в AI‑сгенерированном прототипе?
Повторяющиеся блокировки обычно означают хрупкую логику аутентификации, смешанные сессии/токены или незаконченные пути восстановления. Если унаследовали AI‑сгенерированный прототип и логика аутентификации несогласованна, FixMyMess (fixmymess.ai) может провести бесплатный аудит кода, чтобы указать места, где MFA может быть обойдена, сломаться или заблокировать аккаунты.