You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PHP中使用LIKE通配符%%查询MySQL数据时崩溃的问题排查

问题分析与解决办法

为啥带%的LIKE会崩溃?

核心是你PHP拼接SQL的时候引号处理错了,生成的SQL语法完全无效。你写的'" . $sourceType. "'这种写法,会让PHP把"当成普通字符串输出,最终生成的SQL里会出现" .object. "这类乱码内容,数据库根本解析不了。而你在Workbench里直接写正确的SQL,当然能正常运行。

怎么修复?

临时方案:修正字符串拼接(不建议生产环境用,有安全风险)

如果非要直接拼接字符串,得把引号和变量的关系理清楚:

$sourceType = 'object';
$sourceId = 189;
$path = 'test';

// 用双引号包裹SQL,变量直接嵌入
$query = "SELECT d.targetid as id, d.sourcetype as type, CONCAT(o.o_path, o.o_key) as path
FROM dependencies d
INNER JOIN objects o ON o.o_id = d.targetid AND d.targettype= 'object'
WHERE d.sourcetype = '$sourceType' AND d.sourceid = $sourceId AND CONCAT(o.o_path, o.o_key) LIKE '%$path%';";

或者用单引号加连接符:

$query = 'SELECT d.targetid as id, d.sourcetype as type, CONCAT(o.o_path, o.o_key) as path
FROM dependencies d
INNER JOIN objects o ON o.o_id = d.targetid AND d.targettype= \'object\'
WHERE d.sourcetype = \'' . $sourceType . '\' AND d.sourceid = ' . $sourceId . ' AND CONCAT(o.o_path, o.o_key) LIKE \'%' . $path . '%\';';

⚠️ 注意:如果$path是用户输入的内容,这种写法会存在SQL注入风险,绝对不能在生产环境使用。

推荐方案:用预处理语句(安全还省心)

不管是PDO还是MySQLi,预处理语句都能彻底解决语法错误和安全问题:

PDO写法:

$sourceType = 'object';
$sourceId = 189;
$path = 'test';

// 假设你已经完成数据库连接,$pdo是PDO实例
$stmt = $pdo->prepare("
    SELECT d.targetid as id, d.sourcetype as type, CONCAT(o.o_path, o.o_key) as path
    FROM dependencies d
    INNER JOIN objects o ON o.o_id = d.targetid AND d.targettype= 'object'
    WHERE d.sourcetype = ? AND d.sourceid = ? AND CONCAT(o.o_path, o.o_key) LIKE ?
");
// 把通配符和变量拼接好
$likePath = "%$path%";
$stmt->execute([$sourceType, $sourceId, $likePath]);
// 获取查询结果
$results = $stmt->fetchAll(PDO::FETCH_ASSOC);

MySQLi写法:

$sourceType = 'object';
$sourceId = 189;
$path = 'test';

// 假设$conn是已经初始化的MySQLi连接
$stmt = $conn->prepare("
    SELECT d.targetid as id, d.sourcetype as type, CONCAT(o.o_path, o.o_key) as path
    FROM dependencies d
    INNER JOIN objects o ON o.o_id = d.targetid AND d.targettype= 'object'
    WHERE d.sourcetype = ? AND d.sourceid = ? AND CONCAT(o.o_path, o.o_key) LIKE ?
");
$likePath = "%$path%";
// 绑定参数,"sis"表示参数类型为字符串、整数、字符串
$stmt->bind_param("sis", $sourceType, $sourceId, $likePath);
$stmt->execute();
$result = $stmt->get_result();
$results = $result->fetch_all(MYSQLI_ASSOC);

关于REGEXP的问题

你用REGEXP能运行但结果不全,原因有两个:

  1. MySQL的REGEXP默认大小写敏感(取决于数据库字符集的校对规则),比如大写的Test可能匹配不到;
  2. 如果$path里包含正则特殊字符(比如.、*),会被当成正则语法解析,而非简单的字符串匹配,导致漏数据。而LIKE是纯通配符匹配,不存在这个问题。

内容的提问来源于stack exchange,提问作者Mariglen Meta

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.28 14:17:42