反向代理实现同域名下PHP和Java共存
1、背景介绍
之前一直从事PHP开发工作,公司内业务均由PHP实现,最近由于公司架构微调,分配了几个Java项目给团队,但是由于团队对Java不熟悉,有几人对Java理解程度也是略懂,这里说的略懂,真的是略懂,所以不敢直接改Java代码。那么怎么办呢?经过商量将Java项目的新需求,暂时还是用PHP来实现,但是有一个前提:域名和URL不能变,不能Java代码用一个域名,PHP用另外一个,因为项目提供的接口有被手机APP客户端调用,如果更改接口域名或者是URL,客户端要重新对接,假如将来PHP 要换回Java 又要重新对接,这样非常不方便,所以域名和接口URL不能变化。
新需求不外乎包含两种: 第一 更改之前的已有的功能;第二 新增之前没有的功能。
对于上面两种情况,第一种情况比较复杂,意味着要把Java已经实现的功能放弃(代码不用改),用PHP实现一遍,在此基础上添加新需求的功能,并且URL还不能变。第二种情况需要用PHP实现新功能,当然URL也是新的。根据上面分析,我们必须实现可以识别哪些URL是Java代码负责的,哪些URL是PHP代码负责的,并把它们分配到对应的服务器上去才行。
2、方案设计
根据上面的背景分析就是要实现PHP和Java处理同一个域名的不同URL请求,经过团队内部讨论可以用Nginx反向代理来实现,所谓的反向代理就是来自互联网的请求不直接访问web服务器,而是先访问反向代理服务器(我们这里用Nginx),之后Nginx服务器将请求转发到(内网环境)服务器。
具体方案如下:
首先,我们要给PHP站点和Java站点分别申请一个内网域名,例如(www.php.domain 和 www.java.domain)
1、假如需求是要更改之前java的已经实现的功能。由于此时由于URL已经存在,且不能更改,我们要把URL转到PHP服务器上去处理,这样的情况,可以在反向代理服务器上通过正则去匹配这个需要用PHP来实现已经存在的URL,之后把他rewrite到PHP处理路径再分发到PHP服务器处理(prox_pass www.php.domain)。
2、假如需求是要开发新功能。由于之前的URL不存在,首先要制定一个PHP处理URL路径约定(或者说规定),就是哪些路径下的请求是用PHP来处理的。例如:http://www.abc/php/* 这路径下所有请求都用PHP处理,其他路径的所有请求都用Java处理,这样根据Nginx Rewrite正则来匹配/php/ 路径之后rewrite到php处理路径,之后分发到PHP服务器(prox_pass www.php.domain)。
3、剩下的其他请求,还是需要java来处理,所以当上面两种URL都没有匹配上,自然就由java来处理,直接(prox_pass www.java.domain)
下面是架构图:
3、nginx配置文件代码
server{ listen 80; server_name www.abc.com; #PHP处理的请求 location ^~ /php/ { rewrite ^/php/(.*)?(.*)$ /index.php?service=$1$2 break; #重写到PHP处理(这里只是示例,大家根据自己路径更改) try_files $uri @my_php; } #原来由java处理,现在改为PHP处理的请求 location ^~ /java/urione{ rewrite ^/java/urione(.*)$ /index.php?service=Other.GetTime$1 break; #重写到PHP处理(这里只是示例,大家根据自己路径更改) try_files $uri @my_php; }
#原来该java处理的,现在还是由java处理 location / { try_files $uri @my_java; } location @my_php { proxy_pass http://www.php.domain:80; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } location @my_java { proxy_pass http://www.java.domain:80; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } }