Сервер MySQL версии 10.3.9-MariaDB не может запрашивать текст имеет одинарные кавычки - PullRequest
0 голосов
/ 19 февраля 2019

У меня есть база данных MySQL, в которой есть поле TagName со значением ~! @ # $% ^ & * () _ + |} {":?> <./ '; [] \ = -` Я пытаюсь выполнить запросвыберите TagName из taginfo, где TagName, например, '% @ # $%'; </p>

Это показывает, что данные с тэгом содержат символ кавычки. Но я запрашиваю оператор = и оператор like и добавляю больше кавычек '', чтобы принять одинарную кавычку, ноон показывает пустой результат.

Я также пытаюсь добавить COLLATE UTF8_GENERAL_CI или изменить CHARACTER SET, но все они не удаются.

SELECT * from taginfo where tagname like '%~!@#$%^&*()_+|}{":?><./'';[]\=-`%';
SELECT * from taginfo where tagname like '%~!@#$%^&*()_+|}{":?><./'';[]\=-`%' COLLATE UTF8_GENERAL_CI;
SELECT * from taginfo where tagname COLLATE UTF8_GENERAL_CI like '%~!@#$%^&*()_+|}{":?><./'';[]\=-`%';

ALTER TABLE mytable CONVERT TO CHARACTER SET UTF8_GENERAL_CI
Error   2/19/2019 10:03:24 AM   0:00:00.039 <link> - MySQL Database Error: Unknown character set: 'UTF8_GENERAL_CI' 5   0

Версия сервера БД: MySQL 5.5.5 MariaDB Информация о таблице: enter image description here

Вот результат запроса без одинарных кавычек: enter image description here

Обновлено: я обнаружил проблему, что если я запрашиваю без символа \это показывает результат:

select TagName from taginfo where TagName like '%~!@#$%^&*()_+|}{":?><./'';[]%';

Но я добавил символ \, в конце он ничего не показывает:

select TagName from taginfo where TagName like '%~!@#$%^&*()_+|}{":?><./'';[]\%';

добавить еще всплеск все еще не работает

select TagName from taginfo where TagName like '%~!@#$%^&*()_+|}{":?><./'';[]\\%';

Обновлено: проблема в том, что аналогичный запрос возвращает результат, но запрос = не возвращает.

SELECT * from taginfo where tagname like '%~!@#$%^&*()_+|}{":?><./'';[]\\=-`%';
select * from taginfo where TagName =     '~!@#$%^&*()_+|}{":?><./'';[]\\=-`'

Обновлено: при попытке создатьd БД в MySQL 8.0.13, этот запрос работает нормально и возвращает 1 строку

select * from taginfo1 where TagName = '~!@#$%^&*()_+|}{":?><./'';[]\\=-`';

Но в 10.3.9-MariaDB запрос

select * from taginfo1 where TagName = '~!@#$%^&*()_+|}{":?><./'';[]\\=-`';

не может вернуть никакого результата.

SELECT VERSION();

10.3.9-MariaDB

Ответы [ 4 ]

0 голосов
/ 12 марта 2019

Наконец я обнаружил проблему, потому что я установил этот режим.

SET @@SQL_MODE = CONCAT(@@SQL_MODE, ',NO_BACKSLASH_ESCAPES');

и этот запрос возвращает пустое значение

select * from taginfo where tagname = '~!@#$%^&*()_+|}{":?><./'';[]\\=-`'

Когда я удаляю NO_BACKSLASH_ESCAPES на SET @@SQL_MODE = 'NO_ENGINE_SUBSTITUTION';

select * from taginfo where tagname = '~!@#$%^&*()_+|}{":?><./'';[]\\=-`'

возвращает строку с тэгом = ~! @ # $% ^ & * () _ + |} {":?> <./ '; [] \ = -` </p>

0 голосов
/ 19 февраля 2019

Я пытаюсь установить

SET @@SQL_MODE = CONCAT(@@SQL_MODE, ',NO_BACKSLASH_ESCAPES');

И обновить запрос добавить двойной \

SELECT * from taginfo where tagname like '%~!@#$%^&*()_+|}{":?><./'';[]\\=-`%';

Этот запрос возвращает правильный результат, но не работает с оператором =.

0 голосов
/ 19 февраля 2019
DROP TABLE IF EXISTS `taginfo`;

CREATE TABLE `taginfo` (
    `tagname` VARCHAR(50) NULL DEFAULT NULL
)
COLLATE='utf8_general_ci'
ENGINE=InnoDB
;

-- Notice single quote and backslash are escaped:
INSERT INTO `taginfo` (`tagname`) VALUES   ('~!@#$%^&*()_+|}{":?><./'';[]\\=-`'); 
SELECT * FROM `taginfo` WHERE tagname =     '~!@#$%^&*()_+|}{":?><./'';[]\\=-`'; 

-- Notice single quote, percent and underscore are escaped and backslash escaped twice
SELECT * FROM `taginfo` WHERE tagname LIKE  '~!@#$\%^&*()\_+|}{":?><./'';[]\\\\=-`';
SELECT * FROM `taginfo` WHERE tagname LIKE '%~!@#$\%^&*()\_+|}{":?><./'';[]\\\\=-`%';
0 голосов
/ 19 февраля 2019

Обратная косая черта - это экранирующий символ в MySQL.Вам нужно будет дважды убежать от него, как \\.Кроме того, если используется условие LIKE, знак процента и знак подчеркивания также необходимо экранировать (в противном случае вы переносите совпадение на нерелевантные значения).

Вы можете увидеть, что происходит, просто выбрав значение, котороеВы проходите мимо:

SELECT '%~!@#$\%^&*()_+|}{":?><./'';[]\=-`%' test1;

| test1                            |
| -------------------------------- |
| %~!@#$%^&*()_+|}{":?><./';[]=-`% |

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

Теперь давайте дважды избежим обратного слэша, и он появляется ввывод:

SELECT '%~!@#$\%^&*()\_+|}{":?><./'';[]\\=-`%' test2;

| test2                             |
| --------------------------------- |
| %~!@#$%^&*()_+|}{":?><./';[]\=-`% |

Просмотр на БД Fiddle

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...