在本系列第四篇文章中简单介绍了一下引入elementUI的图片上传组件,但是没有进行详细说明,本文将详细介绍如何上传图片。
1 后端部分
-
新建上传路由
app.post('/admin/api/upload',async(req,res)=>{ const file=req.file res.send(file) })
-
创建中间件
需要先在server中安装multer帮助处理中间件:npm i multer,然后引入multer
const multer=require('multer') const upload =multer({dest:__dirname + '/../../uploads'}) //目标地址
加入该中间件:
app.post('/admin/api/upload',upload.single('file'),async(req,res)=>{ const file=req.file file.url=`http://localhost:3000/uploads/${file.filename}`//通过文件的url显示图片 res.send(file) })
-
让上传的文件对于前端可见,使用静态文件托管
app.use('/uploads', express.static(__dirname + '/uploads'))
2 前端部分
上传图片组件:
<el-form-item label="图标" >
<el-upload
class="avatar-uploader"
:action="uploadUrl" /**动态请求地址**/
:show-file-list="false"
:on-success="afterUpload" /**执行成功后调用**/>
<img v-if="model.icon" :src="model.icon" class="avatar">
<i v-else class="el-icon-plus avatar-uploader-icon"></i>
</el-upload>
</el-form-item>
:action 用于动态请求上传地址 地址为$http.defaults.baseURL+'/upload',可以在全局定义该地址:
/**main.js**/
uploadUrl(){
return this.$http.defaults.baseURL+'/upload'
}
v-if v-else表示如果有返回图片地址即展示,若没有则显示默认的箭头
<img v-if="model.icon" :src="model.icon" class="avatar">
<i v-else class="el-icon-plus avatar-uploader-icon"></i>
:on-success="afterUpload"表示执行成功后调用该函数,得到的服务端返回的图片地址值,并且显示赋值给model.icon, 通过图片的url展示图片
afterUpload(res){
this.$set(this.model,'icon',res.url) //显式赋值
}
3 富文本编辑器的图片上传
直接复制文章内容通过富文本编辑器上传图片会导致图片资源嵌入到整个请求数据中,导致数据量过大,加载接口速度会非常慢。所以为了解决这个问题,我们对前端部分进行修改,改为点击富文本编辑器的图片按钮上传图片的方式。
查找官方文档,找到有关upload的部分。
-
给vue-editor组件增加图片上传方法
<vue-editor v-model="model.body" useCustomImageHandler @image-added="handleImageAdded"> </vue-editor>
-
修改方法写法,改为await同步的写法,也减少了代码量
async handleImageAdded(file, Editor, cursorLocation, resetUploader) { const formData = new FormData(); //表单数据对象 formData.append("file", file); //图片是file格式 const res= await this.$http.post('upload',formData); //插入图片资源地址到光标所在位置,元素名为image Editor.insertEmbed(cursorLocation, "image", res.data.url); resetUploader(); }