MultipartFile 常用方法

String getOriginalFilename();/ /获取原始文件名
void transferTo(File dest);//将接收的文件转存到磁盘文件中  ●getSize();//获取文件的大小,单位:字节
byte getBytes();//获取文件内容的字节数组
InputStream getInputStream();//获取接收到的文件内容的输入流

前端准备

element-plus官网网址:

https://element-plus.org/zh-CN/component/upload.html

截图说明

将以下代码统一全部复制到编辑器(vscode||idea)中,进行修改,样式不要动

name="fileName"手动加入,

<template>

    
    <el-upload 
    class="avatar-uploader" 
    action="/api/file/upload" 
    name="fileName"
    :show-file-list="false"
    :on-success="handleAvatarSuccess" 
    :before-upload="beforeAvatarUpload">
    <img v-if="imageUrl" :src="imageUrl" class="avatar" />
        <el-icon v-else class="avatar-uploader-icon">
            <Plus />
        </el-icon>
    </el-upload>
<hr  >
    <p>{{ form }}</p>
</template>

<script setup>
import { ref } from 'vue'
import { ElMessage } from 'element-plus'
import { Plus } from '@element-plus/icons-vue'

// import type { UploadProps } from 'element-plus'

// 定义表单对象,提交带有图片url的表单对象,准备提交
const form = ref({
    name:'',
    fileName:'',
    fileUrl:''
})

const imageUrl = ref('')
const handleAvatarSuccess = (
    response,
    uploadFile
) => {
    imageUrl.value = URL.createObjectURL(uploadFile.raw)
    console.log(response.object)
    form.value.fileUrl = response.object
}

const beforeAvatarUpload = (rawFile) => {
    if (rawFile.type !== 'image/jpeg') {
        ElMessage.error('Avatar picture must be JPG format!')
        return false
    } else if (rawFile.size / 1024 / 1024 > 2) {
        ElMessage.error('Avatar picture size can not exceed 2MB!')
        return false
    }
    return true
}
</script>

<style scoped>
.avatar-uploader .avatar {
    width: 178px;
    height: 178px;
    display: block;
}
</style>

<style>
.avatar-uploader .el-upload {
    border: 1px dashed var(--el-border-color);
    border-radius: 6px;
    cursor: pointer;
    position: relative;
    overflow: hidden;
    transition: var(--el-transition-duration-fast);
}

.avatar-uploader .el-upload:hover {
    border-color: var(--el-color-primary);
}

.el-icon.avatar-uploader-icon {
    font-size: 28px;
    color: #8c939d;
    width: 178px;
    height: 178px;
    text-align: center;
}
</style>

如果样式不生效,需要执行以下命令,以便安装scss样式

npm  i  sass --save   

浏览器效果图,展示

后端准备

application.yml 配置文件准备

server:
  port: 8080

spring:
  datasource:
    driver-class-name: com.mysql.cj.jdbc.Driver
    url: jdbc:mysql://localhost:3306/rbac
    username: root
    password: root

自定义配置信息,设置静态资源映射路径
file:
    staticAccessPath: /file/**
    uploadFolder: D:/video/2403A_zhuanye5/code/file_upload/src/main/resources/static/

mvc配置类

package com.zhentao.file_upload.config;


import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@Configuration
public class SpringMvcConfig implements WebMvcConfigurer {

    @Value("${file.staticAccessPath}")
    String staticAccessPath;
    @Value("${file.uploadFolder}")
    String uploadFolder;
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        // 当访问前面的路径是,用后面的路径形成替换
        registry.addResourceHandler(staticAccessPath)
                .addResourceLocations("file:"+uploadFolder);
        // 让其配置的映射,生效
        WebMvcConfigurer.super.addResourceHandlers(registry);
    }
}

支持文件上传的后端控制器

package com.zhentao.file_upload.rest;


import com.zhentao.file_upload.vo.Result;
import org.springframework.beans.factory.annotation.Value;
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 java.io.File;
import java.io.IOException;
import java.util.UUID;

@RestController
@RequestMapping("file")
public class FileController {
    @Value("${file.uploadFolder}")
    String uploadFolder;

    @PostMapping("upload")
    public Result upload(MultipartFile fileName) throws IOException {
        // 获取文件真实名字
        String originalFilename = fileName.getOriginalFilename();
        // 获取动态的文件名字
        String newFileName= UUID.randomUUID().toString().replace("-", "")+
                ""+originalFilename.substring( originalFilename.lastIndexOf("."));
        System.out.println("图片新名字为:"+newFileName);
        File file = new File(uploadFolder,newFileName);
        if(!file.exists()){
            file.mkdirs();
        }
        // 将文件转存到服务器对应的路径中
        fileName.transferTo(file);
        String url ="http://localhost:5173/api/file/"+newFileName;
        return Result.OK("上传成功", url);
    }
}

postMan测试

报错如下:, 1048576 , 代表文件上传的最大内存是 1048576 bytes等于1MB

org.apache.tomcat.util.http.fileupload.impl.FileSizeLimitExceededException: The field file exceeds its maximum permitted size of 1048576 bytes.
	at org.apache.tomcat.util.http.fileupload.impl.FileItemStreamImpl$1.raiseError(FileItemStreamImpl.java:117) ~[tomcat-embed-core-10.1.5.jar:10.1.5]
	at org.apache.tomcat.util.http.fileupload.util.LimitedInputStream.checkLimit(LimitedInputStream.java:76) ~[tomcat-embed-core-10.1.5.jar:10.1.5]
	at org.apache.tomcat.util.http.fileupload.util.LimitedInputStream.read(LimitedInputStream.java:135) ~[tomcat-embed-core-10.1.5.jar:10.1.5]

如果显示文件过大,超出上限,需要修改配置文件application.yml


# 设置最大文件上传大小为10MB
#  spring.servlet.multipart.max-file-size=10MB
#  spring.servlet.multipart.max-request-size=10MB

课堂案例

完成菜品的新增和展示

新增功能


    <!-- 菜品添加 -->
    <!-- dialog-->
    <el-dialog v-model="dialogVisible" title="新增页面" width="500"  >
        <el-form :model="form" label-width="auto" style="max-width: 600px">
            <el-form-item label="菜名">
                <el-input v-model="form.dishesName" />
            </el-form-item>
            <el-form-item label="价格">
                <el-input v-model="form.dishesPrice" />
            </el-form-item>
            <el-form-item label="口味">
                <el-input v-model="form.dishesTaste" />
            </el-form-item>

            <el-form-item label="菜系">
                <el-select v-model="form.typeId" placeholder="请选择">
                    <el-option v-for="t  in typeList" :label="t.typeName" :value="t.typeId" />
                </el-select>
            </el-form-item>

            <el-form-item label="菜品参考图">
                <el-upload class="avatar-uploader" action="/api/file/upload" name="fileName" :show-file-list="false"
                    :on-success="handleAvatarSuccess" :before-upload="beforeAvatarUpload">
                    <img v-if="imageUrl" :src="imageUrl" class="avatar" />
                    <el-icon v-else class="avatar-uploader-icon">
                        <Plus />
                    </el-icon>
                </el-upload>
            </el-form-item>

            <el-form-item>
                <el-button type="primary" @click="onSubmit">新增提交</el-button>
                <el-button>Cancel</el-button>
            </el-form-item>
        </el-form>
    </el-dialog>


    <!-- 添加按钮 -->
    <el-button plain @click="dialogVisible = true">
        新增菜品
    </el-button>
    
    
    下面是js代码
    
<script setup>
import { ref } from 'vue'
import { ElMessage } from 'element-plus'
import { Plus } from '@element-plus/icons-vue'
import axios from 'axios'

// 定义表单对象,提交带有图片url的表单对象,准备提交
// 准备做添加
const dialogVisible = ref(false)
// 获取所有的菜系
const typeList = ref()
function findAllType(){
    axios({
        url:'/api/type/findAllType',
        method:'get'
    }).then((res)=>{
        console.log(res.data.object);
        typeList.value = res.data.object
    })
}
findAllType()


const form = ref({
    dishesTaste: '',// 口味
    dishesName: '',
    dishesImg: '',
    dishesPrice: '',
    typeId: ''

})

const imageUrl = ref('')
const handleAvatarSuccess = (
    response,
    uploadFile
) => {
    imageUrl.value = URL.createObjectURL(uploadFile.raw)
    console.log(response)
    form.value.dishesImg = response
}

const beforeAvatarUpload = (rawFile) => {
    if (rawFile.type !== 'image/jpeg') {
        ElMessage.error('Avatar picture must be JPG format!')
        return false
    } else if (rawFile.size / 1024 / 1024 > 2) {
        ElMessage.error('Avatar picture size can not exceed 2MB!')
        return false
    }
    return true
}

// 添加提交
function onSubmit(){
    axios({
        url:'/api/dishes/saveDishes',
        method:'post', 
        data:form.value
    }).then((res)=>{
        console.log(res.data.code  );
        if(res.data.code == 2000){
            ElMessage.success('添加成功')
            dialogVisible.value = false;

            // 刷新页面
            findAllDishes()

        }else{
            ElMessage.error('添加失败')
        }
    })
}
    
    

展示所有菜品的功能

表格标签,的选择

<!-- -------------------------------------------------------表格标签的引入----------------------------------------    -->

    <el-table
    :data="tableData"
    style="width: 100%"
    @selection-change="handleSelectionChange"
  >
    <el-table-column type="selection" width="55" />

    <el-table-column label="参考图" width="120">
      <template #default="scope">
        <el-image :src="scope.row.dishesImg"  style="width: 100px; height: 100px"   />
      </template>
    </el-table-column>
    <el-table-column property="dishesName" label="菜名" width="120" />
    <el-table-column property="dishesImg" label="图片路径" width="300" />
    <el-table-column property="dishesPrice" label="价格" width="120" />
    <el-table-column property="dishesTaste" label="口味" width="120" />
  </el-table>
  
  
  以下是js代码
  
// -------------------------------------------------列表展示所有的菜品信息-------------------------------------------------------
const handleSelectionChange = (val) => {
  multipleSelection.value = val
}
const tableData =ref([]);
// 用于模糊查询及条件查询的对象
const queryParam = ref({
    pageNum:1,
    pageSize:5,
    dishesName:'',
    min:'',
    max:''
})
function findAllDishes(){
    axios({
        url:'/api/dishes/findAllDishes',
        method:'post', 
        data:queryParam.value
    }).then((res)=>{
        console.log(res.data.object.list  );
        if(res.data.code == 2000){
            ElMessage.success('查询成功')
            tableData.value = res.data.object.list  
        }
    })
}
findAllDishes()


</script>

Logo

Agent 垂直技术社区,欢迎活跃、内容共建。

更多推荐