springboot全面加密方案

springboot全面加密方案

  • 最近项目上又出幺蛾子了,甲方要求前端后台全部的数据都需要加密处理,不允许明文。简单的来说,就是传的参数是加密数据,然后接口返回给前端的数据也是加密数据。

  • 显示的效果就是比方说,前端传给我的是一个json

    {
    "data":"8cfd4ebd90359d687b0dd8345fad44ab3405cecd81e9d7e5da5ec994259e171575aa2384a024677276c98db9c13ef66e"
    }

  • 然后我拿到这个数据后解析成原本我的接口的参数,然后传到接口中处理逻辑,然后把返回值也加密,返回给前端的值类似于

    {
    "result":"6CC375B93947D06ED64E4A0E21227147C0D63EB71BD871EFFAF3A6319A7A6519B55E8919E0B505321230CC0DD951B535F6C8BB42EBFF6DA07B6F7C638658714F59D0522098BA91BB2B51174EF08B9DC99A98D99BD6A31599A995CAB8996EE4C2"
    }

  • 于是就要开始思考如何解决该问题,由于项目里没有统一的格式规范,各种类型层出不穷,比如@RequestBody,或者@RequestParam,各种表单提交或者json提交,然后返回值也是各种各样的。这对于我做全面加密产生了极大的阻碍。

  • 正常做首先看网上有没有现成的,但是经过我多次试验,均无法满足我的全部需求,它只能处理json格式的,对于我表单提交的方式那就是一个无能为力

  • 然后还有拦截器的方式,本来我是非常看好这个方法,但是拦截器HandlerInterceptor,我实在是无法实现解析后再把值变为表单提交进原来的接口中,如果有大佬实现了,希望能告诉在下,如何实现。

  • 同理自定义注解,也是同样的原因,我始终无法实现把解析后的参数转化为表单再重新提交进接口

  • 最后我使用过滤器的方式来实现,过滤器,缺失能实现把值转化为表单重新提交进接口

  • 而把返回值重新进行加密的方式,我选择使用implements ResponseBodyAdvice,我测试目前基本上返回值都会经过这里,重新进行加密封装后,再返回给前端


  • 进入filter后,重新赋值
    MyParameterRequestWrapper wrapRequest = new MyParameterRequestWrapper(request, newParams, jsonData);
    其中,newParams传的是表单的数据,jsonData传的是json的数据,都是解析出来的数据,然后继续进入下一个过滤
    filterChain.doFilter(wrapRequest, servletResponse);

    public class MyParameterRequestWrapper extends HttpServletRequestWrapper {
    private Map<String, String[]> params;
    private String requestBody = null;

    复制代码
      /**
       * Constructs a request object wrapping the given request.
       *
       * @param request the {@link HttpServletRequest} to be wrapped.
       * @throws IllegalArgumentException if the request is null
       */
      public MyParameterRequestWrapper(HttpServletRequest request, Map<String, String[]> params, String requestBody) {
          super(request);
          this.params = params;
          this.requestBody = requestBody;
      }
    
      @Override
      public Map<String, String[]> getParameterMap() {
          return params;
      }
    
      @Override
      public Enumeration<String> getParameterNames() {
          Vector<String> l = new Vector<>(params.keySet());
          return l.elements();
      }
    
      @Override
      public String[] getParameterValues(String name) {
          Object v = params.get(name);
          if (v == null) {
              return null;
          } else if (v instanceof String[]) {
              return (String[]) v;
          } else if (v instanceof String) {
              return new String[]{(String) v};
          } else {
              return new String[]{v.toString()};
          }
      }
    
      @Override
      public String getParameter(String name) {
          Object v = params.get(name);
          if (v == null) {
              return null;
          } else if (v instanceof String[]) {
              String[] strArr = (String[]) v;
              if (strArr.length > 0) {
                  return strArr[0];
              } else {
                  return null;
              }
          } else if (v instanceof String) {
              return (String) v;
          } else {
              return v.toString();
          }
      }
    
      @Override
      public BufferedReader getReader() throws IOException {
          return new BufferedReader(new StringReader(requestBody));
      }
    
      @Override
      public ServletInputStream getInputStream() throws IOException {
    
          ServletRequest request = getRequest();
    
          return new ServletInputStream() {
    
              @Override
              public boolean isFinished() {
                  return false;
              }
    
              @Override
              public boolean isReady() {
                  return false;
              }
    
              @Override
              public void setReadListener(ReadListener readListener) {
    
              }
    
              private InputStream in = new ByteArrayInputStream(
                      requestBody.getBytes(request.getCharacterEncoding() == null ? "UTF-8" : request.getCharacterEncoding()));
    
              // 读取 requestBody 中的数据
              @Override
              public int read() throws IOException {
                  return in.read();
              }
          };
      }

    }

    /**

    • 响应加解密拦截器

    • @author lyk
      */
      @Component
      @ControllerAdvice
      public class ResponseHandler implements ResponseBodyAdvice<Object> {

      // 这里假设你希望只有某些特定的 Controller 或方法走这个处理器
      @Override
      public boolean supports(MethodParameter methodParameter, Class<? extends HttpMessageConverter<?>> aClass) {
      //这里可以写一些条件return false,代表不进入返回加密流程
      return true;
      }

      /**

      • 响应加密
        */
        @Override
        public Object beforeBodyWrite(Object body, MethodParameter methodParameter, MediaType mediaType, Class<? extends HttpMessageConverter<?>> aClass, ServerHttpRequest request, ServerHttpResponse serverHttpResponse) {
        //这里body就是返回值,对它进行加密即可
        String encrypt = encryptEcb(body);

        JSONObject json = new JSONObject();
        json.put("result", encrypt);
        return json;
        }
        }

相关推荐
sniper_fandc44 分钟前
SpringBoot系列—入门
java·spring boot·后端
Albert Edison6 小时前
【最新版】IntelliJ IDEA 2025 创建 SpringBoot 项目
java·spring boot·intellij-idea
Piper蛋窝7 小时前
深入 Go 语言垃圾回收:从原理到内建类型 Slice、Map 的陷阱以及为何需要 strings.Builder
后端·go
六毛的毛10 小时前
Springboot开发常见注解一览
java·spring boot·后端
AntBlack10 小时前
拖了五个月 ,不当韭菜体验版算是正式发布了
前端·后端·python
315356691310 小时前
一个简单的脚本,让pdf开启夜间模式
前端·后端
uzong10 小时前
curl案例讲解
后端
开开心心就好11 小时前
免费PDF处理软件,支持多种操作
运维·服务器·前端·spring boot·智能手机·pdf·电脑
一只叫煤球的猫11 小时前
真实事故复盘:Redis分布式锁居然失效了?公司十年老程序员踩的坑
java·redis·后端
猴哥源码11 小时前
基于Java+SpringBoot的农事管理系统
java·spring boot