前端环境配置
从Element文档找见upload对应的代码先copy下来,这里选择的是用户头像上传中的代码。然后要替换一下action
中的接口地址,换成自己后端的,这里我的后端地址为http://localhost:5277/api/article/UploadPic
修改一下handleAvatarSuccess
方法
这里提一嘴,如果你的项目中请求的时候需要携带token,那么要在upload中加上:headers="headers
属性,把token赋值给headers
。
handleAvatarSuccess(res, file) {
console.log(res);
this.imageUrl = res.data;
console.log("图片预览的url:"+this.imageUrl);
}
前端整体代码如下:
<template>
<el-upload
class="avatar-uploader"
action="http://localhost:5277/api/article/UploadPic"
:show-file-list="false"
:on-success="handleAvatarSuccess"
:before-upload="beforeAvatarUpload"
:headers="headers"
>
<img v-if="imageUrl" :src="imageUrl" class="avatar" />
<i v-else class="el-icon-plus avatar-uploader-icon"></i>
</el-upload>
</template>
<style>
.avatar-uploader .el-upload {
border: 1px dashed #d9d9d9;
border-radius: 6px;
cursor: pointer;
position: relative;
overflow: hidden;
}
.avatar-uploader .el-upload:hover {
border-color: #409eff;
}
.avatar-uploader-icon {
font-size: 28px;
color: #8c939d;
width: 178px;
height: 178px;
line-height: 178px;
text-align: center;
}
.avatar {
width: 178px;
height: 178px;
display: block;
}
</style>
<script>
import { getToken } from "@/utils/auth"; // get token from cookie
export default {
data() {
return {
imageUrl: "",
headers: {
token: getToken() ? getToken() : "",
},
};
},
methods: {
handleAvatarSuccess(res, file) {
console.log(res);
this.imageUrl = res.data;
console.log("图片预览的url:"+this.imageUrl);
},
beforeAvatarUpload(file) {
const isJPG = file.type === "image/jpeg";
const isLt2M = file.size / 1024 / 1024 < 2;
if (!isJPG) {
this.$message.error("上传头像图片只能是 JPG 格式!");
}
if (!isLt2M) {
this.$message.error("上传头像图片大小不能超过 2MB!");
}
return isJPG && isLt2M;
},
},
};
</script>
文件auth.js
中的getToken()
方法为
import Cookies from 'js-cookie'
const TokenKey = 'Admin-Token'
export function getToken() {
return Cookies.get(TokenKey)
}
搭建后端环境
可以参考之前的一篇文章,用IDEA快速搭建SpringBoot环境,这里搭建环境不做重点介绍。搭建完环境以后,引入上传文件的依赖
<!--文件上传-->
<dependency>
<groupId>commons-fileupload</groupId>
<artifactId>commons-fileupload</artifactId>
<version>1.4</version>
</dependency>
这里要重点说明一下,浏览器只能访问resources/static
下的文件,之后把图片存到里面才可以直接访问。这里在static
下再新建一个img
文件夹专门用于存放图片。
如果这个img文件夹直接放在resource下是访问不到的,会报404的错误。文件会上传到target/classes/static/img
目录下
之后访问的时候直接使用端口号+/img(如http://localhost:5277/img/2022-04-97/154b20d9-32de-43b7-997e-50e925a8becc.png
)即可访问到,访问链接中不需要再img
之前再加static/
,否则也会报404的错误。
//返回可供外界访问的url
String url = request.getScheme() + "://" + request.getServerName() + ":" + request.getServerPort() + "/img" + format + newName;
之后建立Controller文件
import com.cms.utils.ResultUtils;
import com.cms.utils.ResultVo;
import org.springframework.util.ResourceUtils;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.UUID;
@RestController
@RequestMapping("/api/article")
public class ImgController {
@PostMapping("/UploadPic")
public ResultVo UploadPic(MultipartFile file, HttpServletRequest request) throws FileNotFoundException {
SimpleDateFormat dateFormat = new SimpleDateFormat("/yyyy-MM-DD/");
String filename = file.getOriginalFilename();//取得文件名称
if (!filename.endsWith(".png") && !filename.endsWith(".jpg")) {
return ResultUtils.error("文件类型不对");
}
String format = dateFormat.format(new Date());
//realPath为文件保存的位置
String realPath = ResourceUtils.getURL("classpath:").getPath() + "static/img" + format;
realPath = realPath.substring(1);//去掉第一个/符号
File folder = new File(realPath);
if (!folder.exists()) {
folder.mkdirs();
}
String newName;
if (filename.endsWith(".png"))
newName = UUID.randomUUID().toString() + ".png";
else
newName = UUID.randomUUID().toString() + ".jpg";
try {
//新建文件
file.transferTo(new File(folder, newName));
//String url = realPath + newName;
} catch (IOException e) {
return ResultUtils.error(e.getMessage());
}
//返回可供外界访问的url
String url = request.getScheme() + "://" + request.getServerName() + ":" + request.getServerPort() + "/img" + format + newName;
return ResultUtils.success("图片上传成功", url);
}
}
注:这里ResultUtils和ResultVo是我自定义的两个类
ResultUtils
:
/**
* 数据返回工具类
*/
public class ResultUtils {
/**
* 无参数返回
* @return
*/
public static ResultVo success() {
return Vo(null, StatusCode.SUCCESS_CODE, null);
}
public static ResultVo success(String msg){
return Vo(msg,StatusCode.SUCCESS_CODE,null);
}
/**
* 返回带参数
* @param msg
* @param data
* @return
*/
public static ResultVo success(String msg,Object data){
return Vo(msg,StatusCode.SUCCESS_CODE,data);
}
public static ResultVo success(String msg,int code,Object data){
return Vo(msg,code,data);
}
public static ResultVo Vo(String msg, int code, Object data) {
return new ResultVo(msg, code, data);
}
/**
* 错误返回
* @return
*/
public static ResultVo error(){
return Vo(null,StatusCode.ERROR_CODE,null);
}
public static ResultVo error(String msg){
return Vo(msg,StatusCode.ERROR_CODE,null);
}
public static ResultVo error(String msg,int code,Object data){
return Vo(msg,code,data);
}
public static ResultVo error(String msg,int code){
return Vo(msg,code,null);
}
public static ResultVo error(String msg,Object data){
return Vo(msg, StatusCode.ERROR_CODE,data);
}
}
ResultVo
:
public class ResultVo<T> {
private String msg;
private int code;
private T data;
}
这样就上传成功了
注:如果项目中加入了Spring Security,要对图片访问链接进行放行。
再次感谢一位神秘计科大佬鼎力相助~