www.system-it-cons.ru
Dr.Web Сертифицированный партнер
регистрация

Статьи :: Безопасность GET, POST

Безопасность данных передаваемых методами GET и POST

 

Описание:

 

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

 

Методы передачи данных:

 

При вызове из браузера и передачи серверу данных из URL, например

http://test.com:80/script.ext?onestring

браузер разбирает URL строку, определяет имя сервера порт, имя протокола, тип передаваемых данных, имя браузера, длину данных и другие параметры.  Устанавливает соединение с сервером test.com на 80 порт и передает параметры. Все параметры отделяются друг от друга символом перевода строки (\n), а последний параметр  символом окончания заголовка запроса(\n\n). Только после получение символа окончания сервер начинает обрабатывать наши данные. Все параметры, которые попадают перед символом окончания заголовка запроса называют заголовками(headers). Их может быть несколько(см. выше сервер и порт, имя браузера и др.) Протокол HTTP  задает правила формирования и интерпретации этих заголовков. Приведем для примера заголовки, которые чаще всего используются сервером:

CONTENT-TYPEпеременная окружения, идентифицирует тип передаваемых данных. Обычно указывается значение application/x-www-form-urlencoded , определяет формат в котором все управляющие символы(кроме алфавитно-цифровых и других) специальным образом кодируются. Может применяться и значение multipart/form-data необходимое при передачи файлов на сервер.

HOST переменная окружения, содержит доменное имя узла, к которому обращается пользователь при вводе в адресной строке браузера, а также номер порта. Если на сервере используется порт службы(демона) отличного от по-умолчанию(80).

SERVER_NAME переменная окружения похожа на переменную HOST, но имеет отличия.

COOKIEпеременная окружения, содержит данные хранящиеся на локальном компьютере и необходимые для сценария. Может хранить пути до ваших настроек на сервере, данные о идентификаторах сессий и т. п.

ACCEPT переменная окружения, содержит типы документов воспринимаемых браузером. Например: text/html, text/plain, image/gif, image/jpeg и др.

CONTENT-LENGTHпеременная окружения, представляет строку с представлением длины данных в байтах, при передаче методом POST (см. ниже), при методе GET(см. ниже) переменная отсутствует.

USER-AGENTпеременная окружения, содержит информацию о версии браузера (Mozilla Firefox 6.0 и т. п.)

REFERERпеременная окружения, содержит URL страницы, c осуществился переход на текущую страницу(гиперссылка).

ACCEPT-CHARSET переменная окружения, указывает на кодировку данных (koi8-r, utf8, cp1251 и др.) в которой браузер ожидает получить ответ от сервера.

ACCEPT-ENCODINGпеременная окружения, в которой передается информация о методах сжатия данных например - метод gzip. Данные полученные сервером, пересылаются браузеру обратно в сжатом виде(меньший объем передаваемых данных по сети). Браузер принимает запакованные данные по наличию заголовка (gzip), определяет метод сжатия и распаковывает информацию, отображая ее в браузере.

Обращение к серверу чаще всего реализуется методами GET и POST. Рассмотрим  эти методы.

  1. Метод GET

Параметры данных передаются в заголовке HTTP запроса. Формат передачи данных серверу — GET сценарий?параметры HTTP/1.0

Этот метод имеет ограничение в размере длины заголовков, соответственно большие данные(более 2 Кбайт)1 в одном запросе мы передать уже не сможем.

 

Строка сценарий?параметры еще эту строку называют URI (идентификатор ресурса). На стороне сервера эти данные сохраняются в переменных, например переменные окружения в REQUEST_URI, в переменной QUERY_STRING сохраняются параметры после знака вопроса(?), а в переменной REQUEST_METOD имя метода GET.

  1. Метод POST

Параметры данных передаются в теле HTTP запроса. Формат передачи данных серверу — POST сценарий?параметры HTTP/1.0

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

 

Принципы обработки данных:

 

Условно обработку данных можно разбить на 2 этапа проверки : на клиенте и сервере. На клиенте проверка может осуществляться с помощью: Javascript, jQuery. Здесь ограничениями самой формы из которой передаются данные. На сервере необходимо проверять факт существования переданных переменных, их возможные значения и длину данных. Большее внимание стоит уделить именно проверки данных на сервере, так как данные можно передавать не из формы, тогда отсутствует проверка полей средствами HTML, а Javascript можно отключить в браузере или подключить свой скрипт.

 

Реализация приемов проверки данных:

 

  1. При получении данных от сервера, в первую очередь проверяем каким методом посылаются данные.
  2. Проверяем факт существования переменных окружения и их существование значений в переменных
  3. Проверяем предполагаемую длину входящих данных.
  4. Производим действия по «приведению» переменных к актуальным типам данных применяемых в серверной части
  5. Применение приема «модерирования» данных, таким образом проводим проверку на соответствие (исключаем html тэги, экранируем символы, исключаем операторы вызовов в файловой системе(system,exec, passthru, popen и др.), при использовании базы данных исключаем операторы управления данными и вызовами триггеров и т.п.)

 

При получении данных на сервере  формируются массивы в соответствии с методом массив $_GET или $_POST, если проверка на метод не производится то можно использовать массив который объединяет оба метода - $_REQUEST. Определяем факт существования переменных, в зависимости от типа или предполагаемого значения переменной можно применять следующие функции gettype, empty, is_null, isset. Более подробное описание функций можно посмотреть на www.php.net. Например на факт что переменная передана и не «пустая» можно использовать функцию isset($var1), где var1 – переменная переданная от браузера. Далее определяем тип переменных методом gettype, если тип переменным заранее известен можно проверять переменные в соответствии с типами is_bool, is_int, is_float, is_array, is_int, is_string. Для проверки длины данных(имеет смысл у строковых типов) можно использовать strlen или count,числовые типы можно также проверить предварительно привести их к строковому типу (string). Для всех типов данных применяем функции приведения переменных к нужному типу следующим выражением (int)$var1   - этим выражением мы принудительно привели переменную $var к числовому виду. Ограничиваем или «обрезаем» лишние пробелы функцей trim и mb_substr($var1,0,5)ограничили количество символов в строке/числе. Для «модерирования» данных применяют встроенные функции для удаления  html тегов и замену «сущностей», например замена символа «кавычки» на ее символ «&lt», а также поиск «опасных» операторов применяемых для SQL инъекций 2, используя регулярные выражения. При вводе данных в базу данных экранируйте данные функцией addslashes,   для удаления html тэгов используйте strip_tags, а поиск выражений выполняйте используя perl совместимыми функциями, например preg_replace(“<script[^>]*?>*?</script>”,””,$var1) удалить Javascript из переменной $var1.

 

1- Данное ограничение справедливо для большинства браузеров (IE, Safary, Chrome), Opera – 4 Кб,  Firefox – до 64 Кб.

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