可以在github上找到nginx-java-parser工具,项目地址:https://github.com/odiszapc/nginx-java-parser,
解析nginx.conf过程可以参考该项目的README.md
<!-- https://mvnrepository.com/artifact/com.github.odiszapc/nginxparser -->
<dependency>
<groupId>com.github.odiszapc</groupId>
<artifactId>nginxparser</artifactId>
<version>0.9.3</version>
</dependency>
stream {
upstream test {
server 172.0.0.1:8080;
}
server {
listen 80;
proxy_responses 1;
proxy_timeout 20s;
proxy_pass test;
}
}
http {
server {
resolver 8.8.8.8;
listen 4569;
proxy_connect;
proxy_connect_allow 443;
proxy_connect_connect_timeout 10s;
proxy_connect_read_timeout 10s;
proxy_connect_send_timeout 10s;
location / {
set $passport 80;
if ($request_method ~ "get" )
{
return 403;
}
if ($scheme = 'http')
{
proxy_pass http://$host:$passport$request_uri;
}
if ($scheme = 'https')
{
proxy_pass http://$host;
}
proxy_set_header HOST $host;
proxy_buffers 256 4k;
proxy_max_temp_file_size 0k;
proxy_connect_timeout 30;
proxy_send_timeout 60;
proxy_read_timeout 60;
proxy_next_upstream error timeout invalid_header http_502;
}
}
}
public static void main(String[] args) throws IOException {
//NgxConfig.read(配置文件路径);读取配置文件
//new NgxBlock();新建一个block块,
//new NgxParam();新建param数据,比如listen 80;
//NgxDumper ngxDumper = new NgxDumper(ngxConfig);
//String rs = ngxDumper.dump();输出成字符串
//查找指定配置项
//NgxBlock members = block.findBlock(“server”);
//NgxParam bHealthyCheck = block.findParam(“Listener”);
//Collection entries = members.getEntries();
//ListserverList=ngxHttpBlock.findAll(NgxConfig.BLOCK,“server”);
//从查找的配置中取值,例如listen 80,name为listen,value为80
//String state = ngxParam.getValue()
//String state = ngxParam.getName()
//我将配置文件中的一个{}理解为一个块,前面的stream为value,value可以为多个,中间以空格分隔,块中的entry可以为block也可以为param
//NgxConfig.read(配置文件路径)用来读取配置文件
NgxConfig ngxConfig = NgxConfig.read("D:\\srv\\nginx.conf");
//找到名字为stream的块
NgxBlock ngxBlockStream = ngxConfig.findBlock("stream");
if (ngxBlockStream==null){
//如果没找到value为stream的块,则新建一个value为stream的block,将其加到ngxConfig中
ngxBlockStream = new NgxBlock();
ngxBlockStream.addValue("stream");
ngxConfig.addEntry(ngxBlockStream);
}
NgxBlock ngxBlockUpStream = new NgxBlock();
//将upstream块加入Stream块
ngxBlockStream.addEntry(ngxBlockUpStream);
ngxBlockUpStream.addValue("upstream");
ngxBlockUpStream.addValue("test");
NgxParam ngxParam = new NgxParam();
ngxParam.addValue("server 172.0.0.1:8080");
//将内容为server 172.0.0.1:8080的param加入到upstream块中
ngxBlockUpStream.addEntry(ngxParam);
NgxBlock ngxBlockServer = new NgxBlock();
//将server块加入Stream块
ngxBlockStream.addEntry(ngxBlockServer);
ngxBlockServer.addValue("server");
//param会自动在最后加上;\n
//为了一次性写入四个我采取了以下方式
//如果要分开写,可以分别new NgxParam();然后addValue("listen 80")
ngxParam = new NgxParam();
ngxParam.addValue("listen 80;\n" +
"\tproxy_responses 1;\n" +
"\tproxy_timeout 20s;\n" +
"\tproxy_pass test";
//将param加入到server块中
ngxBlockServer.addEntry(ngxParam);
//使用NgxDumper将内容输出
NgxDumper ngxDumper = new NgxDumper(ngxConfig);
System.out.println(ngxDumper.dump());
//if和(之间必须以空格分隔开,否则启动nginx时会报错
if ($request_method ~ "get" ) {}
在nginxparser框架中,对于if的处理存在问题,代码如下
private void writeToStream(NgxBlock config, PrintWriter writer, int level) {
Iterator i$ = config.iterator();
while(i$.hasNext()) {
NgxEntry entry = (NgxEntry)i$.next();
NgxEntryType type = NgxEntryType.fromClass(entry.getClass());
switch(type) {
case BLOCK:
NgxBlock block = (NgxBlock)entry;
writer.append(this.getOffset(level)).append(block.toString()).append(this.getLineEnding());
this.writeToStream(block, writer, level + 1);
writer.append(this.getOffset(level)).append("}").append(this.getLineEnding());
break;
case IF:
NgxIfBlock ifBlock = (NgxIfBlock)entry;
writer.append(this.getOffset(level)).append(ifBlock.toString()).append(this.getLineEnding());
this.writeToStream(ifBlock, writer, level + 1);
//append中加入的{导致if{}成了if{{
writer.append(this.getOffset(level)).append("{").append(this.getLineEnding());
//此处缺少break;
case COMMENT:
case PARAM:
writer.append(this.getOffset(level)).append(entry.toString()).append(this.getLineEnding());
}
}
writer.flush();
}
//使用这方法你会发现最后if(){}还丢失了()