其他后端常用功能
文件上传
Servlet实现文件上传需要借助fileupload或其他第三方上传工具包,fileupload是Apache commons下面的一个子项目,需要引入相关jar包,从maven官网中查找Apache Commons FileUpload并下载,以及下载相关依赖(commons-io),导入项目即可
<form action="${pageContext.request.contextPath}/upload" method="post" enctype="multipart/form-data">
<!-- 必须指定enctype为multipart/form-data -->
<input type="text" name="name">
<input type="file" name="file">
<input type="submit" value="上传">
</form>
该工具上传步骤比较复杂,我将其提取成一个方法,该方法仅适合于单文件上传,因为Map的关系,虽然可以上传成功,但是返回的Map对象中的文件属性是最后一个文件,因为之前的被覆盖掉了
/**
* 解析有文件上传的表单提交,并将表单项解析成Map对象
*
* @param servletRequest 要解析的请求对象
* @param dir 要上传的目录(应该是静态资源目录下的子目录,即web目录下的子目录,要保证该目录存在)
* @return HashMap<String, String>
* @throws IOException
*/
private HashMap<String, String> parseRequest(ServletRequest servletRequest, String dir) throws IOException {
/*1.fileupload中核心类的创建*/
HashMap<String, String> hashMap = new HashMap<>(); //存储返回结果的Map对象
HttpServletRequest req = (HttpServletRequest) servletRequest; //向下强制转换为HttpServletRequest
DiskFileItemFactory diskFileItemFactory = new DiskFileItemFactory(); //创建磁盘文件项工厂类用于创建文件上传核心类使用
ServletFileUpload fileUpload = new ServletFileUpload(diskFileItemFactory); //创建文件上传核心类
/*2.fileupload的使用*/
InputStream inputStream = null;
FileOutputStream fileOutputStream = null;
try {
List<FileItem> fileItems = fileUpload.parseRequest(req); //使用fileupload核心类解析请求
for (FileItem fileItem : fileItems) {
if (fileItem.isFormField()) { //若不是文件
String name = fileItem.getFieldName(); //获取字段名
String value = fileItem.getString("UTF-8"); //获取字段值,并防止中文乱码
hashMap.put(name, value); //添加到Map对象中
} else { //若是文件
String name = fileItem.getFieldName(); //获取字段名
String filename = fileItem.getName(); //获取文件名
/*2.1.解决文件上传重名覆盖问题*/
int idx = filename.lastIndexOf(".");
String exName = filename.substring(idx); //截取文件后缀名
filename = UUID.randomUUID().toString().replace("-", "") + exName; //生成随机UUID拼接后缀名,修改文件名避免上传重名文件被覆盖
/*2.2.文件上传的输入流对接*/
inputStream = fileItem.getInputStream(); //获取文件的输入流
String dirAPath = getServletContext().getRealPath(dir); //获取上传目录的的绝对路径
String fileRealPath = dirAPath + File.separator + filename; //将fieldName修改为上传后的文件路径
fileOutputStream = new FileOutputStream(fileRealPath); //根据文件名真实路径创建文件输出流
int len = 0;
byte[] bytes = new byte[1024];
while ((len = inputStream.read(bytes)) != -1) {
fileOutputStream.write(bytes, 0, len); //1KB,1KB的写入文件
}
/*3.返回值中Map对象value值的优化拼接*/
String fileRPath = getServletContext().getContextPath() + "/" + dir + "/" + filename; //拼接文件符合src的相对路径
hashMap.put(name, fileRPath); //将上传后的路径添加到Map对象中
}
}
} catch (FileUploadException e) {
e.printStackTrace();
} finally { //释放IO资源
if (inputStream != null) {
inputStream.close();
}
if (fileOutputStream != null) {
fileOutputStream.close();
}
}
return hashMap;
}
验证码校验
Servlet实现验证码校验需要借助Kaptcha或其他第三方上传工具包,Kaptcha是一个可高度配置的实用验证码生成工具,原理就是在内存中生成一张验证码图片返回给客户端,使用需要引入相关jar包,从maven官网中查找Kaptcha并下载,以及下载相关依赖(Filters)导入项目,并在web.xml
中配置即可
<servlet>
<servlet-name>Kaptcha</servlet-name>
<servlet-class>com.google.code.kaptcha.servlet.KaptchaServlet</servlet-class>
<init-param> <!-- 边框颜色 -->
<param-name>kaptcha.border.color</param-name>
<param-value>white</param-value>
</init-param>
<init-param> <!-- 字体颜色 -->
<param-name>kaptcha.textproducer.font.color</param-name>
<param-value>white</param-value>
</init-param>
<init-param> <!-- 干扰线的颜色 -->
<param-name>kaptcha.noise.color</param-name>
<param-value>black</param-value>
</init-param>
<init-param> <!-- 背景渐变开始颜色 -->
<param-name>kaptcha.background.clear.from</param-name>
<param-value>254,67,101</param-value>
</init-param>
<init-param> <!-- 背景渐变结束颜色 -->
<param-name>kaptcha.background.clear.to</param-name>
<param-value>252,157,154</param-value>
</init-param>
<init-param><!-- 图片样式添加阴影 -->
<param-name>kaptcha.obscurificator.impl</param-name>
<param-value>com.google.code.kaptcha.impl.ShadowGimpy</param-value>
</init-param>
<init-param> <!-- 图片宽度 -->
<param-name>kaptcha.image.width</param-name>
<param-value>200</param-value>
</init-param>
<init-param> <!-- 图片高度 -->
<param-name>kaptcha.image.height</param-name>
<param-value>50</param-value>
</init-param>
<init-param> <!-- 字体大小 -->
<param-name>kaptcha.textproducer.font.size</param-name>
<param-value>45</param-value>
</init-param>
<init-param> <!-- 验证码字符个数 -->
<param-name>kaptcha.textproducer.char.length</param-name>
<param-value>4</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>Kaptcha</servlet-name>
<url-pattern>/kaptcha</url-pattern>
</servlet-mapping>
jsp中的表单提交代码
<form action="${pageContext.request.contextPath}/check" method="get">
<input type="text" name="kaptcha">
<img id="kaptcha" src="${pageContext.request.contextPath}/kaptcha" alt="">
<input type="button" id="reset" value="看不清,换一张">
<input type="submit" value="提交">
</form>
<script>
var reset = document.getElementById("reset");
reset.addEventListener("click", function () {
var img = document.getElementById("kaptcha");
img.src = "${pageContext.request.contextPath}/kaptcha?time=" + new Date().getTime();
//加时间戳是为了消除浏览器缓存
})
</script>
servlet中验证验证码是否正确代码
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException {
String kaptcha_session_key = (String) request.getSession().getAttribute("KAPTCHA_SESSION_KEY"); //从sesion中获取真正验证码
String kaptcha = request.getParameter("kaptcha"); //用户提交的验证码
response.setContentType("text/html;charset=utf8");
if (kaptcha_session_key.equals(kaptcha)) { //比较是否相同
response.getWriter().write("验证码通过");
} else {
response.getWriter().write("验证码错误");
}
}
Comments NOTHING