正则表达式:从MySQL查询中提取有效的表名和列

时间:2014-12-14 04:02:41

标签: mysql regex

我试图匹配并从任何给定的MySQL查询中提取所有表名和列。

给定的查询是不带引号的(返回标记)并且根据MySQL,命名规则是:

  

不带引号的标识符中允许的字符:

     

ASCII:[0-9,a-z,A-Z $ _](基本拉丁字母,数字0-9,美元,下划线)

     

扩展:U + 0080 .. U + FFFF

对于我使用此查询的测试用例:

SELECT  users.id , users.first_name ,users.last_name,  roles.role,avatars.img_name,timezone.gmt_offset
FROM  users 
LEFT JOIN roles ON  users.role = roles.id 
LEFT JOIN  avatars ON users.avatar=avatars.id 
LEFT JOIN country ON users.country=country.country_code 
LEFT JOIN  timezone ON users.timezone = timezone.id 
WHERE (users.id >=2 AND  users.id <=4 ) OR (roles.role LIKE  'us%')
OR (roles.role =  'user(complex.sit )' && (timezone.gmt_offset >=7200
OR  users.last_name ='tryme'))
LIMIT 0 , 30

到目前为止我的正则表达式:

%[ .(),]?([a-z0-9_$]{2,})[ .(),]?(?!AND|OR|LIKE|SELECT|JOIN|ON)%i

我计划捕获组并用带有反引号的匹配包替换它问题是我无法过滤掉匹配的保留字(SELECT,JOIN ....),我有尝试添加否定前瞻但它不起作用。

第二个问题是示例= 'user(complex.sit )'中的值,我不希望它匹配这两个词(复杂的坐下)。

有什么建议吗?

2 个答案:

答案 0 :(得分:1)

该形式的另一个问题是,“如何使用Regexps(使用宿主语言YYY)操作语言XXX中的一些小程序?”基本问题是,“我如何使用regexps解析语言XXX中的程序?”正确的答案几乎总是,不要

你正走上一条流泪的道路。 Regexp并不是为了解析除了大多数琐碎,有限的语言之外的任何语言。你可能会找到一个满足你当前需求的正则表达式,但是当另一个要求出现时,你会遇到一堵砖墙。正则表达式越来越长,越来越难以理解,更不用说维护了。

要解析语言,使用解析器。在这个时间点,毫不夸张地说几乎所有平台都有几乎所有语言都可用的解析器。

我不知道您正在使用哪种语言/平台,因此我不会建议任何特定的解析器,但是对“JavaScript SQL解析器”的查询立即提出了这个问题:https://www.npmjs.com/package/simple-sql-parser。仅作为一个例子。

答案 1 :(得分:0)

%g全局修饰符与表达式一起使用:

%[\s.(),]+?([a-z\d_$]{2,})[\s.(),]*?(?:AND|OR|LIKE|SELECT|JOIN|ON|)%g