这个思路主要解决MySQL 中的科学记数法漏洞使 AWS WAF 客户端易受 SQL 注入攻击这篇文章中的问题
目前基本上都使用阿里巴巴的druid并开启sql防火墙模式以语义层面拦截sql注入,如果极端情况下对sql解析结果不一致还是会产生sql注入
于是尝试了一下mysql自带的功能
1)EXPLAIN
2)optimizer_trace
SET optimizer_trace = "enabled=on";
EXPLAIN
SELECT GROUP_CONCAT(TABLE_NAME) FROM information_schema.tables WHERE table_schema = DATABASE();
SELECT TRACE
FROM information_schema.OPTIMIZER_TRACE;
SET optimizer_trace = "enabled=off";
EXPLAIN保证sql不会对数据库造成污染
optimizer_trace主要保证获取sql在数据库中的实际内容
在information_schema的OPTIMIZER_TRACE中
QUERY是执行的sql而TRACE是sql引擎跟踪后的内容使用json表达
注意,内容非常的长啊!所以我们只截取我们比较关心的部分
"expanded_query": "/* select#1 */ select group_concat((`mysql`.`tbl`.`name` collate utf8mb3_tolower_ci) separator ',') AS `GROUP_CONCAT(TABLE_NAME)` from <constant table> join ((((((`mysql`.`tables` `tbl` join `mysql`.`schemata` `sch` on((`mysql`.`tbl`.`schema_id` = `mysql`.`sch`.`id`))) join `mysql`.`catalogs` `cat` on((`mysql`.`cat`.`id` = `mysql`.`sch`.`catalog_id`))) left join `mysql`.`collations` `col` on((`mysql`.`tbl`.`collation_id` = `mysql`.`col`.`id`))) left join `mysql`.`tablespaces` `ts` on((`mysql`.`tbl`.`tablespace_id` = `mysql`.`ts`.`id`))) left join `mysql`.`table_stats` `stat` on(((`mysql`.`tbl`.`name` = `mysql`.`stat`.`table_name`) and (`mysql`.`sch`.`name` = `mysql`.`stat`.`schema_name`))))) on(((0 <> can_access_table(`mysql`.`sch`.`name`,`mysql`.`tbl`.`name`)) and (0 <> is_visible_dd_object(`mysql`.`tbl`.`hidden`)))) where ((`mysql`.`sch`.`name` collate utf8mb3_tolower_ci) = database())"
这个思路的好处是:
1)避免sql中间件解析sql和实际数据库产生差异
2)可以充分避免注释、bug、花式技巧导致的sql注入bypass,因为optimizer_trace追踪后的输出都是统一格式化后的sql
例如,1e1的解析:
EXPLAIN
SELECT GROUP_CONCAT(TABLE_NAME),1e1FROM/*
*/ information_schema.tables WHERE table_schema = DATABASE()
#解析为
"expanded_query": "/* select#1 */ select group_concat((`mysql`.`tbl`.`name` collate utf8mb3_tolower_ci) separator ',') AS `GROUP_CONCAT(TABLE_NAME)`,1e1 AS `1e1` from <constant table> join
标签:格式化,name,数据库,sql,tbl,mysql,id,schema From: https://www.cnblogs.com/k4n5ha0/p/18061870