Безопасность
Атаки инъекциями в запросах
Если вы передаете параметры $_GET
(или $_POST
) в запросах,
убедитесь, что они сначала приводятся к строкам.
Пользователи могут вставлять ассоциативные массивы в запросы GET и POST,
которые затем могут стать нежелательными $-запросами.
Довольно безобидный пример. Предположим, вы ищете информацию о пользователе
по запросу http://www.example.com?username=bob.
Ваше приложение выполняет запрос $collection->find(array("username" => $_GET['username']))
.
Кто-то может сломать это, сделав запрос
http://www.example.com?username[$ne]=foo, который PHP
волшебным образом превратит в ассоциативный массив, превратив его в
$collection->find(array("username" => array('$ne' => "foo")))
,
который вернет всех пользователей, не имеющих имени "foo" (вероятно, всех ваших пользователей).
От такой атаки довольно легко защититься: убедитесь, что параметры $_GET и $_POST соответствуют ожидаемому типу, прежде чем отправлять их в базу данных (в данном примере приведите их к строкам).
Обратите внимание, что этот тип атаки может использоваться с любым взаимодействием с базой данных: включая поиск, изменение и удаление.
Спасибо » Филу за указание на это.
Смотрите » основную документацию для получения дополнительной информации об SQL-инъекциях в MongoDB.
Атаки JavaScript-инъекциями
Если вы используете JavaScript, убедитесь, что все переменные,
которые пересекают границы PHP-JavaScript, передаются
в поле scope
класса MongoCode,
а не интерполируются в строку JavaScript. Это может произойти при использовании MongoDB::execute(),
$where
сlauses, MapReduces, group-by и в любых других случаях,
когда вы можете передать JavaScript в базу данных.
Замечание:
MapReduce игнорирует поле
scope
класса MongoCode, но в команде есть параметрscope
, который можно использовать вместо него.
Например, предположим, что у нас есть некоторый JavaScript, чтобы приветствовать пользователя в журналах базы данных. Мы могли бы сделать:
<?php
// не делайте так!
$username = $_POST['username'];
$db->execute("print('Привет, $username!');");
?>
Что будет, если злоумышленник передаст какой-то JavaScript?
<?php
// не делайте так!
// в $username будет передано "'); db.users.drop(); print('"
$db->execute("print('Привет, $username!');");
?>
Теперь MongoDB выполняет строку JavaScript
"print('Привет, '); db.users.drop(); print('!');"
.
Эту атаку легко предотвратить: используйте scope
для передачи переменных из PHP в JavaScript:
<?php
$scope = array("user" => $username);
$db->execute(new MongoCode("print('Привет, '+user+'!');", $scope));
?>
Это добавит переменную user
в область JavaScript.
Теперь, если кто-то попытается отправить вредоносный код, MongoDB безвредно напечатает
Привет, '); db.dropDatabase(); print('!
.
Использование scope
помогает предотвратить выполнение вредоносного ввода базой данных.
Тем не менее, вы должны убедиться, что ваш код не изменится и все равно выполнит ввод!
Например, никогда не используйте функцию JavaScript eval
при вводе пользователем данных:
<?php
// не делайте так!
// $jsShellInput is "db.users.drop();"
$scope = array("input" => $jsShellInput);
$db->execute(new MongoCode("eval(input);", $scope));
?>
Всегда используйте scope
и никогда не позволяйте
базе данных выполнять пользовательский ввод в виде кода.