Инъекция может быть через любой запрос.
И защищать тоже надо любые запросы.
Никогда не надо торговаться, "а можно я не буду защищать именно этот запрос? Ну мааааам!"
Надо просто всегда следовать простым правилам - любая переменная попадает в запрос только через плейсхолдер
Важно понимать, что в рассуждениях про инъекции люди постоянно путают два понятия - самой уязвимости, и конкретных способов ей воспользоваться.
Уязвимость — это сама возможность с помощью переданных в запрос данных изменить его код.
Даже если ты не знаешь ни одного способа ей воспользоваться, уязвимость от этого никуда не девается.
Даже если та возможность, про которую ты знаешь, в данном случае не прокатит - остаются ещё тысячи других.
Если есть уязвимость, то способы ей воспользоваться всегда найдутся.
То есть
сама уязвимость никак не зависит ни от каких второстепенных факторов - типа запроса, передаваемых данных, способов их валидации, твоих знаний SQL. Это сам факт. Можно подставить свой код в запрос? Значит он уязвим. А как конкретно можно нагадить - это отдельная тема.
Кроме того, любая уязвимость - это всегда ошибки. Если в $id будет пусто, то запрос вызовет ошибку. Если в $id будет слово select то запрос вызовет ошибку. Если будет слово "привет", то запрос вызовет ошибку.
Оно тебе надо?
При этом разных вариантов возможных ошибок и способов воспользоваться уязвимостью - тысячи, им посвящены целые учебники и статьи.
Но для того чтобы защищаться, не надо знать ни одного. Потому что защищаться надо не от отдельных способов эксплуатации, а закрывать саму уязвимость. И сделать это очень просто:
- Любые данные должны добавляться в запрос только через плейсхолдеры
- Любые другие элементы запроса должны выбираться из белого списка - заранее прописанных в нашем коде значений.
Если вопрос "а можно я не буду защищаться?" вызван ленью, то это тоже решаемо. В принципе, лень - это очень важное качество для программиста. Главное - направить её в нужное русло.
Если каждый раз писать по три строчки долго
$sql = "INSERT INTO users SET email = ?, password = ?"; // заменяем на знаки вопроса
$stmt = $db->prepare($sql); // подготавливаем запрос, получаем stmt
$stmt->bind_param("ss", $email, $hash); // два знака вопроса - две переменных - две буквы s
$stmt->execute(); // выполняем запрос
То надо воспользоваться такой вещью, как
программирование. И написать
функцию, которая возьмет на себя всю рутинную работу.
function prepared_query($mysqli, $sql, $params, $types = "")
{
$types = $types ?: str_repeat("s", count($params));
$stmt = $mysqli->prepare($sql);
$stmt->bind_param($types, ...$params);
$stmt->execute();
return $stmt;
}
и в итоге предыдущие 4 строчки превратятся в одну:
prepared_query($db, "INSERT INTO users SET email = ?, password = ?", [$email, $hash]);
или твой запрос:
prepared_query($db, "UPDATE table SET test WHERE id = ?", [$id]);
- просто, быстро, удобно и безопасно