• Что можно приготовить из кальмаров: быстро и вкусно

    Привет. Меня зовут Саша Баранник. В Mail.Ru Group я руковожу отделом веб-разработки, состоящим из 15 сотрудников. Мы научились создавать сайты для десятков миллионов пользователей и спокойно справляемся с несколькими миллионами дневной аудитории. Сам я занимаюсь веб-разработкой около 20 лет, и последние 15 лет по работе программировать приходится преимущественно на PHP. Хотя возможности языка и подход к разработке за это время сильно изменились, понимание основных уязвимостей и умение от них защититься остаются ключевыми навыками любого разработчика.

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

    P. S. Книга длинная, поэтому перевод будет выкладываться несколькими статьями. Итак, приступим…

    Ещё одна книга по безопасности в PHP? Есть много способов начать книгу про безопасность в PHP. К сожалению, я не читал ни одной из них, так что придётся разобраться с этим в процессе написания. Пожалуй, я начну с самого основного и буду надеяться, что всё получится.

    Если рассмотреть абстрактное веб-приложение, запущенное в онлайне компанией Х, то можно предположить, что оно содержит ряд компонентов, которые, если их взломать, способны нанести существенный вред. Какой, например?

  • Вред пользователям: получение доступа к электронной почте, паролям, персональным данным, реквизитам банковских карт, деловым тайнам, спискам контактов, истории транзакций и глубоко охраняемым секретам (вроде того, что кто-то назвал свою собаку Блёсткой). Утечка этих данных вредит пользователям (частным лицам и компаниям). Навредить могут также веб-приложения, неправильно применяющие подобные данные, и узлы, которые используют доверие пользователей в своих интересах.
  • Вред самой компании X: из-за причинённого пользователям ущерба ухудшается репутация, приходится выплачивать компенсации, теряется важная деловая информация, возникают дополнительные расходы - на инфраструктуру, улучшение безопасности, ликвидацию последствий, судебные издержки, крупные пособия увольняемым топ-менеджерам и т. д.
  • Я остановлюсь на этих двух категориях, так как они включают в себя большинство неприятностей, которые должна предотвращать система безопасности веб-приложения. Все компании, столкнувшиеся с серьёзными нарушениями безопасности, быстренько пишут в пресс-релизах и на сайтах, как они трепетно к ней относятся. Так что советую вам заранее всем сердцем прочувствовать важность этой проблемы, до того как вы столкнётесь с ней на практике.

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

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

    Поскольку система безопасности веб-приложения должна защищать пользователей, которые доверяют сервисам приложения, необходимо знать ответы на вопросы:

  • Кто хочет нас атаковать?
  • Как они могут нас атаковать?
  • Как мы можем их остановить?
  • Кто хочет нас атаковать? Ответ на первый вопрос очень прост: все и всё. Да, вся Вселенная хочет вас проучить. Пацан с разогнанным компом, на котором запущен Kali Linux? Вероятно, он вас уже атаковал. Подозрительный мужчина, любящий вставлять палки в колёса? Вероятно, он уже нанял кого-то, чтобы вас атаковали. Доверенный REST API, через который вы ежечасно получаете данные? Вероятно, он был хакнут ещё месяц назад, чтобы подкидывать вам заражённые данные. Даже я могу атаковать вас! Так что не нужно слепо верить этой книге. Считайте, что я лгу. И найдите программиста, который выведет меня на чистую воду и разоблачит мои вредные советы. С другой стороны, может быть, он тоже собирается вас хакнуть…

    Смысл этой паранойи в том, чтобы было проще мысленно разделить на категории всё, что взаимодействует с вашим веб-приложением («Пользователь», «Хакер», «База данных», «Ненадёжный ввод», «Менеджер», «REST API»), а затем присваивать каждой категории индекс доверия. Очевидно, что «Хакеру» доверять нельзя, но что насчёт «Базы данных»? «Ненадёжный ввод» получил своё название не просто так, но вы действительно станете фильтровать пост в блоге, полученный из доверенной Atom-ленты своего коллеги?

    Те, кто серьёзно занимаются взломом веб-приложений, учатся использовать преимущество такого мышления, чаще атакуя не уязвимые источники данных, а доверенные, которые с меньшей вероятностью будут иметь хорошую систему защиты. Это не случайное решение: в реальной жизни субъекты с более высоким индексом доверия вызывают меньше подозрения. Именно на такие источники данных я в первую очередь обращаю внимание при анализе приложения.

    Вернёмся к «Базам данных». Если предположить, что хакер сможет получить доступ к базе (а мы, параноики, всегда это предполагаем), то ей никогда нельзя доверять. Большинство приложений доверяют базам безо всяких вопросов. Снаружи веб-приложение выглядит единым целым, но внутри оно представляет из себя систему из отдельных компонентов, обменивающихся данными. Если считать все эти компоненты доверенными, то при взломе одного из них быстро окажутся скомпрометированы и все остальные. Такие катастрофические проблемы в безопасности не получится решить фразой «Если база взломана, то мы всё равно проиграли». Вы можете так сказать, но вовсе не факт, что вам придётся это делать, если изначально не будете доверять базе и действовать соответствующе!

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

    Если вы используете источники данных без проверки того, полностью ли безопасны эти данные и подходят ли они для использования, то вы потенциально открыты для атаки. Также необходимо проверять, что полученные данные соответствуют данным, которые вы отправляете. Если данные не сделаны полностью безопасными для вывода, то у вас тоже будут серьёзные проблемы. Всё это можно выразить в виде правила для PHP «Проверяйте ввод; экранируйте вывод».

    Это очевидные источники данных, которые мы должны как-то контролировать. Также к источникам могут относиться хранилища на стороне клиента. Например, большинство приложений распознают пользователей, присваивая им уникальные ID сессии, которые могут храниться в куках. Если атакующий заполучит значение из куки, то он может выдать себя за другого пользователя. И хотя мы можем уменьшить некоторые риски, связанные с перехватом или подделкой пользовательских данных, гарантировать физическую безопасность компьютера пользователя мы не в состоянии. Мы даже не можем гарантировать, что юзеры сочтут «123456» глупейшим паролем после «password». Дополнительную пикантность придаёт факт, что сегодня куки не единственный вид хранилища на стороне пользователя.

    Ещё один риск, часто упускаемый из виду, касается целостности вашего исходного кода. В PHP становится всё популярнее разработка приложений на основе большого количества слабо связанных друг с другом библиотек, модулей и пакетов для фреймворков. Многие из них скачиваются из общественных репозиториев, таких как Github, ставятся с помощью установщиков пакетов вроде Composer и его веб-компаньона Packagist.org. Поэтому безопасность исходного кода полностью зависит от безопасности всех этих сторонних сервисов и компонентов. Если окажется скомпрометирован Github, то, скорее всего, он будет использован для раздачи кода с вредоносной добавкой. Если Packagist.org - то атакующий сможет перенаправлять запросы пакетов на свои, вредоносные пакеты.

    На сегодняшний день Composer и Packagist.org подвержены известным уязвимостям в определении зависимостей и раздаче пакетов, так что всегда проверяйте всё дважды в рабочем окружении и сверяйте источник получения всех пакетов с Packagist.org.

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

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

    Базовые принципы безопасности При разработке средств защиты их эффективность можно оценивать с помощью следующих соображений. Некоторые я уже приводил выше.
  • Не верьте никому и ничему.
  • Всегда предполагайте худший сценарий.
  • Применяйте многоуровневую защиту (Defence-in-Depth).
  • Придерживайтесь принципа «чем проще, тем лучше» (Keep It Simple Stupid, KISS).
  • Придерживайтесь принципа «минимальных привилегий».
  • Злоумышленники чуют неясность.
  • Читайте документацию (RTFM), но никогда ей не доверяйте.
  • Если это не тестировали, то это не работает.
  • Это всегда ваша ошибка!
  • Давайте кратко пробежимся по всем пунктам.1. Не верьте никому и ничему Как уже говорилось выше, правильная позиция - предполагать, что всё и все, с чем взаимодействует ваше веб-приложение, хотят его взломать. В том числе другие компоненты или слои приложения, которые нужны для обработки запросов. Всё и все. Без исключений.2. Всегда предполагайте худший сценарий У многих систем безопасности есть общее свойство: не важно, насколько хорошо они сделаны, каждая может быть пробита. Если вы будете это учитывать, то быстро поймёте преимущество второго пункта. Ориентирование на худший сценарий поможет оценить обширность и степень вредоносности атаки. А если она и впрямь произойдёт, то, возможно, вам удастся уменьшить неприятные последствия благодаря дополнительным средствам защиты и изменениям в архитектуре. Быть может, традиционное решение, которое вы используете, уже заменили чем-то лучшим?3. Применяйте многоуровневую защиту (Defence-in-Depth) Многоуровневая защита заимствована из военной науки, потому что люди давно сообразили, что многочисленные стены, мешки с песком, техника, бронежилеты и фляжки, прикрывающие жизненно важные органы от вражеских пуль и клинков, - правильный подход к безопасности. Никогда не знаешь, что из перечисленного не защитит, и нужно сделать так, чтобы несколько уровней защиты позволяли полагаться не на одно лишь полевое укрепление или боевой порядок. Конечно, дело не только в одиночных отказах. Представьте себе нападающего, который залез на гигантскую средневековую стену по лестнице и обнаружил, что за ней ещё одна стена, откуда его осыпают стрелами. Хакеры будут чувствовать себя так же.4. Придерживайтесь принципа «чем проще, тем лучше» (Keep It Simple Stupid, KISS) Лучшие средства защиты всегда просты. Их просто разрабатывать, внедрять, понимать, использовать и тестировать. Простота уменьшает количество ошибок, стимулирует правильную работу приложения и облегчает внедрение даже в наиболее сложных и недружелюбных окружениях.5. Придерживайтесь принципа «минимальных привилегий» Каждый участник обмена информацией (пользователь, процесс, программа) должен иметь только те права доступа, которые ему необходимы для выполнения своих функций.6. Злоумышленники чуют неясность «Безопасность через неясность » основана на предположении, что если вы используете защиту А и никому не говорите, что это, как она работает и существует ли вообще, то это волшебным образом помогает вам, потому что атакующие оказываются в растерянности. На самом деле это даёт лишь небольшое преимущество. Зачастую опытный злоумышленник способен вычислить предпринятые вами меры, поэтому нужно использовать и явные средства защиты. Тех, кто излишне уверен в том, что неясная защита отменяет необходимость в защите реальной, нужно специально наказывать ради избавления от иллюзий.7. Читайте документацию (RTFM), но никогда ей не доверяйте Руководство по PHP - это Библия. Конечно, оно не было написано Летающим Макаронным Монстром , так что формально может содержать какое-то количество полуправды, недочётов, неверных толкований или ошибок, пока ещё не замеченных или не исправленных. То же самое касается и Stack Overflow.

    Специализированные источники мудрости в сфере безопасности (ориентированные на PHP и не только) в целом дают более подробные знания. Ближе всего к Библии по безопасности в PHP находится сайт OWASP с предлагаемыми на нём статьями, руководствами и советами. Если на OWASP что-то не рекомендуется делать - никогда не делайте!

    8. Если это не тестировали, то это не работает Внедряя средства защиты, вы должны писать все необходимые для проверки работающие тесты. В том числе притворитесь, что вы хакер, по которому плачет тюрьма. Это может показаться надуманным, но знакомство с методами взлома веб-приложений - хорошая практика; вы узнаете о возможных уязвимостях, а ваша паранойя усилится. При этом необязательно рассказывать руководству о свежеприобретённой благодарности за взлом веб-приложения. Для выявления уязвимостей обязательно применяйте автоматизированные инструменты. Они полезны, но конечно же не заменяют качественное ревью кода и даже ручное тестирование приложения. Чем больше ресурсов вы потратите на тестирование, тем надёжнее будет ваше приложение.9. Это всегда ваша ошибка! Программисты привыкли считать, что уязвимости в системе безопасности будут находить разрозненными атаками, а их последствия незначительны.

    Например, утечки данных (хорошо задокументированный и широко распространённый вид взлома) часто рассматриваются как небольшие проблемы в безопасности, потому что они не влияют на пользователей напрямую. Однако утечка данных о версиях ПО, языках разработки, расположении исходного кода, о логике приложения и бизнес-логике, о структуре базы данных и прочих аспектах окружения веб-приложения и внутренних операций часто важна для успешной атаки.

    В то же время атаки на системы безопасности часто представляют собой комбинации атак. По отдельности они малозначимы, но при этом иногда открывают дорогу другим атакам. Например, для внедрения SQL-кода иногда требуется имя конкретного пользователя, которое можно получить с помощью атаки по времени (Timing Attack) против административного интерфейса, вместо куда более дорогого и заметного брутфорса. В свою очередь, внедрение SQL позволяет реализовать XSS-атаку на конкретный административный аккаунт, не привлекая внимания большим количеством подозрительных записей в логах.

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

    Кажущаяся незначительность не важна. Безответственно заставлять программистов или пользователей исправлять ваши уязвимости, особенно если вы даже не проинформировали о них.

    Проверка входных данных Проверка входных данных - это внешний оборонный периметр вашего веб-приложения. Он защищает основную бизнес-логику, обработку данных и генерацию выходных данных. В буквальном смысле всё за пределами этого периметра, за исключением кода, исполняемого текущим запросом, считается вражеской территорией. Все возможные входы и выходы периметра день и ночь охраняются воинственными часовыми, которые сначала стреляют, а потом задают вопросы. К периметру подключены отдельно охраняемые (и очень подозрительно выглядящие) «союзники», включая «Модель», «Базу данных» и «Файловую систему». Никто в них стрелять не хочет, но, если они попытаются испытать судьбу… бах. У каждого союзника есть свой собственный периметр, который может доверять или не доверять нашему.

    Помните мои слова о том, кому можно доверять? Никому и ничему. В мире PHP везде встречается совет не доверять «вводимым пользователем данным». Это одна из категорий по степени доверия. Предполагая, что пользователям доверять нельзя, мы думаем, что всему остальному доверять можно. Это не так. Пользователи - наиболее очевидный ненадёжный источник входных данных, потому что мы их не знаем и не можем ими управлять.

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

    Filter_var("php://example.org", FILTER_VALIDATE_URL);
    Фильтр проходится без вопросов. Проблема в том, что принятый URL php:// может быть передан PHP-функции, которая ожидает получения удалённого HTTP-адреса, а не возвращения данных от исполняемого PHP-скрипта (через PHP-обработчик). Уязвимость возникает потому, что опция фильтрации не имеет метода, ограничивающего допустимые URI. Несмотря на то, что приложение ожидает ссылки http, https или mailto, а не какой-то URI, характерный для PHP. Нужно всеми способами избегать подобного, слишком общего подхода к проверке.

    Будьте осторожны с контекстом Проверка входных данных должна предотвращать ввод в веб-приложение небезопасных данных. Серьёзный камень преткновения: проверка на безопасность данных обычно выполняется только для первого предполагаемого использования.

    Допустим, я получил данные, содержащие имя. Я достаточно просто могу проверить его на наличие апострофов, дефисов, скобок, пробелов и целого ряда алфавитно-цифровых Unicode-символов. Имя - это корректные данные, которые могут использоваться для отображения (первое предполагаемое использование). Но если использовать его где-то ещё (например, в запросе в базу данных), то оно окажется в новом контексте. И некоторые из символов, которые допустимы в имени, в этом контексте окажутся опасными: если имя преобразуется в строку для выполнения SQL-инъекции.

    Получается, что проверка входных данных по сути ненадёжна. Она наиболее эффективна для отсечения однозначно недопустимых значений. Скажем, когда что-то должно быть целым числом, или буквенно-цифровой строкой, или HTTP URL. Такие форматы и значения имеют свои ограничения и при должной проверке с меньшей вероятностью будут представлять угрозу. Другие значения (неограниченный текст, GET/POST-массивы и HTML) проверять труднее, и вероятность получения зловредных данных в них выше.

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

    Наряду с проверкой входных данных очень часто используется такой метод защиты, как экранирование. С его помощью данные проверяются на безопасность при входе в каждый новый контекст. Обычно этот метод применяют для защиты от межсайтового скриптинга (XSS), но он востребован и во многих других задачах, в качестве средства фильтрации.

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

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

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

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

    Так что белые списки предпочтительнее для любых процедур проверки благодаря более высокой безопасности и надёжности.

    Никогда не пытайтесь исправлять входные данные Проверка входных данных часто сопровождается фильтрацией. Если при проверке мы просто оцениваем корректность данных (с выдачей положительного или отрицательного результата), то фильтрация изменяет проверяемые данные, чтобы они удовлетворяли конкретным правилам.

    Обычно это несколько вредит. К традиционным фильтрам относятся, например, удаление из телефонных номеров всех символов, за исключением цифр (в том числе лишних скобок и дефисов), или обрезка ненужного горизонтального или вертикального пространства. В подобных ситуациях выполняется минимальная чистка, чтобы исключить ошибки при отображении или передаче. Однако можно чересчур увлечься использованием фильтрации для блокирования вредоносных данных.

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

    alert(document.cookie);
    В этом примере простая фильтрация по тэгу ничего не даст: удаление явного тэга приведёт к тому, что данные будут считаться полностью валидным элементом HTML-скрипта. То же самое можно сказать и про фильтрацию по любым конкретным форматам. Всё это наглядно показывает, почему нельзя делать проверку входных данных последним защитным контуром приложения.

    Вместо попыток исправить входные данные просто применяйте валидатор на базе белого списка и полностью отклоняйте такие попытки ввода. А там, где нужно фильтровать, всегда фильтруйте до выполнения проверки, никогда - после.

    Никогда не доверяйте средствам внешней проверки и постоянно отслеживайте уязвимости Ранее я отмечал, что проверка необходима при каждой передаче данных в новый контекст. Это применимо и к проверке, выполняемой вне самого веб-приложения. К подобным средствам относится проверка или иные ограничения, применяемые к HTML-формам в браузере. Посмотрите на эту форму из HTML 5 (метки опущены):

    Rep. Of Ireland United Kingdom
    HTML-формы умеют накладывать ограничения на вводимые данные. Вы можете ограничивать выбор с помощью списка из фиксированных пунктов, задавать минимальные и максимальные значения, а также ограничивать длину текста. Возможности HTML 5 ещё шире. Браузеры могут проверять URL и адреса почты, контролировать даты, числа и диапазоны (хотя поддержка последних двух довольно условна). Также браузеры способны проверять вводимые данные с помощью регулярных выражений JavaScript, включённых в атрибут шаблона.

    Со всем этим обилием средств контроля нельзя забывать: их предназначение - улучшить удобство вашего приложения. Любой злоумышленник способен создать форму, которая не будет содержать ограничений из вашей исходной формы. Можно даже создать HTTP-клиент для автоматизированного заполнения форм!

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

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

    Избегайте преобразования типов в PHP PHP не строго типизированный язык, и большинство его функций и операций типизируются небезопасно. Это может привести к серьёзным проблемам. Причём особенно уязвимы не сами значения, а валидаторы. Например:

    Assert(0 == "0ABC"); //возвращает TRUE assert(0 == "ABC"); //возвращает TRUE (даже без цифры в начале!) assert(0 === "0ABC"); //возвращает NULL/Выдаёт предупреждение о невозможности проверить утверждение
    При разработке валидаторов удостоверьтесь, что вы используете строгое сравнение и ручное преобразование типов, когда входные или выходные значения могут быть строкой. К примеру, формы могут возвращать строку, так что, если вы работаете с данными, которые должны быть целочисленными, обязательно проверяйте их тип:

    Function checkIntegerRange($int, $min, $max) { if (is_string($int) && !ctype_digit($int)) { return false; // содержит нецифровые символы } if (!is_int((int) $int)) { return false; // другое не целое значение или больше PHP_MAX_INT } return ($int >= $min && $int = $min && $int array("verify_peer" => TRUE))); $body = file_get_contents("https://api.example.com/search?q=sphinx", false, $context);
    UPD. В PHP 5.6+ опция ssl.verify_peer по умолчанию установлена в TRUE .

    Расширение cURL включает проверку сервера из коробки, поэтому можно ничего не настраивать. Однако программисты порой бездумно подходят к безопасности своих библиотек и приложений. Такой подход можно найти в любых библиотеках, от которых будет зависеть ваше приложение.

    Curl_setopt(CURLOPT_SSL_VERIFYPEER, false);
    Отключение проверки сервера в контексте SSL или при использовании curl_setopt() приведёт к уязвимости к атакам «человек посередине». Но её отключают как раз для того, чтобы решить проблему назойливых ошибок, которые свидетельствуют об атаке или о попытках приложения связаться с хостом, чей SSL-сертификат сконфигурирован неправильно или просрочен.

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

    Выводы Зачастую у нас есть все возможности для создания безопасного приложения. Но мы сами обходим некоторые разумные ограничения для облегчения разработки, отладки и отключения вывода назойливых ошибок. Либо из благих побуждений пытаемся излишне усложнить логику работы приложения.

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

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

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

    Лучшие страны для женщин

    1. Вам не хватает интима? Отправляйтесь в Канаду. Оказывается, канадки занимаются сексом на 45% чаще, чем средние пользователи приложения.

    2. Но будьте осторожны: Канада - отличное место, чтобы забеременеть. Канадские женщины могут забеременеть на 21% легче, чем остальные.

    3. Австралийки также часто занимаются сексом - на 37% больше, чем пользователи приложения в среднем.

    4. Стоит ли говорить, что женщины в Австралии также имеют хорошие шансы забеременеть? У них они на 14% выше, чем у других пользователей.

    5. США - хорошее место, чтобы стать счастливой. Американки на 16% чаще других женщин занимаются сексом.

    6. Худшее место, чтобы стать счастливой? Латинская Америка. Здесь женщины занимаются сексом на 4% реже, чем среднестатистические пользователи приложения.

    Сексуальные аппетиты

    1. Сексуальный аппетит женщины соответствует ее месячному циклу. Первым днем цикла считается первый день менструации, которая длится примерно пять дней. Таким образом, женщины меньше всего интересуются сексом от одного до пяти дней в месяц.

    2. Многие женщины сообщают об изменении уровня энергии или настроения в это время, и это связано, как правило, со снижением сексуального влечения. Также женщины менее заинтересованы в сексе еще целую неделю после менструации.

    3. Большинство женщин снова начинают заниматься сексом на 12-й день цикла.

    4. Многие женщины имеют регулярные сексуальные отношения с 12 по 14 день цикла. Приложение Glow называет эти дни «пиком сексуальности».

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

    6. Больше всего женщины наслаждаются сексом в последний, 30-й день своего цикла. Этот день в Glow обозначен как ​​«пик оргазмов».

    Довольны ли женщины

    1. Женщины чувствуют себя наиболее счастливыми в 15-й и 16-й дни своего цикла, а также в том случае, когда у них было много секса в предыдущие дни.

    2. Пользователи Glow за два года зарегистрировали 7,6 млн сексуальных контактов.

    3. Это значит, что каждую минуту по крайней мере семь женщин, которые используют приложение Glow, занимаются сексом.

    4. Кстати, пользователи также сообщили о своей влюбленности 2 миллиона раз. Также приложение отслеживает циклы секса и фертильность 88 тысяч пар.

    5. К сожалению, несмотря на имеющиеся сексуальные контакты, не все женщины ими довольны. Почти треть женщин готова скорее отказаться от секса, чем от смартфона.

    6. Но это все равно означает, что две трети скорее откажутся от телефонов, чем от секса.