我应该如何转义此LIKE查询中的字符?

Nis*_*sto 5 mysql escaping sql-like

我的一个表中有一个包含此字符串的字段:

!"#¤%&/()=?´`?=)(/&%¤#"!\'\'"'
Run Code Online (Sandbox Code Playgroud)

(仅用于测试目的).我已经尝试了无数的查询来正确选择这个字段,当然没有返回任何错误,但我似乎无法做到正确.

这是我目前使用的查询:

SELECT * FROM mytable WHERE `column` LIKE '%!"#¤%&/()=?´`?=)(/&%¤#"!\\\'\\\'"\'%'
Run Code Online (Sandbox Code Playgroud)

任何人都可以解释一下我的做法是不是正确的?'我应该逃避任何其他角色(除了)吗?我还没有在任何地方读过它...(但我尝试在precent符号之前添加反斜杠).

Mod*_*der 8

来自MySQL手册:

因为MySQL在字符串中使用C转义语法(例如," \n"表示换行符),所以必须\将在LIKE字符串中使用的任何" " 加倍.例如,要搜索" \n",请将其指定为" \\n".要搜索" \",请将其指定为" \\\\"; 这是因为反斜杠被解析器剥离一次,并且在进行模式匹配时再次剥离,留下一个反斜杠来匹配.

因此,您应该LIKE在两个步骤中为运算符转义字符串.

在PHP中它可以是这样的:

// Your search string, for example, from POST field
$string = $_POST['column'];

// First step - LIKE escaping
$string = str_replace(array('\\', '_', '%'), array('\\\\', '\\_', '\\%'), $string);

// Second step - literal escaping
$string = mysql_real_escape_string($string);

// Result query
mysql_query("SELECT * FROM `table` WHERE `column` LIKE '%".$string."%'");
Run Code Online (Sandbox Code Playgroud)

更新:

MySQL扩展在PHP 5.5.0中已弃用,并在PHP 7.0.0中被删除.相反,应该使用MySQLiPDO_MySQL扩展.

使用MySQLi

// Connect to database
$mysqli = new mysqli('localhost', 'username', 'password', 'database');

// Your search string, for example, from POST field
$string = $_POST['column'];

// First step - LIKE escaping
$string = str_replace(['\\', '_', '%'], ['\\\\', '\\_', '\\%'], $string);

// Second step - literal escaping
$string = $mysqli->real_escape_string($string);

// Result query
$mysqli->query("SELECT * FROM `table` WHERE `column` LIKE '%{$string}%'");
Run Code Online (Sandbox Code Playgroud)

使用PDO

// Connect to database
$conn = new PDO('mysql:host=localhost;dbname=database', 'username', 'password');

// Your search string, for example, from POST field
$string = $_POST['column'];

// First step - LIKE escaping
$string = str_replace(['\\', '_', '%'], ['\\\\', '\\_', '\\%'], $string);

// Second step - literal escaping
$string = $conn->quote($string);

// Result query
$conn->query("SELECT * FROM `table` WHERE `column` LIKE '%{$string}%'");
Run Code Online (Sandbox Code Playgroud)

或者您可以使用PDO预处理语句,而不是第二步(文字转义):

// Connect to database
$conn = new PDO('mysql:host=localhost;dbname=database', 'username', 'password');

// Your search string, for example, from POST field
$string = $_POST['column'];

// First step - LIKE escaping
$string = str_replace(['\\', '_', '%'], ['\\\\', '\\_', '\\%'], $string);

// Prepare a statement for execution
$statement = $conn->prepare("SELECT * FROM `table` WHERE `column` LIKE ?");

// Execute a prepared statement
$statement->execute(["%{$string}%"]);
Run Code Online (Sandbox Code Playgroud)


nul*_*lll 1

不清楚您想要获得什么以及出了什么问题。

顺便说一句,如果你想保护你的查询免受 SQL 注入,你应该使用 mysql_real_escape_string
http://dev.mysql.com/doc/refman/5.0/en/mysql-real-escape-string.html

假设你使用的是 PHP

$query = "SELECT * FROM mytable WHERE `column` LIKE '".mysql_real_escape_string($whatever)."'"
Run Code Online (Sandbox Code Playgroud)

但你必须记住,LIKE运算符有他自己的特殊字符(wildchars)
http://dev.mysql.com/doc/refman/5.0/en/string-comparison-functions.html#operator_like

% Matches any number of characters, even zero characters
_ Matches exactly one character
Run Code Online (Sandbox Code Playgroud)

所以如果你想阻止他们的魔法,这个字符必须用反斜杠转义

假设你使用 PHP 我会这样做

// This removes magic on LIKE wildchars
$whatever = preg_replace('#(%|_)#', '\\$1', $input);

// This secures the query from sql injection 
// and hads the trailing % wildchars to the search string
$query = "SELECT * FROM mytable WHERE `column` LIKE '%".mysql_real_escape_string($whatever)."%'"
Run Code Online (Sandbox Code Playgroud)