spring-boot 实现接口转发服务,同时支持get 和 post等多种请求
spring-boot 实现接口转发服务,同时支持get 和 post等多种请求
(1)新建类:ProxyController.java
package com.taobao.product.controller;import com.taobao.framework.HttpResult;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.ResponseEntity;
import org.springframework.web.client.RestTemplate;import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;import javax.servlet.http.HttpServletRequest;
import java.net.URISyntaxException;
import java.util.Enumeration;import org.springframework.http.MediaType;
import java.io.IOException;
import java.net.URI;
import java.util.Collections;
import java.util.List;import java.security.KeyManagementException;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import javax.net.ssl.SSLContext;
import javax.net.ssl.TrustManager;
import javax.net.ssl.X509TrustManager;
import org.apache.http.conn.ssl.NoopHostnameVerifier;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.impl.client.HttpClients;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;/*** @Author: sunkaiyuan* @Date: 2023-05-23 9:02* @Desperation: TODO*/
@Api(tags = "代理服务")
@RestController
@RequestMapping("/proxy")
@Slf4j
public class ProxyController {@ApiOperation(value = "接口转发")@RequestMapping("/dahua/**")public ResponseEntity<String> handleRequest(HttpServletRequest request) throws IOException, URISyntaxException, NoSuchAlgorithmException, KeyStoreException, KeyManagementException {String method = request.getMethod();String path = getPath(request);// 去掉url中的/proxy/dahuapath = path.substring(request.getContextPath().length() + "/proxy/dahua".length());URI targetUri = new URI("https://121.26.142.174:8443" + path);System.out.println(targetUri);HttpHeaders headers = getRequestHeaders(request);HttpEntity<?> entity = new HttpEntity<>(headers);RestTemplate restTemplate = new RestTemplate(getSecureHttpRequestFactory());if (method.equalsIgnoreCase(HttpMethod.GET.name())) {return restTemplate.exchange(targetUri, HttpMethod.GET, entity, String.class);} else if (method.equalsIgnoreCase(HttpMethod.POST.name())) {String requestBody = getRequestBody(request);headers.setContentType(MediaType.APPLICATION_JSON);HttpEntity<String> postEntity = new HttpEntity<>(requestBody, headers);return restTemplate.exchange(targetUri, HttpMethod.POST, postEntity, String.class);} else {return ResponseEntity.badRequest().body("Unsupported request method: " + method);}}private String getPath(HttpServletRequest request) {String contextPath = request.getContextPath();String servletPath = request.getServletPath();String pathInfo = request.getPathInfo() != null ? request.getPathInfo() : "";return contextPath + servletPath + pathInfo;}private HttpHeaders getRequestHeaders(HttpServletRequest request) {HttpHeaders headers = new HttpHeaders();Enumeration<String> headerNames = request.getHeaderNames();while (headerNames.hasMoreElements()) {String headerName = headerNames.nextElement();List<String> headerValues = Collections.list(request.getHeaders(headerName));headers.put(headerName, headerValues);}return headers;}private String getRequestBody(HttpServletRequest request) throws IOException {return request.getReader().lines().reduce("", (accumulator, actual) -> accumulator + actual);}private HttpComponentsClientHttpRequestFactory getSecureHttpRequestFactory() throws NoSuchAlgorithmException, KeyStoreException, KeyManagementException {TrustManager[] trustAllCerts = new TrustManager[] { new X509TrustManager() {public X509Certificate[] getAcceptedIssuers() {return null;}public void checkClientTrusted(X509Certificate[] certs, String authType) {}public void checkServerTrusted(X509Certificate[] certs, String authType) throws CertificateException {}} };SSLContext sslContext = SSLContext.getInstance("TLS");sslContext.init(null, trustAllCerts, null);SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext, NoopHostnameVerifier.INSTANCE);HttpComponentsClientHttpRequestFactory requestFactory = new HttpComponentsClientHttpRequestFactory();requestFactory.setHttpClient(HttpClients.custom().setSSLSocketFactory(csf).build());return requestFactory;}
}
(2)代码说明:
这是一个 Java 类,名称为 ProxyController。代码中包含以下方法:
handleRequest(HttpServletRequest request)
这是一个公共方法,返回类型为 ResponseEntity<String>,会抛出一些可能的异常。该方法的目的是根据传入的请求对象处理 HTTP 请求并返回相应的响应。该方法被注解 @RequestMapping("/dahua/**") 所标记,它表示当 URL 包含 /proxy/dahua 的时候,该方法才会被调用。该方法实现了将传入的请求转发到另一个 URL 并返回响应的功能。如果请求不是 GET 或 POST,则会返回一个错误响应。
getPath(HttpServletRequest request)
这是一个私有方法,返回类型为 String。该方法接收一个请求对象,从中获取上下文路径、Servlet 路径和路径信息,并将它们组合成完整的 URL 路径并返回。
getRequestHeaders(HttpServletRequest request)
这是一个私有方法,返回类型为 HttpHeaders。该方法接收一个请求对象,从中获取所有请求头,并将它们放入一个新的 HttpHeaders 对象中,然后返回该对象。
getRequestBody(HttpServletRequest request)
这是一个私有方法,返回类型为 String,可能会抛出 IO 异常。该方法接收一个请求对象,从中获取请求体(如果有),将其转换为字符串,并返回该字符串。
getSecureHttpRequestFactory()
这是一个私有方法,返回类型为 HttpComponentsClientHttpRequestFactory,可能会抛出一些异常。该方法的目的是创建一个安全的 HTTP 请求工厂,使我们可以通过 HTTPS 连接到另一个 URL。该方法使用 TrustManager 和 SSLContext 来实现信任所有证书,并将其设置为请求工厂中的 SSL 套接字工厂,然后返回该请求工厂。
除此之外,代码还包含一些注解和变量声明。其中,@ApiOperation 注解表示该方法具有操作说明信息;@RequestMapping("/dahua/**") 表示当 URL 包含 /proxy/dahua 的时候,该方法才会被调用。变量 method、path、targetUri、headers、entity、restTemplate、postEntity、requestFactory 等在代码中都有对应的使用。
相关文章:
spring-boot 实现接口转发服务,同时支持get 和 post等多种请求
spring-boot 实现接口转发服务,同时支持get 和 post等多种请求 (1)新建类:ProxyController.java package com.taobao.product.controller;import com.taobao.framework.HttpResult; import io.swagger.annotations.Api; import …...
About JDKFlightRecorder--人工翻译
JFR是什么 JDK Flight Recorder是一个工具,用于收集有关JVM以及在JVM上运行的Java程序的诊断和分析数据。 集成到Java虚拟机(JVM)中,使用默认设置时,性能影响小于1%。几乎不产生性能开销,因此即使在负载很…...
【计算机系统基础3】数据的存储与运算
【计算机系统基础3】数据的存储与运算 3.程序调试与实践:数据存储与运算3.1真值与机器数3.1.1整数的编码 3.2数据的存储3.3数组的对齐3.4数据类型的转换3.4.1整数之间的数据类型转换3.4.2整数与浮点数之间的转换3.4.3自动类型转换 3.5浮点数的表示和运算--IEEE 7543…...
【算法】快速排序
目录 核心思想: 过程: 演示: 第一趟: 第二趟: 代码: 核心思想: 从待排序列中取一个元素作为中心,所有比它小或相等的元素一律放在前面, 所有比它大的元素放在后面&…...
【移动端网页布局】流式布局案例 ③ ( 实现搜索栏功能 | 伪元素选择器 | 子绝父相 | 外边距塌陷处理 | 二倍精灵图处理方案 )
文章目录 一、搜索栏样式及核心要点1、实现效果2、自动伸缩搜索栏实现3、搜索栏父容器设置4、搜索栏左右两侧的按钮盒子5、搜索栏盒子6、二倍精灵图处理方案 二、完整代码示例1、HTML 标签结构2、CSS 样式3、展示效果 一、搜索栏样式及核心要点 1、实现效果 上一篇博客中 , 完成…...
【C++修炼之路】30.可变参数模板包装器
每一个不曾起舞的日子都是对生命的辜负 C11之可变参数模板&&包装器 前言一.可变参数模板的首次登场二.参数包展开2.1 递归函数方式展开参数包2.2 逗号表达式展开参数包 三.容器的emplace方法四.包装器4.1 什么是function4.2 function包装器的作用4.3 function的实际用途…...
Linux防火墙之firewalld基础
一、firewalld概述 firewalld防火墙是Centos7系统默认的防火墙管理工具,取代了之前的iptables防火墙,也是工作在网络层,属于包过滤防火墙。 firewalld和iptables都是用来管理防火墙的工具(属于用户态)来定义防火墙的…...
GitLab CI/CD
CI/CD 简介 CI/CD 简单来说就是可以自动化编译、测试、打包我们的代码。 GitLab CICD的使用 首先需要安装gitlab-runner。 在GitLab 中,runners 是运行 CI/CD 作业的代理。我们的对代码的作业都是在runner上去执行的。我们可以在本地、服务器、等任意一个联网设…...
PHP复习资料(未完待续)
(未完待续,请持续关注此板块) 【计科三四】雪课堂PHP期末模拟题:https://ks.wjx.top/vm/tUAmjxq.aspx# 【计科一二】PHP第一章练习题 https://ks.wjx.top/vm/QnjHad4.aspx# 【计科一二】PHP第二章练习题 https://ks.wjx.top/vm/h2…...
【python】pytorch包(第二章)API使用与介绍
1> nn.Module (用于构建模型的底层逻辑) 介绍 nn.Module 是 torch.nn 中的一个类,是pytorch中自定义网络的基类 __init__需要调用super方法,继承父类属性和方法forward方法必须实现,用来定义网络的向前计算的过程…...
Linux驱动基础(SR501人体感应模块)
文章目录 前言一、SR501模块介绍二、设备树编写三、驱动编写1.确定主设备号2.编写file_operations结构体3.注册file_operations结构体4.出口函数编写5.probe函数和remove函数编写6.中断编写7.测试程序编写8.全部驱动程序 总结 前言 本篇文章将给大家介绍一下SR501驱动程序的编…...
Android Studio Flamingo (火烈鸟) 升级踩坑记录
由于想要验证Compose最新的debug特性,而我目前使用的版本(Dolphin 小海豚)不支持,查看官网说明需要最新版本,所以不得已进行了一下Android Studio版本升级,过程中遇到一些问题,本文仅做记录。&a…...
【JAVA凝气】异常篇
哈喽~大家好呀,这篇来看看JAVA异常篇。 目录 一、前言 二、Exception 异常 1、Java 的非检查性异常 2、Java 检查性异常类 三、Error 错误 四、捕获异常 五、多重捕获块 六、throws/throw 关键字 七、自定义异常类 八、图书推荐 一、前言 异常是程序中的一…...
C++中的函数模板
目录 1. 什么是函数模板? 2. 如何定义函数模板? 3. 如何使用函数模板? 4. 函数模板与函数重载的区别是什么? 5. 函数模板与类模板有何异同点? 1. 什么是函数模板? - 函数模板是一种通用的函数描述&…...
MapReduce【Shuffle-Combiner】
概述 Conbiner在MapReduce的Shuffle阶段起作用,它负责局部数据的聚合,我们可以看到,对于大数据量,如果没有Combiner,将会在磁盘上写入多个文件等待ReduceTask来拉取,但是如果有Combiner组件,我们…...
postman接口自动化测试
Postman除了前面介绍的一些功能,还有其他一些小功能在日常接口测试或许用得上。今天,我们就来盘点一下,如下所示: 1.数据驱动 想要批量执行接口用例,我们一般会将对应的接口用例放在同一个Collection中…...
历经70+场面试,我发现了大厂面试的套路都是···
今年的金三银四刚刚过去,我又想起了我在去年春招时面试了50余家,加上暑期实习面试了20余家,加起来也面试了70余场的面试场景了。 基本把国内有名的互联网公司都面了一遍,不敢说自己的面试经验很丰富,但也是不差的。 …...
可视区域兼容性问题的思考及方法封装
今日在复习可视化尺寸获取时突发奇想,为什么要在怪异模式下使用document.body.clientWidth,在标准模式下使用document.documentElement.clientWidth?以及是否在IE8及以下的版本中其中一个获取方式将返回undefined或0。 出于该问题的思考&am…...
安全工具 | CMSeeK [指纹识别]
0x00 免责声明 本文仅限于学习讨论与技术知识的分享,不得违反当地国家的法律法规。对于传播、利用文章中提供的信息而造成的任何直接或者间接的后果及损失,均由使用者本人负责,本文作者不为此承担任何责任,一旦造成后果请自行承担…...
Android新logcat使用技巧
Android新logcat使用技巧 logcat新UI出现后,我常困惑于怎么过滤log,和以前的UI差异比较大,新UI界面结构如下: 这个新的 logcat 的问题是如何过滤信息并不是很明显。 获取应用的日志信息 要获取我们当前调试应用的日志信息&…...
装饰模式(Decorator Pattern)重构java邮件发奖系统实战
前言 现在我们有个如下的需求,设计一个邮件发奖的小系统, 需求 1.数据验证 → 2. 敏感信息加密 → 3. 日志记录 → 4. 实际发送邮件 装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其…...
rknn优化教程(二)
文章目录 1. 前述2. 三方库的封装2.1 xrepo中的库2.2 xrepo之外的库2.2.1 opencv2.2.2 rknnrt2.2.3 spdlog 3. rknn_engine库 1. 前述 OK,开始写第二篇的内容了。这篇博客主要能写一下: 如何给一些三方库按照xmake方式进行封装,供调用如何按…...
【机器视觉】单目测距——运动结构恢复
ps:图是随便找的,为了凑个封面 前言 在前面对光流法进行进一步改进,希望将2D光流推广至3D场景流时,发现2D转3D过程中存在尺度歧义问题,需要补全摄像头拍摄图像中缺失的深度信息,否则解空间不收敛…...
定时器任务——若依源码分析
分析util包下面的工具类schedule utils: ScheduleUtils 是若依中用于与 Quartz 框架交互的工具类,封装了定时任务的 创建、更新、暂停、删除等核心逻辑。 createScheduleJob createScheduleJob 用于将任务注册到 Quartz,先构建任务的 JobD…...
MVC 数据库
MVC 数据库 引言 在软件开发领域,Model-View-Controller(MVC)是一种流行的软件架构模式,它将应用程序分为三个核心组件:模型(Model)、视图(View)和控制器(Controller)。这种模式有助于提高代码的可维护性和可扩展性。本文将深入探讨MVC架构与数据库之间的关系,以…...
2025盘古石杯决赛【手机取证】
前言 第三届盘古石杯国际电子数据取证大赛决赛 最后一题没有解出来,实在找不到,希望有大佬教一下我。 还有就会议时间,我感觉不是图片时间,因为在电脑看到是其他时间用老会议系统开的会。 手机取证 1、分析鸿蒙手机检材&#x…...
鸿蒙中用HarmonyOS SDK应用服务 HarmonyOS5开发一个生活电费的缴纳和查询小程序
一、项目初始化与配置 1. 创建项目 ohpm init harmony/utility-payment-app 2. 配置权限 // module.json5 {"requestPermissions": [{"name": "ohos.permission.INTERNET"},{"name": "ohos.permission.GET_NETWORK_INFO"…...
零基础设计模式——行为型模式 - 责任链模式
第四部分:行为型模式 - 责任链模式 (Chain of Responsibility Pattern) 欢迎来到行为型模式的学习!行为型模式关注对象之间的职责分配、算法封装和对象间的交互。我们将学习的第一个行为型模式是责任链模式。 核心思想:使多个对象都有机会处…...
CMake 从 GitHub 下载第三方库并使用
有时我们希望直接使用 GitHub 上的开源库,而不想手动下载、编译和安装。 可以利用 CMake 提供的 FetchContent 模块来实现自动下载、构建和链接第三方库。 FetchContent 命令官方文档✅ 示例代码 我们将以 fmt 这个流行的格式化库为例,演示如何: 使用 FetchContent 从 GitH…...
服务器--宝塔命令
一、宝塔面板安装命令 ⚠️ 必须使用 root 用户 或 sudo 权限执行! sudo su - 1. CentOS 系统: yum install -y wget && wget -O install.sh http://download.bt.cn/install/install_6.0.sh && sh install.sh2. Ubuntu / Debian 系统…...
