ЧАСТИНА I: Як увійти
Ми припустимо, що ви вже знаєте, як створити HTML-форму для входу + пароль, яка розміщує значення сценарію на стороні сервера для аутентифікації. У поданих нижче розділах будуть розглянуті схеми для надійної практичної роботи та як уникнути найпоширеніших підводних каменів безпеки.
Для HTTPS чи ні до HTTPS?
Якщо з'єднання вже не захищено (тобто проходить тунель через HTTPS за допомогою SSL / TLS), ваші значення форми входу будуть надіслані в чіткому тексті, що дозволяє кожному підслуховуванню на лінії між браузером та веб-сервером зможе читати входи під час проходження наскрізь. Цей тип прослуховування проводять урядами, але загалом ми не будемо звертатися до "власних" проводів, крім того, щоб сказати це: Просто використовуйте HTTPS.
По суті, єдиним практичним способом захисту від прослуховування прослуховування / нюху пакетів під час входу є використання HTTPS або іншої схеми шифрування на основі сертифікатів (наприклад, TLS ) або перевіреної та перевіреної схеми реагування на виклики (наприклад, Diffie-Hellman -на основі СРП). Будь-який інший метод може бути легко обійти підслуховувачем.
Звичайно, якщо ви хочете зробити трохи непрактичним, ви можете також застосувати певну форму двофакторної схеми аутентифікації (наприклад, додаток Google Authenticator, фізичну кодову книгу «стилю холодної війни» або ключовий ключ генератора RSA). Якщо застосувати правильно, це може працювати навіть при незахищеному з'єднанні, але важко уявити, що розробник буде готовий реалізувати двофакторний auth, але не SSL.
(Не варто) Робіть власне шифрування / хешування JavaScript
Враховуючи визнану (хоча і зараз уникнуту ) вартість та технічні труднощі налаштування сертифіката SSL на вашому веб-сайті, деякі розробники спокушаються прокручувати власні схеми хешування або шифрування у веб-переглядачі, щоб уникнути передачі вхідних даних явного тексту через незахищений провід.
Хоча це шляхетна думка, вона по суті є марною (і може бути вадою безпеки ), якщо вона не поєднується з одним із перерахованих вище, тобто або забезпечує захист лінії сильним шифруванням, або використовуючи перевірений виклик-відповідь. механізм (якщо ви не знаєте, що це таке, просто знайте, що це один із найскладніших у доведенні, найскладніший у проектуванні та найскладніший для реалізації концепцій цифрової безпеки).
Хоча це правда, що хешування пароля може бути ефективним проти розкриття пароля , він уразливий для повторного нападу, атаки / викрадення людини-в-середині (якщо зловмисник може ввести кілька байт у вашу незахищену HTML-сторінку до того, як дістанеться до вашої браузер, вони можуть просто прокоментувати хешування в JavaScript) або жорстокі атаки (оскільки ви передаєте зловмиснику і ім'я користувача, і сіль, і хеш-пароль).
КАПЧАСИ проти людства
CAPTCHA призначений для запобігання одній конкретній категорії атаки: автоматизованому словнику / грубій спробі та помилки без будь-якого оператора. Немає сумнівів, що це реальна загроза, однак, існують способи поводження з нею без проблем, які не потребують CAPTCHA, спеціально правильно розроблених схем дроселювання входу на стороні сервера - про це ми поговоримо пізніше.
Знайте, що реалізації CAPTCHA створюються не так; вони часто не вирішуються людиною, більшість з них насправді неефективні проти ботів, всі вони неефективні проти дешевої робочої сили третього світу (згідно з OWASP , поточна ставка роботи становить 12 доларів за 500 тестів), і деякі реалізації можуть бути технічно незаконні в деяких країнах (див. чіт-лист OWASP Authentication ). Якщо вам потрібно використовувати CAPTCHA, використовуйте reCAPTCHA від Google , оскільки це за визначенням важко OCR (оскільки він використовує вже скановані книги, що не відповідають класифікації OCR), і дуже намагається бути зручним для користувачів.
Особисто я вважаю, що CAPTCHAS дратує, і використовую їх лише в крайньому випадку, коли користувач не вдається зареєструватися в декілька разів, і затримки вимкнення прискорюються. Це станеться досить рідко, щоб бути прийнятним, і це зміцнює систему в цілому.
Зберігання паролів / перевірка логінів
Це, нарешті, може бути загальновідомим після всіх широко розрекламованих хак та витоків даних користувачів, які ми спостерігали останніми роками, але слід сказати: не зберігайте паролі у чіткому тексті у вашій базі даних. Користувальницькі бази даних руйнуються, просочуються або збираються через інжекцію SQL, і якщо ви зберігаєте необроблені паролі в прямому тексті, це моментальна гра для безпеки вашого входу.
Отже, якщо ви не можете зберегти пароль, як перевірити правильність комбінації входу + пароля POSTed з форми входу? Відповідь є хешування, використовуючи функцію виведення ключа . Щоразу, коли створюється новий користувач або змінюється пароль, ви берете пароль і запускаєте його через KDF, наприклад, Argon2, bcrypt, scrypt або PBKDF2, перетворюючи пароль чіткого тексту ("правильнедоступне стаття") у довгу, випадкову вигляд рядок , що набагато безпечніше зберігати у вашій базі даних. Щоб перевірити логін, ви запускаєте ту саму функцію хешу на введеному паролі, цього разу передаючи сіль і порівнюючи отриману хеш-рядок зі значенням, збереженим у вашій базі даних. Argon2, bcrypt і scrypt зберігають сіль з хешем. Перегляньте цю статтю на sec.stackexchange для отримання більш детальної інформації.
Причина, якою використовується сіль, полягає в тому, що хешування саме по собі недостатньо - вам потрібно додати так звану сіль для захисту хешу від веселкових столів . Сіль ефективно запобігає збереженню двох паролів, які точно збігаються, як одне і те ж хеш-значення, запобігаючи скануванню всієї бази даних за один запуск, якщо зловмисник виконує атаку вгадування пароля.
Криптографічний хеш не повинен використовуватися для зберігання паролів, оскільки вибрані користувачем паролі недостатньо сильні (тобто зазвичай не містять достатньої кількості ентропії), і атака вгадування пароля може бути завершена за порівняно короткий час зловмисником, що має доступ до хешей. Ось чому використовуються KDF - вони ефективно "розтягують ключ" , а це означає, що кожен здогад про пароль, який нападник робить, викликає багаторазове повторення алгоритму хешу, наприклад, 10000 разів, що змушує зловмисника вгадувати пароль у 10000 разів повільніше.
Дані сесії - "Ви ввійшли як Павук69"
Після того, як сервер перевірив логін та пароль у вашій базі даних користувачів та знайшов відповідність, системі потрібен спосіб пам’ятати, що браузер був аутентифікований. Цей факт повинен коли-небудь зберігатися на стороні сервера в даних сеансу.
Якщо ви не знайомі з даними сеансу, ось як це працює: Один рядок, що генерується випадковим чином, зберігається у файлі cookie, що закінчується, і використовується для посилання на збір даних - дані сеансу - які зберігаються на сервері. Якщо ви використовуєте рамку MVC, це, безсумнівно, вже вдається.
Якщо це взагалі можливо, переконайтеся, що у файлі cookie сеансу встановлені захищені та встановлені прапорці HTTP-прапори, коли вони надсилаються до браузера. Прапор HttpOnly забезпечує певний захист від зчитування файлу cookie через атаку XSS. Захищений прапор гарантує, що файл cookie буде відправлений назад лише через HTTPS, а отже, захищає від атак мережевих нюхів. Значення файлу cookie не повинно бути передбачуваним. Якщо представлено файл cookie, на який посилається на неіснуючий сеанс, його значення слід негайно замінити, щоб запобігти фіксації сеансу .
ЧАСТИНА II: Як залишитись увійти в систему - сумнозвісний прапорець "Запам'ятати мене"
Постійні файли cookie (функція "запам'ятайте мене") - небезпечна зона; з одного боку, вони цілком такі ж безпечні, як і звичайні логіни, коли користувачі розуміють, як з ними поводитися; з іншого боку, вони становлять величезний ризик для безпеки недбалих користувачів, які можуть використовувати їх на загальнодоступних комп’ютерах і забути виходити з системи, а також можуть не знати, що таке куки браузера або як їх видалити.
Особисто мені подобаються стійкі входи для веб-сайтів, які я відвідую регулярно, але я знаю, як безпечно поводитися з ними. Якщо ви впевнені, що ваші користувачі знають те саме, ви можете використовувати стійкі входи з чистою совістю. Якщо ні - добре, тоді ви можете підписатись на філософію того, що користувачі, які недбало ставляться до своїх ідентифікаційних даних для входу, наклали це на себе, якщо вони зламаються. Це не так, як ми заходимо до будинків нашого користувача і відриваємо всі ті примітки, що викликають обличчя Post-It, із паролями, які вони також вишикували на краю своїх моніторів.
Звичайно, деякі системи не можуть дозволити собі зламати будь-які акаунти; для таких систем немає можливості виправдати наявність стійких логінів.
Якщо ви вирішили реалізувати постійні файли cookie для входу, це робиться так:
Спочатку знайдіть трохи часу, щоб прочитати статтю Ініціативи Paragon на цю тему. Вам потрібно буде підібрати купу елементів правильно, і стаття робить чудову роботу з пояснення кожного.
І лише щоб повторити одну з найпоширеніших підводних каменів, НЕ ЗБЕРІГАЙТЕ ПЕРСИСТИЦІЙНИЙ ВІДКЛЮЧЕНИЙ КОКІ (ЖИВОТНІ) У ВАШІЙ ДАТАБАЗІ, ТОЛЬКО МОЖЛИВО ЙОГО! Маркер для входу є еквівалентним паролем, тому якщо зловмисник потрапив у вашу базу даних, вони могли використовувати маркери для входу в будь-який обліковий запис, так само, як якщо б вони були чіткими комбінаціями входу-пароля. Тому використовуйте хешування (згідно з https://security.stackexchange.com/a/63438/5002 слабкий хеш буде цілком чудово для цієї мети) під час зберігання стійких маркерів для входу.
ЧАСТИНА III: Використання таємних запитань
Не застосовуйте "таємні запитання" . Функція "секретних питань" - це антиблокувальна безпека. Прочитайте документ за посиланням № 4 зі списку ОБОВ'ЯЗКОВО. Ви можете запитати Сару Пейлін про цю, після її Yahoo! Обліковий запис електронної пошти був зламаний під час попередньої президентської кампанії, оскільки відповідь на її питання безпеки полягала у ...
Навіть із запитаннями, визначеними користувачем, велика ймовірність, що більшість користувачів обирає будь-яке:
«Стандартне» таємне питання, як дівоче прізвище матері чи улюблений вихованець
Простий фрагмент, який кожен може підняти зі свого блогу, профілю LinkedIn чи подібного
Будь-яке питання, на який простіше відповісти, ніж вгадувати їх пароль. Що для будь-якого гідного пароля - це кожне питання, яке ви можете собі уявити
На закінчення, питання безпеки за своєю суттю є незахищеними практично у всіх їх формах та варіаціях, і їх не слід використовувати в схемі аутентифікації з будь-якої причини.
Справжня причина, чому питання безпеки навіть існують у дикій природі, полягає в тому, що вони зручно економить вартість декількох дзвінків підтримки від користувачів, які не можуть отримати доступ до своєї електронної пошти, щоб отримати код повторної активації. Це за рахунок безпеки та репутації Сари Пейлін. Варто? Напевно, ні.
ЧАСТИНА IV: Функція забутого пароля
Я вже згадував, чому ви ніколи не повинні використовувати питання безпеки для обробки забутих / втрачених паролів користувачів; Зрозуміло, що ніколи не слід надсилати електронною поштою користувачам їхні фактичні паролі. У цьому полі є щонайменше дві ще занадто поширені підводні камені:
Не скидайте забутий пароль на автогенерований надійний пароль - такі паролі, як відомо, важко запам’ятати, а це означає, що користувач повинен або змінити його, або записати - скажімо, на яскраво-жовтому Пості-Це на краю свого монітора. Замість того, щоб встановлювати новий пароль, просто дозвольте користувачам вибирати новий відразу - що саме вони хочуть зробити. (Виняток із цього може бути, якщо користувачі загалом використовують диспетчер паролів для зберігання / управління паролями, які зазвичай неможливо запам'ятати, не записуючи їх).
Завжди хешуйте загублений код / маркер пароля в базі даних. ПРОТИ , цей код є ще одним прикладом еквівалентного пароля, тому його ОБОВ'ЯЗКОВО хеширувати у випадку, якщо зловмисник потрапив у вашу базу даних. Коли запитується загублений пароль, надішліть код простого тексту на електронну адресу користувача, а потім хеште його, збережіть хеш у вашій базі даних - та викиньте оригінал . Так само, як пароль або постійний маркер входу.
Остаточне зауваження: завжди переконайтеся, що ваш інтерфейс для введення «коду втраченого пароля» принаймні настільки ж безпечний, як і сама форма для входу, або зловмисник просто використовуватиме це для отримання доступу. Переконайтеся, що ви генеруєте дуже довгі «загублені коди паролів» (наприклад, 16 буквено-цифрових символів, залежних від регістру) - це вдалий початок, але подумайте про додавання тієї самої схеми дроселювання, що і для самої форми входу.
ЧАСТИНА V: Перевірка міцності пароля
По-перше, вам потрібно прочитати цю невелику статтю для перевірки реальності: 500 найпоширеніших паролів
Гаразд, тому, можливо, цей список не є канонічним списком найпоширеніших паролів у будь-якій системі будь-де , але це хороший показник того, як погано люди вибиратимуть свої паролі, коли не буде застосовано примусової політики. Крім того, цей список виглядає страхітливо близьким до домашнього, коли ви порівнюєте його з загальнодоступними аналізами нещодавно вкрадених паролів.
Отже: Без мінімальних вимог щодо надійності пароля 2% користувачів використовують один із 20 найпоширеніших паролів. Значення: якщо зловмисник отримує всього 20 спроб, 1 з 50 облікових записів на вашому веб-сайті буде складно.
Для запобігання цьому потрібно обчислити ентропію пароля, а потім застосувати поріг. Спеціальна публікація Національного інституту стандартів та технологій (NIST) 800-63 має набір дуже хороших пропозицій. У поєднанні з аналізом розкладки словника та клавіатури (наприклад, "qwertyuiop" - це неправильний пароль), можна відхилити 99% усіх погано вибраних паролів на рівні 18 біт ентропії. Просто обчислити міцність пароля та показати користувачеві візуальний вимірювач міцності - це добре, але недостатньо. Якщо це не буде застосовано, багато користувачів, швидше за все, ігнорують це.
І для того, щоб освіжити зручність паролів з високою ентропією, настійно рекомендується пароль Randall Munroe xkcd .
Використовуйте API Troy Hunt's I Been Pwned для перевірки паролів користувачів на порушення паролів, порушених при порушенні публічних даних.
ЧАСТИНА VI: Багато іншого - Або: Запобігання спробам швидкого вогню
Спочатку подивіться на цифри: швидкість відновлення пароля - як довго буде стояти ваш пароль
Якщо у вас немає часу переглядати таблиці за цим посиланням, ось їх список:
Він займає практично немає часу , щоб зламати слабкий пароль, навіть якщо ви розтріскування його з абаки
Він займає практично немає часу , щоб зламати буквено - цифровий пароль 9 символів , якщо воно чутливо до регістру
Він займає практично немає часу , щоб зламати заплутану, символи-і-букву-і-номер, верхні і малі літери пароль , якщо він довжиною менше 8 символів (настільний ПК можна знайти все простір ключів до 7 символів в питанні днів або навіть годин)
Однак знадобиться непомітна кількість часу, щоб зламати навіть 6-символьний пароль, якби ви обмежилися однією спробою в секунду!
То що ми можемо дізнатися з цих чисел? Ну, багато, але ми можемо зосередитись на найважливішій частині: факт запобігання великій кількості послідовних спроб входу у швидкий вогонь (тобто груба атака) насправді не так складно. Але запобігти правильному не так просто, як здається.
Взагалі кажучи, у вас є три варіанти, які ефективні проти жорстоких атак (і атак на словник, але оскільки ви вже застосовуєте чітку політику паролів, вони не повинні бути проблемою) :
Подаруйте CAPTCHA після N невдалих спроб (дратує як пекло і часто малоефективне - але я тут повторююсь)
Блокування облікових записів та необхідність підтвердження електронної пошти після N спроб (це DoS- атака, що чекає)
І нарешті, затримка входу : тобто встановлення часової затримки між спробами після N невдалих спроб (так, DoS-атаки все ще можливі, але принаймні вони набагато рідше і набагато складніше зняти).
Найкраща практика № 1: коротка затримка в часі, яка збільшується з кількістю невдалих спроб, наприклад:
- 1 невдала спроба = без затримки
- 2 невдалі спроби = затримка на 2 секунди
- 3 невдалі спроби = 4 секунди затримки
- 4 невдалі спроби = 8 секунд затримки
- 5 невдалих спроб = затримка на 16 сек
- тощо.
Напад, що атакує цю схему, був би дуже недоцільним, оскільки отриманий час блокування дещо більший, ніж сума попередніх епізодів.
Для уточнення: затримка не є затримкою до повернення відповіді в браузер. Це скоріше, як тайм-аут або вогнетривкий період, протягом якого спроби входу в конкретний обліковий запис або з певної IP-адреси взагалі не приймаються і не оцінюються. Тобто, правильні облікові дані не повернуться при успішному вході, а неправильні облікові дані не спровокують збільшення затримки.
Найкраща практика № 2: Середня тривалість затримки, яка набирає чинності після N невдалих спроб, наприклад:
- 1-4 невдалі спроби = без затримки
- 5 невдалих спроб = затримка 15-30 хв
Напад, що атакує цю схему, був би непрактичним, але, безумовно, можливим. Крім того, може бути доречно зазначити, що така велика затримка може дуже дратувати законного користувача. Незабутні користувачі вас не сподобаються.
Найкраща практика №3: Комбінування двох підходів - або фіксований, короткий затримок у часі, який набуває чинності після N невдалих спроб, наприклад:
- 1-4 невдалі спроби = без затримки
- 5+ невдалих спроб = 20 секунд затримки
Або збільшення затримки з фіксованою верхньою межею, наприклад:
- 1 невдала спроба = затримка на 5 сек
- 2 невдалі спроби = затримка на 15 сек
- 3+ невдалих спроб = затримка на 45 сек
Ця остаточна схема була взята із пропозицій щодо найкращих практик OWASP (посилання 1 зі списку ОБОВ'ЯЗКОВОГО ПРОЧИТАННЯ) і повинна вважатися найкращою практикою, навіть якщо вона, безумовно, є на обмежувальній стороні.
Однак, як правило, я б сказав: чим сильніше ваша політика щодо паролів, тим менше вам доведеться клопотати користувачів із затримками. Якщо вам потрібні сильні (буквені і цифрові символи + необхідні цифри та символи) 9+ паролів символів, ви можете дати користувачам 2-4 спроби паролі, що не затримуються, перш ніж активувати дроселювання.
DoS, що атакує цю остаточну схему відключення входу, була б дуже недоцільною. І, як остаточний штрих, завжди дозволяйте постійним реєстраціям (cookie) (та / або підтвердженій CAPTCHA формою входу), тому законні користувачі навіть не затримуються, поки атака триває . Таким чином, сама непрактична атака DoS стає надзвичайно непрактичною атакою.
Крім того, є сенс робити більш агресивне придушення на акаунтах адміністратора, оскільки це найпривабливіші точки входу
ЧАСТИНА VII: Поширені напади грубої сили
Як і в сторону, більш просунуті зловмисники намагатимуться обійти вхід, "поширюючи свою діяльність":
Поширення спроб на ботнеті запобігти позначенню IP-адреси
Замість того, щоб вибрати одного користувача та спробувати 50 000 найпоширеніших паролів (які вони не можуть через наше переключення), вони підберуть НАЙЩОШИЙ звичайний пароль та спробують його проти 50 000 користувачів. Таким чином, вони не лише обробляють максимально можливі спроби, такі як CAPTCHA та увімкнення входу, і їх шанс на успіх збільшується, оскільки найпоширеніший пароль №1 набагато частіше, ніж число 49,995
Розміщення запитів на вхід для кожного облікового запису користувача, скажімо, за 30 секунд один від одного, щоб проникнути під радари
Тут найкращою практикою буде реєстрація кількості невдалих реєстрацій, загальносистемних , та використання середнього показника частоти невдалого входу на ваш сайт як основу для верхньої межі, яку ви потім встановлюєте для всіх користувачів.
Занадто абстрактно? Дозвольте перефразувати:
Скажімо, на вашому веб-сайті за останні 3 місяці було в середньому 120 поганих входів. Використовуючи це (середнє значення), ваша система може встановити глобальний ліміт у 3 рази більше - тобто. 360 невдалих спроб протягом 24 годин. Тоді, якщо загальна кількість невдалих спроб у всіх облікових записах перевищує це число протягом одного дня (а ще краще, слідкуйте за швидкістю прискорення та спрацьовуйте за розрахунковим порогом), це активує загальне системне зменшення входу - це означає короткі затримки для ВСІХ користувачів (все ж, за винятком реєстрації файлів cookie та / або резервного входу CAPTCHA).
Я також розмістив запитання з більш детальною інформацією та дуже хорошим обговоренням того, як уникнути хитромудрих підводних каменів у відбитті розподілених нападів грубої сили
ЧАСТИНА VIII: Двофакторні аутентифікація та аутентифікація
Посвідчення даних можуть бути поставлені під загрозу, як через подвиги, записування та втрату паролів, ноутбуки з викраденими ключами, так і користувачі, що вводять логіни на фішинг-сайти. Вхід може бути додатково захищений двофакторною аутентифікацією, яка використовує позадіапазонні фактори, такі як коди одноразового використання, отримані під час телефонного дзвінка, SMS-повідомлення, програми чи ключа. Кілька постачальників пропонують послуги двофакторної аутентифікації.
Автентифікацію можна повністю делегувати службі одноразового входу, де інший постачальник обробляє збір облікових даних. Це підштовхує проблему до надійної третьої сторони. Google і Twitter надають послуги SSO на основі стандартів, а Facebook - аналогічне фірмове рішення.
ОБОВ'ЯЗКОВО читати посилання про веб-аутентифікацію
- Посібник OWASP з аутентифікації / шпаргалка для аутентифікації OWASP
- Документи та недоліки аутентифікації клієнтів в Інтернеті (дуже читабельний дослідницький документ MIT)
- Вікіпедія: кукі HTTP
- Питання особистого знання для резервної аутентифікації: питання безпеки в епоху Facebook (дуже читабельний дослідний документ Берклі)