# 网关服务

jweb-boot对jboot的网关服务做了增强,在jboot原有的功能上,增加结合nacos + jweb服务发现功能,实现根据服务名自动发现与调用。

注意

网关服务jvm启动参数需要添加:-Dsun.net.http.allowRestrictedHeaders=true,否则请求Header以下参数将无法传递给后端服务:

  private static final String[] restrictedHeaders = {
    /* Restricted by XMLHttpRequest2 */
    //"Accept-Charset",
    //"Accept-Encoding",
    "Access-Control-Request-Headers",
    "Access-Control-Request-Method",
    "Connection", /* close is allowed */
    "Content-Length",
    //"Cookie",
    //"Cookie2",
    "Content-Transfer-Encoding",
    //"Date",
    "Expect",
    "Host",
    "Keep-Alive",
    "Origin",
    // "Referer", 
    // "TE",
    "Trailer",
    "Transfer-Encoding",
    "Upgrade",
    //"User-Agent",
    "Via"
    };

    action = new sun.security.action.GetBooleanAction( "sun.net.http.allowRestrictedHeaders")
    allowRestrictedHeaders = ((Boolean)java.security.AccessController.doPrivileged(action)).booleanValue();
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27

# 配置

在配置网关服务时,需要先开启服务发现模块

#--------jweb 网关路由配置 start--------
# 需要配合配置 ---jweb 服务发现配置---
# 熔断限流支持需要配置 ---jweb 熔断限流sentinel配置---
# 匹配示例
jweb.gateway.demo.enable = true
jweb.gateway.demo.name = demo
# 网关路由目标地址
# 支持{target.jweb.discovery.serviceName}的配置,动态选择健康的服务路由
jweb.gateway.demo.uri = http://{demo}
# 是否开启uri健康检查,默认false
jweb.gateway.demo.uriHealthCheckEnable = false
# 健康检查访问路径: {uri} + {checkPath}, 默认为 空, 返回200表示健康,每10s检查一次 
jweb.gateway.demo.uriHealthCheckPath = /your-health-check-path
jweb.gateway.demo.pathStartsWith = /demo/
# 路径重写,格式:【正则匹配】,【替换字符】。
# 目前简单使用java的,String.replaceAll来替换重写
jweb.gateway.demo.pathRewrite = /demo/,/
# 上下文路径配置
# 该配置将以Header值的形式传递给被代理的目标,
# 具体返回的html页面中的引用资源路径,需要开发者自动添加contextPath前缀,以适应网关再次过滤代理
# jweb.gateway.demo.contextPath = /demo/
# 是否启用网关代理限流熔断
# jweb.gateway.demo.sentinelEnable = false
# 被限流后跳转页面地址
#jweb.gateway.demo.sentinelBlockPage = /block
# 被限流后显示的json内容,如果有配置 sentinelBlockPage,则 sentinelBlockJsonMap 配置无效
#jweb.gateway.demo.sentinelBlockJsonMap ={"block":true}

#--------jweb 网关路由配置 end--------
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29

# 实例

  1. 根据 快速开始 分别创建网关服务-gateway测试服务-demo
  2. 创建网关服务配置文件jboot.properties:
undertow.host=0.0.0.0
undertow.port=80



#服务名配置
jweb.serviceName=gateway



#--------jweb 服务发现配置 start--------
#服务发现开启
jweb.discovery.enable=true
#服务名称,服务关键字,后继调用服务dns名(必填)
jweb.discovery.serviceName=${jweb.serviceName}
#Nacos注册中心地址
jweb.discovery.registerAddress=http://localhost:8848
#命名空间,默认值:public(可选)
#jweb.discovery.namespace=public
#分组名称,默认值:DEFAULT_GROUP(可选)
#jweb.discovery.groupName=dev
#所属集群名称配置,默认值:DEFAULT(可选)
#jweb.discovery.clusterName=TEST
#是否为临时节点实例,默认:true。 true: 临时节点实现;false:为持久化实例;(可选)
#若为临时节点实例,客户端会主动产生上报心跳,来维护节点健康状况
#若为持久化实例,nacos服务器会主动检测服务健康状况,根据集群配置相应检测类型:TCP,HTTP,NONE
jweb.discovery.ephemeral=false
#优先使用的注册的ip段。在一台服务器有多个网卡ip时,优先使用以下ip段(可选)
jweb.discovery.preferredNetworks=192.168.2,10.0
#忽略指定关键字的网卡。在一台服务器有多个网卡ip时,忽略包含以下关键字的网卡名(统一转小写)(可选)
#jweb.discovery.ignoredInterfaces=virtual,docker0,veth,hyper-v,vmware,vmnet,tap,docker,flannel,cni
#--------jweb 服务发现配置 end--------




#--------jweb 网关路由配置 start--------
# 需要配合配置 ---jweb 服务发现配置---
# 熔断限流支持需要配置 ---jweb 熔断限流sentinel配置---
# path 匹配示例
jweb.gateway.demo.enable = true
jweb.gateway.demo.name = demo
# 网关路由目标地址
# 支持{target.jweb.discovery.serviceName}的配置,动态选择健康的服务路由
jweb.gateway.demo.uri = http://{demo}
# 是否开启uri健康检查,默认false
jweb.gateway.demo.uriHealthCheckEnable = false
# 健康检查访问路径: {uri} + {checkPath}, 默认为 空, 返回200表示健康,每10s检查一次 
jweb.gateway.demo.uriHealthCheckPath = /your-health-check-path
jweb.gateway.demo.pathStartsWith = /demo/
# 路径重写,格式:【正则匹配】,【替换字符】。
# 目前简单使用java的,String.replaceAll来替换重写
jweb.gateway.demo.pathRewrite = /demo/,/
# 上下文路径配置
# 该配置将以Header值的形式传递给被代理的目标,
# 具体返回的html页面中的引用资源路径,需要开发者自动添加contextPath前缀,以适应网关再次过滤代理
# jweb.gateway.demo.contextPath = /demo/
# 是否启用网关代理限流熔断
# jweb.gateway.demo.sentinelEnable = false
# 被限流后跳转页面地址
#jweb.gateway.demo.sentinelBlockPage = /block
# 被限流后显示的json内容,如果有配置 sentinelBlockPage,则 sentinelBlockJsonMap 配置无效
#jweb.gateway.demo.sentinelBlockJsonMap ={"block":true}
#--------jweb 网关路由配置 end--------
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
  1. 创建demo工程配置文件jboot.properties
#绑定服务端口不限ip地址
undertow.host=0.0.0.0

#服务名配置
jweb.serviceName=demo


#--------jweb 服务发现配置 start--------
#服务发现开启
jweb.discovery.enable=true
#服务名称,服务关键字,后继调用服务dns名(必填)
jweb.discovery.serviceName=${jweb.serviceName}
#Nacos注册中心地址
jweb.discovery.registerAddress=http://localhost:8848
#命名空间,默认值:public(可选)
#jweb.discovery.namespace=public
#分组名称,默认值:DEFAULT_GROUP(可选)
#jweb.discovery.groupName=dev
#所属集群名称配置,默认值:DEFAULT(可选)
#jweb.discovery.clusterName=TEST
#是否为临时节点实例,默认:true。 true: 临时节点实现;false:为持久化实例;(可选)
#若为临时节点实例,客户端会主动产生上报心跳,来维护节点健康状况
#若为持久化实例,nacos服务器会主动检测服务健康状况,根据集群配置相应检测类型:TCP,HTTP,NONE
jweb.discovery.ephemeral=false
#优先使用的注册的ip段。在一台服务器有多个网卡ip时,优先使用以下ip段(可选)
jweb.discovery.preferredNetworks=192.168.2,10.0
#忽略指定关键字的网卡。在一台服务器有多个网卡ip时,忽略包含以下关键字的网卡名(统一转小写)(可选)
#jweb.discovery.ignoredInterfaces=virtual,docker0,veth,hyper-v,vmware,vmnet,tap,docker,flannel,cni
#--------jweb 服务发现配置 end--------
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
  1. 在网关服务启动界面上添加jvm启动参数 -Dsun.net.http.allowRestrictedHeaders=true
  2. 启动Nacos服务
    可参考Nacos官方文档快速开始 (opens new window)文档启动一个Nacos服务。
    启动成功后,访问[http://127.0.0.1:8848/nacos]{http://127.0.0.1:8848/nacos}可进入Nacos控制台
  3. 修改demo服务的IndexController.java代码如下:
package cc.jweb.demo.index.controller;

import cc.jweb.boot.app.JwebApplication;
import cc.jweb.boot.controller.BaseController;
import io.jboot.aop.annotation.ConfigValue;
import io.jboot.web.controller.annotation.RequestMapping;

@RequestMapping(value = "/")
public class IndexController extends BaseController {

    @ConfigValue("undertow.port")
    int port;

    public static void main(String[] args) {
        JwebApplication.main(args);
    }

    public void index() {
        renderText("This is Demo Server (" + port + ")!");
    }
}

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
  1. 分别启动 gateway服务demo服务,已配置的端口分别是808080
  2. 浏览器访问网关服务地址http://localhost:80/demo/ (opens new window),你将看到This is Demo Server (8080)!字样

至此,你已经完成网关的代理访问了。

# 负载代理

  1. 复制IndexController的运行配置,修改VM参数为-Dundertow.port=8081,配置如下:
    demo2配置
    然后执行,启动第二个demo服务,端口:8081。
  2. 再次访问网关服务地址:http://localhost:80/demo/ (opens new window),刷新页面。
    页面内容将在This is Demo Server (8080)!This is Demo Server (8081)!之间进行负载切换!
  3. 查看Nacos控制台服务列表,demo服务有两个健康实例: list list

至此,你已经完成网关的代理与负载均衡访问了。

# 网关限流

在使用限流之前,请先配置Sentinel限流配置。然后再开启网关限流开关:jweb.gateway.demo.sentinelEnable = true

# 性能测试

LINUX下压测代理性能说明:
测试链路:ab测试--->GW服务器--->SERVICE服务器
被测机:两台服务器4cpu(i5-4590 3.30GHz)16G Centos 7。GW与SERVICE
测试机:4cpu(i5-4590 3.30GHz)16G Centos 7
命令:ab -c 1000 -n 10000 GW.targetUrl
接口:仅输出32个字符,无其它代码逻辑
结果:14000+- tps(GW -> SERVICE)