前语
- 你有没有想过
idea
是怎么做到sql
关键字语法高亮的?毫无疑问需求识别出sql
的关键字。
antlr
- antlr 便是这么一个东西,他能够解析
sql
,下面咱们经过他来完结表名的获取
装置
antlr-tools
- 首先咱们下载上面的
antlr
东西 , 然后再经过东西分析每种sql
的语法,每种sql
的语法需求咱们额定准备,你能够自己将sql 的语法编写好,这儿我就直接运用官方供给的语法了。
sql语法
git clone https://github.com/antlr/grammars-v4.git
- 在开端
sql
解析之前,咱们先将焦点移到antlr
,antlr
是一个语法解析器东西,sql
仅仅其间一个解析,所以咱们先开端一段简略的语法解析吧。
装置文档
windows装置
- 上方文档咱们移动到windows章节,首先
antlr
需求java
环境,然后将上方咱们下载antlr-4.11.1-complete.jar
装备到环境变量中。官网也说到了装备环境变量能够在终端中暂时装备也能够在系统环境变量中永久装备。
暂时装备环境变量
- 在终端中履行
SET CLASSPATH=.;C:\Javalib\antlr-4.11.1-complete.jar;%CLASSPATH%
即可在终端中暂时设置了变量。
永久装备环境变量
- 这样装备只要是新翻开的终端都是能够获取到
CLASSPATH
这个环境变量的。
小结
- 这儿需求注意的是,在装备
CLASSPATH
这个环境变量时有必要装备.
, 如果不装备在履行到grun
指令时会报错Can't load Hello as lexer or parser
。
antlr4&&grun
- 由于
antrl4
根据java
包,每次运行要从java
调用,为了方便运用写一个批处理文件(.bat文件)放在antlr-4.11.1-complete.jar
同一文件夹下,自己命名,我命名为antlr4.bat
- 为了能够访问咱们的自界说脚本,这儿咱们需求将
antlr-4.11.1-complete.jar
所在目录装备成环境变量。我这儿是E:/study/antlr/antlr-4.11.1-complete.jar
- 然后咱们就能够在
E:\study\antlr
的目录下新建一个脚本antlr4.bat
, 内容如下
doskey antlr4=java org.antlr.v4.Tool $*
doskey grun=java org.antlr.v4.gui.TestRig $*
- 这样咱们能够履行
antlr4.bat
指令后就能够在终端履行antlr4&&grun
指令了。官网也介绍到咱们能够分别为antlr4
和grun
创建脚本
antlr4.bat
java org.antlr.v4.Tool %*
grun.bat
@ECHO OFF
SET TEST_CURRENT_DIR=%CLASSPATH:.;=%
if "%TEST_CURRENT_DIR%" == "%CLASSPATH%" ( SET CLASSPATH=.;%CLASSPATH% )
@ECHO ON
java org.antlr.v4.gui.TestRig %*
测验
- 到了这儿咱们的
antlr4
现已装置完结了,那么咱们该怎么进行语法测验呢?
grammar Hello; // 1、界说文法的姓名
s : 'hello' ID ; // 3、匹配关键字hello和标志符
ID : [a-z]+ ; // 标志符由小写字母组成
WS : [ \t\r\n]+ -> skip ; // 4、越过空格、制表符、回车符和换行符
- 下面针对语法进行相关解释:
- 界说了 grammar 的姓名,姓名需求与文件名对应
- s界说的语法,会运用到下方界说的正则表达式词法
- 界说了空白字符,后边的 skip 是一个特殊的符号,符号空白字符会被忽略。
grammar Hello;
r : 'hello' ID ;
ID : [a-z]+ ;
WS : [ \t\r\n]+ -> skip ;
翻开终端
- 针对新翻开的终端咱们履行
antlr4
就会履行咱们装备的E:\study\antlr\antlr4.bat
脚本。履行完结之后就能够履行内部指令了。
- 经过
antlr4 Hello.g4
进行语法翻译
- 会生成一些Java类,这些类便是咱们用来解析相关文本的东西类。为了能够履行这些Java 咱们先
javac
编译一下
javac Hello*.java
grun解析
- 下面咱们经过
grun
进行demo解析
grun Hello r -tree
- 如下指令就会进行等候咱们输入文本。
Hello.g4
的语法便是hello [a-z]+
这个正则,也便是一切的hello开头的文本,中间一个空格后边跟着由小写字母组成的字符的整个文本就会被解析出来。
(注意:^D
在 Unix 上表明 control-D 并表明“输入完毕”;^Z
在 Windows 上运用。)
Linux装置
- windows是大多数人运用的系统,可是Linux才是终究的服务环境,加之我本身便是Linux作为开发环境,所以Linux装置对于我而言很重要。
- 由于
antlr
本事便是jar ,得以与java的跨平台所以这儿资源两个系统是能够通用的。 - linux上装备环境变量更方便,咱们只需求在
~/.bashrc
或许~/.zshrc
中装备即可
export CLASSPATH=".:/home/zxhtom/zxh/antlr/antlr-4.11.1-complete.jar:$CLASSPATH"
- 在终端中给指令创建别名
alias antlr4='java -Xmx500M -cp "/home/zxhtom/zxh/antlr/antlr-4.11.1-complete.jar:$CLASSPATH" org.antlr.v4.Tool'
alias grun='java -Xmx500M -cp "/home/zxhtom/zxh/antlr/antlr-4.11.1-complete.jar:$CLASSPATH" org.antlr.v4.gui.TestRig'
- 或许咱们也能够依照windows方法的指令,其实终究都是履行相同的类
alias antlr4='java org.antlr.v4.Tool '
alias grun='java org.antlr.v4.gui.TestRig'
- export和alias能够一起装备在
~/.zshrc
中。
可视化
-
TestRig
充当一款调试东西,官网建议咱们将它重命名为grun
- 直接输入
grun
能够看到其支撑的参数。
参数 | 功能 |
---|---|
-tokens | 打印出词法符号流 |
-tree | LISP格式打印分析树,啥叫LISP? |
-gui | 可视化打印分析树 |
-ps fiels.ps | 以PostScript格式生成可视化语法分析树 |
-trace | 打印规矩的姓名以及进入和脱离该规矩时的语法符号 |
- 不管是linux还是windows咱们都能够经过
-gui
的方法进行可视化
自界说解析
- 从
4.11
开端,antlr大约支撑10种言语进行语法解析,上面案列中我运用的是Java
言语的解析东西,只需求javac
编译一次即可,或许直接将相关的Java
代码拷贝到项目中进行调用。下面咱们看看怎么生成Python
言语的解析代码吧。
python
pip3 install antlr4-python3-runtime
- 由于是测验
python
的语法生成,这儿就不装备快捷指令了,所以这儿运用全指令java -jar ../antlr-4.11.1-complete.jar -Dlanguage=Python3 Hello.g4
import sys
from antlr4 import *
from HelloLexer import HelloLexer
from HelloParser import HelloParser
def main(argv):
input = FileStream(argv[1])
lexer = HelloLexer(input)
stream = CommonTokenStream(lexer)
parser = HelloParser(stream)
tree = parser.r()
print(tree.toStringTree(recog=parser))
if __name__ == '__main__':
main(sys.argv)
- 上述代码便是咱们对
antlr
生成的解析代码的运用,这样咱们能够进行自界说的处理。
解析Mysql
<dependency>
<groupId>org.antlr</groupId>
<artifactId>antlr4</artifactId>
<version>4.11.1</version>
</dependency>
- 版别需求保持一致。
- 上一章节中咱们经过一个简略的
Hello.g4
语法进行Java
、python
等言语的解析代码的生成。上章节也说到antlr
是一个语法解析东西,并不仅仅是解析sql
, 理论上他能解析一切的语法,比方你自己有一套语法怎么让antlr
解析呢?你只需求依照antlr
的规矩用antlr
的言语表达出你自己的语法,现在比较规范的便是https://github.com/antlr/grammars-v4.git
这个库房供给的语法解析树了,本次对mysql
解析也是运用这个库房下供给的g4
文件。
- 这个库房给咱们供给了
MySqlLexer.g4
和MySqlParser.g4
两个文件,前者是Mysql
的关键词,后者便是Mysql
的语法装备。examples是作者给咱们供给的Mysql
相关的sql 。 咱们能够用来测验用。 - 为了方便测验,这儿咱们将这两个
g4
文件拷贝到其他目录下履行生成Java
解析代码
antlr4 MySqlParser.g4 MySqlLexer.g4
- 两个文件没有先后顺序差异,可是要注意的是不能缺少。笔者便是一开端认为只需求
MysqlParser.g4
一再在报错。MySqlParser.g4:2595:37: cannot create implicit token for string literal in non-combined grammar: '|'
。 - 履行完上述指令后,咱们就能够看到咱们的Java代码了.
- 这样的代码是没有包名的,好在
antlr
在生成代码时支撑指定包名。antlr4 MySqlParser.g4 MySqlLexer.g4 -package com.github.zxhtom.mysql