当前位置: 首页 > news >正文

【技巧】SpringCloud Gateway实现多子域(单个应用开放多个端口)

0. 目录

      • 1. 需求背景
      • 2. 实现
      • 3. 额外 - 其它Servlet容器实现
        • 3.1 Undertow
        • 3.2 Tomcat
      • 4. 相关

1. 需求背景

浏览器针对单个网站地址(ip+port)存在“6个请求”限制;通过多子域配置可以突破这个限制,增加网站的响应效率,尤其是针对三维服务这类大请求量服务。

注意:

  1. 多子域的目的是为了突破浏览器"6个请求"的限制(【浏览器请求并发限制】,与后端应用提供的业务功能无关。
  2. 这个配置项的底层实现原理其实就是为当前网站增加几个访问端口,比如除了原始的123端口之外,还可以通过456,777端口访问;仅此而已,没有任何业务功能上的变化和影响。
  3. 浏览器对于"同一个网址"采取的是 ip + port 的组合认定,只有两者都相同才会认定为同一个网站,这也是通过开放多个端口就可以突破该项限制的原因。

2. 实现

本项功能需求的应用场景比较窄,因此这里直接给出解决方案,不做原理性解读。

以下三个类拷贝到项目中即可。

// ============================== 1/3 MultiportNettyWebServer
// 组合模式
public class MultiportNettyWebServer implements WebServer {private final List<NettyWebServer> servers;public MultiportNettyWebServer(List<NettyWebServer> servers) {this.servers = servers;}@Overridepublic void start() throws WebServerException {servers.stream().forEach(server -> server.start());}@Overridepublic void shutDownGracefully(GracefulShutdownCallback callback) {servers.stream().forEach(server -> server.shutDownGracefully(callback));}@Overridepublic void stop() throws WebServerException {servers.stream().forEach(server -> server.stop());}@Overridepublic int getPort() {return -1;}}// ============================== 2/3 MultiportNettyReactiveWebServerFactory
public class MultiportNettyReactiveWebServerFactory extends NettyReactiveWebServerFactory {@Overridepublic WebServer getWebServer(HttpHandler httpHandler) {NettyWebServer webServer = (NettyWebServer)super.getWebServer(httpHandler);List<NettyWebServer> newArrayList = CollUtil.newArrayList(webServer);// 这里并不是原地修改, 生效的是方法的返回值对象; 所以这里还得塞回去...// 这个思路其实很好, 保证对象的不可变....HttpServer httpServer = Convert.convert(HttpServer.class, ReflectUtil.getFieldValue(webServer, "httpServer"));httpServer = httpServer.port(81);ReflectUtil.setFieldValue(webServer, "httpServer", httpServer);webServer = (NettyWebServer)super.getWebServer(httpHandler);newArrayList.add(webServer);httpServer = Convert.convert(HttpServer.class, ReflectUtil.getFieldValue(webServer, "httpServer"));httpServer = httpServer.port(82);ReflectUtil.setFieldValue(webServer, "httpServer", httpServer);return new MultiportNettyWebServer(newArrayList);}
}// ============================== 3/3 MultiportNettyReactiveWebServerFactory
/*** COPY FROM {@code ReactiveWebServerFactoryConfiguration&EmbeddedNetty}*/
@Configuration
public class MultiportNettyWebServerConfig {@Bean@ConditionalOnMissingBeanReactorResourceFactory reactorServerResourceFactory() {return new ReactorResourceFactory();}@BeanNettyReactiveWebServerFactory nettyReactiveWebServerFactory(ReactorResourceFactory resourceFactory,ObjectProvider<NettyRouteProvider> routes, ObjectProvider<NettyServerCustomizer> serverCustomizers) {NettyReactiveWebServerFactory serverFactory = new MultiportNettyReactiveWebServerFactory();serverFactory.setResourceFactory(resourceFactory);routes.orderedStream().forEach(serverFactory::addRouteProviders);serverFactory.getServerCustomizers().addAll(serverCustomizers.orderedStream().collect(Collectors.toList()));return serverFactory;}}

3. 额外 - 其它Servlet容器实现

3.1 Undertow
@Slf4j
@Configuration
@ConditionalOnClass({Servlet.class, Undertow.class, SslClientAuthMode.class})
// 参考自: ServletWebServerFactoryConfiguration.EmbeddedUndertow.java
public class WebServerMultiPortConfigByUndertow implements WebServerFactoryCustomizer<UndertowServletWebServerFactory> {/*** 多个端口*/@Overridepublic void customize(UndertowServletWebServerFactory factory) {if (ArrayUtil.isEmpty(multiports)) {log.warn("### there is no multi-port config. so skip it");return;}final String[] finalMultiports = new String[]{"81", "82"};factory.addBuilderCustomizers(s -> {log.warn("### 启用Undertow容器, 配置多端口 [ {} ]", Arrays.toString(finalMultiports));Arrays.stream(finalMultiports).forEach(port -> s.addHttpListener(Convert.toInt(port), "0.0.0.0"));});}
}
3.2 Tomcat
@Slf4j
@Configuration
// 参考自: ServletWebServerFactoryConfiguration.EmbeddedTomcat.java
@ConditionalOnClass({ Servlet.class, Tomcat.class, UpgradeProtocol.class }) 
public class WebServerMultiPortConfigByTomcat implements WebServerFactoryCustomizer<TomcatServletWebServerFactory> {/*** 多个端口*/@Overridepublic void customize(TomcatServletWebServerFactory factory) {factory.addAdditionalTomcatConnectors(addtionalConnetors());}private Connector[] addtionalConnetors() {final String[] multiPorts = new String[]{"81", "82"};log.warn("### 启用Tomcat容器, 配置多端口 [ {} ]", Arrays.toString(multiPorts));List<Connector> connectors = new ArrayList<>();for (String s : multiPorts) {Connector connector = new Connector("HTTP/1.1");connector.setPort(Integer.parseInt(s));connector.setScheme("http");connectors.add(connector);}return connectors.toArray(new Connector[] {});}
}

4. 相关

  1. 【浏览器请求并发限制】
  2. Spring Boot中为Tomcat配置多个监听端口

相关文章:

  • Shell输入输出重定向
  • 实用工具:实时监控服务器CPU负载状态并邮件通知并启用开机自启
  • 14-Linux部署Hadoop集群
  • 高中数学:函数的单调性
  • 使用npm i命令时一直idealTree:npm: sill idealTree buildDeps卡住不动
  • 蓝桥杯倒计时41天!DFS进阶1——回溯
  • Vue+Flask电商后台管理系统
  • 【一起学习Arcade】(6):属性规则实例_约束规则和验证规则
  • 记录一次主机不能登录的异常现象解决的问题
  • 自动粘贴与网址管理,让您的网络生活更便捷!“
  • 04锁机制-分布式锁
  • 云上攻防-云原生篇Docker安全系统内核版本漏洞CDK自动利用容器逃逸
  • 人工智能_大模型013_AIGC生成式模型的增强检索_RAG知识补充检索_补充私域和实时场景知识_关键字检索增强---人工智能工作笔记0149
  • 基于yolov5的电瓶车和自行车检测系统,可进行图像目标检测,也可进行视屏和摄像检测(pytorch框架)【python源码+UI界面+功能源码详解】
  • 2403d,d的108版本更改
  • IE报vuex requires a Promise polyfill in this browser问题解决
  • Java 实战开发之spring、logback配置及chrome开发神器(六)
  • jquery ajax学习笔记
  • mongo索引构建
  • Mysql5.6主从复制
  • PermissionScope Swift4 兼容问题
  • react-core-image-upload 一款轻量级图片上传裁剪插件
  • React中的“虫洞”——Context
  • SegmentFault 社区上线小程序开发频道,助力小程序开发者生态
  • Spring声明式事务管理之一:五大属性分析
  • SQL 难点解决:记录的引用
  • -- 查询加强-- 使用如何where子句进行筛选,% _ like的使用
  • 开放才能进步!Angular和Wijmo一起走过的日子
  • 漂亮刷新控件-iOS
  • 前端临床手札——文件上传
  • 前端性能优化——回流与重绘
  • 如何使用Mybatis第三方插件--PageHelper实现分页操作
  • 使用iElevator.js模拟segmentfault的文章标题导航
  • 微服务入门【系列视频课程】
  • #我与Java虚拟机的故事#连载03:面试过的百度,滴滴,快手都问了这些问题
  • (+4)2.2UML建模图
  • (Arcgis)Python编程批量将HDF5文件转换为TIFF格式并应用地理转换和投影信息
  • (C语言)球球大作战
  • (html5)在移动端input输入搜索项后 输入法下面为什么不想百度那样出现前往? 而我的出现的是换行...
  • (vue)el-checkbox 实现展示区分 label 和 value(展示值与选中获取值需不同)
  • (多级缓存)多级缓存
  • (三维重建学习)已有位姿放入colmap和3D Gaussian Splatting训练
  • (太强大了) - Linux 性能监控、测试、优化工具
  • (转)IIS6 ASP 0251超过响应缓冲区限制错误的解决方法
  • .“空心村”成因分析及解决对策122344
  • .NET CORE Aws S3 使用
  • .NET Core WebAPI中使用Log4net 日志级别分类并记录到数据库
  • .NET Core 通过 Ef Core 操作 Mysql
  • .NET Framework 服务实现监控可观测性最佳实践
  • .NetCore部署微服务(二)
  • .NET下ASPX编程的几个小问题
  • /bin、/sbin、/usr/bin、/usr/sbin
  • /bin/bash^M: bad interpreter: No such file or directory
  • @property括号内属性讲解
  • [ C++ ] STL_vector -- 迭代器失效问题