Перейти к содержимому
Назад к пути
Теория 3 мин чтения

3. Роль комментариев

Использование SQL-комментариев

Комментарии в SQL — это не только способ оставить заметку коллеге, но и мощный инструмент для завершения инъекции. С их помощью хакер «отрезает» всё, что идет после его вредоносного кода, предотвращая синтаксические ошибки базы данных.

Для Go-разработчика этот трюк особенно болезнен в multi-condition login-запросах: вы пишете SELECT id FROM users WHERE username='X' AND password_hash='Y' через fmt.Sprintf, ожидая что обе колонки проверятся. Атакующий вводит admin'-- в username — и базе достаётся WHERE username='admin' AND password_hash='...' с условием AND password_hash='...' внутри комментария. Сравнение пароля просто не происходит. Это самый дешёвый exploit-payload в истории SQLi — 8 символов.

Посмотрим на разные стили комментариев и как они помогают сделать атаку незаметной для парсера. Аналогия — заявление в банке: вы заполнили графу «Имя» и «ФИО», а ниже стоит «Кодовое слово». Если злоумышленник в графу «Имя» напишет Сергей. ИГНОРИРОВАТЬ ВСЁ НИЖЕ, а охранник банка следует инструкции дословно — кодовое слово проверяться не будет.


1. Механика: "Обрезание" кода

Представьте типичный запрос из Go-хендлера: SELECT id FROM users WHERE username='%s' AND password='%s' (через fmt.Sprintf).

Этот код встречается в каждом втором туториале «Go login example» на Хабре или Medium — и каждый второй разбор такого туториала забывает упомянуть параметризацию. В результате паттерн расходится по pet-проектам и MVP-стартапам без какой-либо проверки безопасности.

Хакер вводит в поле username: admin' --.

Как это видит SQL-парсер: SELECT id FROM users WHERE username='admin' --' AND password='...'

Все, что идет после двух тире (--), база данных считает обычным комментарием и НЕ ВЫПОЛНЯЕТ.

  • Оригинальный запрос: WHERE username='admin' AND password='...'
  • Результат атаки: WHERE username='admin'

Поздравляем: вы только что авторизовали хакера в аккаунт администратора без пароля! Это классический auth-bypass — payload известен с конца 1990-х и до сих пор регулярно срабатывает на CTF и в реальных bug bounty. На HackerOne такие отчёты до сих пор уходят за 5000-10000 USD, потому что компании сами не верят, что в 2026 году у них может быть такой банальный баг.


2. Разновидности комментариев в разных СУБД

Хакеры знают, какая база данных установлена на вашем сервере, и используют соответствующие символы. Для них это часть фингерпринтинга: если admin'-- не работает, но работает admin'#, то это MySQL. Если работает admin'/* без закрывающего */ — это MSSQL в режиме «терпимости к незакрытым комментариям».

СУБД Однострочный комментарий Многострочный
PostgreSQL -- (пробел необязателен) /* */
MySQL # или -- (пробел ОБЯЗАТЕЛЕН) /* */
SQLite -- /* */
MS SQL Server -- /* */

3. Таблица работы: Исходный SQL vs Атака

Параметр Исходный SQL Результат атаки (SQL Injection)
Тип user='%s' AND pass='%s' user='admin' -- ' AND pass='...'
Условие Логин И Пароль ТОЛЬКО ЛОГИН
Статус 🟢 БЕЗОПАСНО 🔴 ВЗЛОМАНО

4. Почему это работает в Go?

Потому что Go-пакет fmt.Sprintf просто "склеивает" текст, не понимая его значения. Для Go строка — это просто массив байтов. Для базы данных — это команда. Различие в восприятии — это и есть уязвимость. На уровне типов Go не делает различия между «безопасной строкой» и «недоверенным вводом» — оба типа string. Линтер go vet это тоже не отлавливает. Защитники типов появляются только в специализированных linter-ах вроде gosec (правило G201), но они не включены в стандартный go vet и часто отсутствуют в CI молодых проектов.

Решение: db.QueryRow("SELECT id FROM users WHERE username=? AND password_hash=?", u, hashFn(p)).Scan(&id). Драйвер database/sql отправляет SQL-команду и значения параметров отдельно — по wire-protocol. PostgreSQL/MySQL получает WHERE username=$1 AND password_hash=$2 как структуру AST, а admin'-- — как литеральное значение $1. Никакого «парсинга» ввода нет, потому что ввод не доходит до парсера SQL.


Отрезая лишнее, хакер гарантирует, что база выполнит именно его команду. Это делает инъекцию компактной и работоспособной.

Пришло время перейти от изучения атак к защите. Начнем с самого важного инструмента — подготовленных выражений.

Продолжить чтение

Что бы прочитать модуль полностью, зарегистрируйтесь/войдите на платформу

Когда закончишь — отметь раздел, чтобы продолжить.

🚧 Сайт в разработке. Полный функционал пока недоступен. Все вопросы — support@hackandfix.ru