Зачем кавычки вокруг имени таблицы в SQL: ошибка NHibernate
Быстрый ответ
В SQL кавычки " "
делают имена таблиц чувствительными к регистру, а также позволяют использовать в их составе специальные символы и зарезервированные слова. Вот примеры:
- Без кавычек:
SELECT * FROM casesensitivename;
может не выполниться, если название таблицы — "CaseSensitiveName". - С кавычками:
SELECT * FROM "CaseSensitiveName";
точно соответствует нашей таблице.
При использовании зарезервированных слов:
CREATE TABLE "SELECT" (id INT);
Такое применение кавычек важно в случаях, когда настройки не различают регистр, а также при использовании специфических идентификаторов.
Разбираемся глубже
Почему важна чувствительность к регистру?
В Oracle SQL идентификаторы, включая имена таблиц, по умолчанию нечувствительны к регистру:
SELECT * FROM employees;
SELECT * FROM EMPLOYEES;
Оба этих запроса — идентичны. Однако это меняется, когда применяются двойные кавычки:
SELECT * FROM "Employees";
// Этот запрос уже не равнозначен "EMPLOYEES". Здесь начинается совершенно другая история.
Теперь при запросе обязательно учитывать регистр, иначе база данных вернёт ошибку "table or view does not exist".
Кавычки и специальные символы
Кавычки позволяют использовать в идентификаторах специальные символы и зарезервированные слова без конфликтов:
- Специальные символы:
"my-table#with$chars"
- Зарезервированные слова:
"CREATE"
Если имя было создано с кавычками, имейте в виду, что для обращения к таблице всегда следует использовать кавычки.
Совместимость с ORM
Важно согласовывать имена таблиц и классов в ORM, например, NHibernate:
session.QueryOver<User>().List(); // Совпадение имён обязательно.
Если класс User
, а таблица "user"
, то это может привести к проблемам.
Визуализация
Можно представить ВИП-секцию с охранником и списком приглашённых:
Список приглашённых (📜): ["SMITH", "O'NEIL", "MCDONALD'S", "SELECT", "JOIN"]
Кавычки — это своего рода ВИП-пропуск:
"SMITH" // Мистер Смит, добро пожаловать.
"O'NEIL" // Мистер О'Нил, мы учтём ваш апостроф. Проходите.
"MCDONALD'S" // Да, с апострофом, без проблем.
"SELECT" // Сегодня вы не оператор, а гость.
"JOIN" // Обычно соединяете, но сегодня просто гость.
Без кавычек гости не попадают внутрь:
- SELECT не пройдёт как гость, ибо он команда.
- JOIN обычно в центре событий, сейчас — просто зритель.
Без кавычек VIP: 🚫🧍♂️📜
С кавычками VIP: ✅🧍♂️🔖
Кавычки говорят о том, что идентификатор — это явно заданная сущность, а не просто употребляемая конструкция или ключевое слово.
Сценарии погружения
Подводные камни чувствительности к регистру
Если таблица создана как "Employee"
, то при обращении к ней всегда следует использовать кавычки:
SELECT * FROM Employee; -- Ошибка: "employee" не найден, имелось в виду "Employee".
Совместимость при экспорте/импорте
Сохранение регистра критически важно при экспорте/импорте баз данных. Файлы экспорта с именами, требующими учёта регистра, при импорте требуют применения кавычек, в противном случае возникнут ошибки.
Совместимость между СУБД
В Oracle и PostgreSQL имена, заключённые в кавычки — чувствительны к регистру. MySQL и SQLite имеют собственные подходы к вопросу регистра. Знание этих тонкостей помогает писать кросс-совместимый SQL-код.
Полезные материалы
- SQL Aliases — о использовании псевдонимов и кавычек.
- PostgreSQL: Documentation: 16: 4.1. Lexical Structure — об использовании идентификаторов и кавычек в PostgreSQL.
- MySQL :: MySQL 8.0 Reference Manual :: 11.2 Schema Object Names — документация MySQL о применении кавычек и именовании.
- SQLite Keywords — о ключевых словах в SQLite, которые требуют использования кавычек.
- SQL style guide by Simon Holywell — рекомендации по стилю написания SQL, включая именование и использование кавычек.