javaioIOException Stream closed ServletRequestshiro AccessControlFilter 拦截MultipartHttpServletRequest中body内容后字符流关闭
这个异常是由于在拦截MultipartHttpServletRequest中的body内容后,字符流被关闭导致的。通常情况下,在过滤器中拦截请求的body内容后,需要重新创建一个新的ServletRequest对象,并将原始的ServletRequest对象中的内容复制到新的ServletRequest对象中。
以下是一个示例代码,展示了如何在Shiro的AccessControlFilter中正确处理MultipartHttpServletRequest的情况:
public class MyAccessControlFilter extends AccessControlFilter {
@Override
protected boolean isAccessAllowed(ServletRequest request, ServletResponse response, Object mappedValue) throws Exception {
// 获取原始的HttpServletRequest对象
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
// 判断请求是否为Multipart请求
if (ServletFileUpload.isMultipartContent(httpServletRequest)) {
// 创建一个新的MultipartHttpServletRequest对象
MultipartHttpServletRequest multipartRequest = createMultipartHttpServletRequest(httpServletRequest);
// 将原始的ServletRequest对象中的内容复制到新的MultipartHttpServletRequest对象中
copyRequestParameters(httpServletRequest, multipartRequest);
// 将新的MultipartHttpServletRequest对象设置到Shiro的Subject中
Subject subject = SecurityUtils.getSubject();
subject.getSession().setAttribute(DefaultWebSubjectContext.NATIVE_REQUEST, multipartRequest);
}
// 继续执行Shiro的filter链
return true;
}
@Override
protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws Exception {
// 继续执行Shiro的filter链
return true;
}
// 创建一个新的MultipartHttpServletRequest对象
private MultipartHttpServletRequest createMultipartHttpServletRequest(HttpServletRequest httpServletRequest) throws IOException {
MultipartHttpServletRequest multipartRequest = new DefaultMultipartHttpServletRequest(httpServletRequest);
return multipartRequest;
}
// 将原始的ServletRequest对象中的内容复制到新的MultipartHttpServletRequest对象中
private void copyRequestParameters(HttpServletRequest httpServletRequest, MultipartHttpServletRequest multipartRequest) throws IOException {
// 获取原始的请求参数Map
Map<String, String[]> parameterMap = httpServletRequest.getParameterMap();
// 将原始的请求参数Map中的内容复制到新的MultipartHttpServletRequest对象中
for (Map.Entry<String, String[]> entry : parameterMap.entrySet()) {
String name = entry.getKey();
String[] values = entry.getValue();
multipartRequest.getParameterMap().put(name, values);
}
// 复制原始的请求体内容到新的MultipartHttpServletRequest对象中
ServletInputStream inputStream = httpServletRequest.getInputStream();
ServletOutputStream outputStream = multipartRequest.getOutputStream();
IOUtils.copy(inputStream, outputStream);
inputStream.close();
outputStream.close();
}
}
通过以上代码,在Shiro的AccessControlFilter中,可以正确地处理MultipartHttpServletRequest的情况,避免Stream closed的异常
原文地址: http://www.cveoy.top/t/topic/iZiF 著作权归作者所有。请勿转载和采集!