从request 中解析上传参数

本文介绍了一种自定义的HTTP请求解析方法,特别针对POST请求中的form-data类型数据进行处理,包括文件上传和其他表单数据的解析,并提供了一个具体的实现类。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

前言

我们项目经常会在真正进入接口方法之前,对参数进行解析。进行一些预处理,比如权限校验、让接口进入到我们预定方法之中。

实践

1、添加依赖,这里会用到关于上传文件中依赖(处理当是form-data类型的时候),其他关于会涉及到web依赖不再贴出

   <dependency>
        <groupId>commons-fileupload</groupId>
        <artifactId>commons-fileupload</artifactId>
    </dependency>

2、具体解析request

public class PostRequestHttpServletRequestWrapper extends CommonRequestHttpServletRequestWrapper {

    public PostRequestHttpServletRequestWrapper(HttpServletRequest req) {
        super(req);
        if (hasFile(req)) {
            commonRequest = new CommonRequest();
            commonRequest.setData(parseFileRequest(req));
            dataBody=parseJsonExcludeFile(commonRequest.getData());
        }else{
            //默认走body 的解析
            String commonReqDody = StreamUtil.getBodyString(req);
            commonRequest = JSON.parseObject(commonReqDody, CommonRequest.class, Feature.IgnoreNotMatch);
            String dataJson = "";
            if (commonRequest != null){
                dataJson = JSON.toJSONString(commonRequest.getData(), SerializerFeature.WriteMapNullValue);
            }else{
                commonRequest = new CommonRequest();
                commonRequest.setData(new HashMap<>());
            }
            dataBody = dataJson.getBytes(Charset.forName("UTF-8"));
        }
    }



    /**
     * 判断是否是附件上传
     * @param request request
     * @return true 为是附件上传 false 为非附件上传
     */
    private Boolean hasFile(HttpServletRequest request) {
        //判断是否附件上传
        return ServletFileUpload.isMultipartContent(request);
    }

    /**
     * 解析file 或 text
     */
    private Map<String, Object> parseFileRequest(HttpServletRequest request) {
        //有文件走特殊解析
        DiskFileItemFactory factory = new DiskFileItemFactory();
        ServletFileUpload upload = new ServletFileUpload(factory);
        //解决上传文件名中文乱码
        upload.setHeaderEncoding("UTF-8");
        Map<String, Object> data = new HashMap<>();
        try {
            List<FileItem> fileItems = upload.parseRequest(request);
            if (fileItems != null) {
                for (FileItem fileItem : fileItems) {
                    String key = fileItem.getFieldName();
                    Object value;
                    if (fileItem.isFormField()) {
                        value = fileItem.getString();
                    }else{
                        value = new CommonsMultipartFile(fileItem);
                    }
                    data.put(key, value);
                }
            }
        } catch (FileUploadException e) {
            CommonLogUtil.error("parseFileRequest fileUpload fail", e);
        }
        return data;
    }

    /**
     * 解析除了file的字段
     * @param data 需要解析放到的字段
     * @return 返回body 字段
     */
    private byte[] parseJsonExcludeFile(Map<String, Object> data) {
        Map<String, Object> newMap = new HashMap<>();
        for (Map.Entry<String, Object> entry : data.entrySet()) {
            Object value = entry.getValue();
            if (value instanceof CommonsMultipartFile) {
                continue;
            }
            String key = entry.getKey();
            newMap.put(key, value);
        }
        String dataBodyJson = JSON.toJSONString(newMap, SerializerFeature.WriteMapNullValue);
        return dataBodyJson.getBytes(Charset.forName("UTF-8"));
    }
}

2、从body读取内容的工具类

public class StreamUtil {
    private static final Integer BUFFER_SIZE = 128;
    private static final Logger LOGGER = LoggerFactory.getLogger(StreamUtil.class);

    public static String getBodyString(HttpServletRequest request) {
        StringBuilder stringBuilder = new StringBuilder();
        BufferedReader bufferedReader = null;
        try {
            ServletInputStream inputStream = request.getInputStream();
            if (!Objects.isNull(inputStream)) {
                bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
                int bytesRead = 0;
                char[] charBuffer = new char[BUFFER_SIZE];
                while ((bytesRead = bufferedReader.read(charBuffer)) != -1) {
                    stringBuilder.append(charBuffer, 0, bytesRead);
                }
            } else {
                stringBuilder.append("");
            }
        } catch (IOException e) {
            LOGGER.error("get body fail,{}", e.getMessage());
        } finally {
            if (bufferedReader != null) {
                try {
                    bufferedReader.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }

            }
        }
        return stringBuilder.toString();
    }
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值