Vue3+ElementPlus+koa2 realizes the upload of local pictures

1. Example diagram

2. Implementation process

  1. Use Koa2 to write the background interface for submitting pictures

This module is one of the sections in the project I wrote - uploading pictures. The background interface of this project mainly uses the back-end Koa2 framework. The front-end friends want to try to write some interfaces for adding, deleting, modifying and checking by themselves. To start, Koa2 is very easy to use to understand the backend. When you try to complete the interface writing to the realization of the front-end page by yourself, you will have a clearer understanding of the entire process of the project. It is to get data through the interface as usual, and then render it on the page.

When you complete the relevant functions of the interface yourself, you will understand better why we need to pass relevant parameters when using the back-end interface, and how these parameters are searched in the database, and have a more comprehensive consideration of the overall project , For example, adding a shopping cart is not as simple as we imagined. The data we add actually adds a record in the related table of the database in real time, so there is a need to call the interface for obtaining shopping cart information again.

As for when to share this complete project (about the background management system of xxxx, which is mainly implemented using Vite+Vue3+Element-plus+TypeScript), I still need to sort it out and put it on gitee. Interested parties are welcome friends to read.

Closer to home: How to implement the back-end interface for uploading pictures?

1.1 Install koa/multer

npm i --save @koa/multer

koa/multer is a middleware in Koa, used to upload files, see https://www.itying.com/koa/article-index-id-90.html for details

1.2 specific implementation code

/**
 * 上传模块
 */
const router = require('koa-router')()
const fs = require('fs')
const path = require('path')
const multer = require('@koa/multer');
router.prefix('/uploads') //接口的地址前缀
//配置    
let upload = multer({
    storage: multer.diskStorage({
        //文件保存路径
        destination: function (req, file, cb) {
            let dir = "./public/images"
            if (!fs.existsSync(dir)) {
                fs.mkdirSync(dir, {
                    recursive: true
                })
            }
            cb(null, dir) //注意路径必须存在
        },
        //修改文件名称
        filename: function (req, file, cb) {
            let fileName = file.fieldname + "-" + Date.now() + path.extname(file.originalname)
            cb(null, fileName)
        }
    })
})

// 实现图片的上传
router.post('/img', upload.single('myfile'), async ctx => {
    console.log(ctx);
    let path = ctx.request.file.path
    console.log(path);
    path = ctx.request.origin + '' + path.replace(/public/, '');
    ctx.body = {
        data: path,
        code: 1,
        msg: "文件上传成功"
    }
});
module.exports = router
Explanation of related parameters:
path: Because this is mainly to upload pictures to the public/image folder in the background, it is necessary to specify the path for uploading pictures
. The interface written under the module
  1. The front end uses the interface to complete the rendering of data

As usual, we still need to use the interface to call the backend. Of course, this major premise is that you have performed axios encapsulation before you can get the data.

2.1 Encapsulation of the data acquisition function?

Usually we write a request function to splice the address and the data passed in the request method, and then call the interface, which is not needed here. There are related components in the component library Element-Plus for us to use, and there are many APIs that can be easily solved this problem. For example, here we can set an action, and this parameter is used to fill in the address of uploading pictures . For details, see the official component https://element-plus.gitee.io/zh-CN/component/upload.html

There are many ways to upload pictures in the component library, here we take drag and drop upload as an example

<template>
  <el-upload
    class="upload-demo"
    drag
    action="https://run.mocky.io/v3/9d059bf9-4660-45f2-925d-ce80ad6c4d15"
    multiple
  >
    <el-icon class="el-icon--upload"><upload-filled /></el-icon>
    <div class="el-upload__text">
      Drop file here or <em>click to upload</em>
    </div>
    <template #tip>
      <div class="el-upload__tip">
        jpg/png files with a size less than 500kb
      </div>
    </template>
  </el-upload>
</template>

<script setup lang="ts">
import { UploadFilled } from '@element-plus/icons-vue'
</script>

2.2 specific implementation code

<template>
  <img :src="realImg" alt="" />
  <el-upload
    class="upload-demo"
    drag
    action="/api/uploads/img"
    multiple
    name="myfile"
    :headers="result"
    :on-success="sucUpload"
  >
    <el-icon class="el-icon--upload"><upload-filled /></el-icon>
    <div class="el-upload__text">选择图片 或者 <em>上传图片</em></div>
    <template #tip>
      <div class="el-upload__tip">
        jpg/png files with a size less than
        500kb(jpg/pgn格式的文件大小不可超过500kb)
      </div>
    </template>
  </el-upload>
</template>

<script setup lang="ts">
import { reactive, ref, onMounted } from "vue";
import { UploadFilled } from "@element-plus/icons-vue";
// 获取请求头
let userToken = window.sessionStorage.getItem("userToken") || "";
let result = reactive({
  Authorization: "Bearer " + JSON.parse(userToken),
});

let realImg: any = ref("");
// 上传图片成功的回调
const sucUpload = (res: any) => {
  console.log(res, "上传图片的结果");
  if (res) {
    window.sessionStorage.setItem("imgList", res.data);
  }
};

onMounted(() => {
    realImg.value = window.sessionStorage.getItem('imgList');
});
</script>

<style scoped>
/*图片的样式*/
img {
  width: 300px;
  height: 200px;
}
</style>

Summarize

The above are some of my sharing. I am very sorry that the front-end time has not been updated. I opened the private message last night and saw a friend asking me why I didn’t continue to write. It was put on hold together, and secondly, I didn't think that my writing would be read by anyone, um... All in all, I will continue to update it in the future, continue to share what I know with everyone, and let's make progress together.

Finally, I still wish you health, happiness, peace and happiness in front of the screen! Bye

Guess you like

Origin blog.csdn.net/Bonsoir777/article/details/128992552