文件上传和公共组件的开发

一个职场小白,增删改查都写不明白,去公司好多都看不懂,老师可能教过,但自己不写就不明白其中的乐趣,要做一个文件上传,我们以图片上传为列,首先一个前后台交互的问题,第一步一定要有自己的前端,前端怎样与后台交互,后台怎样控制,最后操作数据库,怎样写sql语句。

1先画一个页面 一个页面有三个部分

    <template></template>放前端我们能看到的所有东西,大部分数据和按钮,好不好看就看个人的前端水平,

    <script></script>导入资源一些前端要用的依赖,自定义用来接收后台数据的变量数组什么的主要有import 导入一些依赖,js写的一些方法,之前在公司写的项目用JS实现前后台交互的 在JS写好与后台交互的方法通过import在页面导入这些方法

<script>

  import Pagination from "../../components/pagination";
  import File from "../../components/file.vue";
  export default
  {
    component:{Pagination,File},
    name: 'business-teacher',
    components: {Pagination,File},
    data:function(){
      return{
        teacher:{},/*映射表单数据*/
        teachers:[]
      }
    },
data: function () {
      return {
        course: {},/*映射表单数据*/
        courses: [],
        COURSE_LEVEL: COURSE_LEVEL,
        COURSE_CHARGE: COURSE_CHARGE,
        COURSE_STATUS: COURSE_STATUS,
        categorys: [],
        tree: {},
        savaContentLabel:"",/*内容v保存时生成的变量,用来记录自动保存的时间*/
        sort: {
          id: "",
          oldSort: 0,
          newSort: 0
        },/*用来更新排序*/
        teachers:[],/*接收所有的老师*/
      }
    },
data: function () {}用来定义一些我们用来存放数据的集合,数组,全局变量,
mounted: function () {}用来执行页面初始化要执行的方法,比如数据的查询操作,
methods:{}自定义一些方法页面调用,在我最近学的项目中,在这些方法中会会用ajax请求后台contrller层的方法,
   <style scoped></style scoped>,定义一些标签的共有的属性 如字体大小,颜色等
<template>
  <div>

  
        <!--hidden隐藏 input class="hidden"-->
        <input  ref="file" type="file" v-on:change="uploadFile()" v-bind:id="inputId+'-input'">


  </div>

</template>

定义一个div 容器 用input自带的文件上传type="file"默认是text 定义一个change事件点击的时候会触发uploadFile()方法,在mounted: function () {}定义一个uploadFile()方法

 /*
      * 文件上传方法
      * */
      uploadFile(){
        let _this=this;
        let formData=new window.FormData;

        console.log("开始判断文件格式")
        // let file=_this.$refs.file.files[0];取得控件上传的数据
        let file=_this.$refs.file.files[0];
        console.log("开始判断文件格式2")
        //判断文件格式
        //let suffixs=["jpg","jpeg","png"];
        let suffixs=_this.suffixs;
        let fileName=file.name;
        let suffix=fileName.substring(fileName.lastIndexOf(".")+1,fileName.length).toLowerCase();
        let validateSuffix=false;
        for(let i=0;i<suffixs.length;i++){
          if(suffixs[i].toLowerCase()===suffix) {
            validateSuffix = true;
            break;
          }
        }
        if(!validateSuffix){
          toast.warning("文件格式不正确!只支持上传:"+suffixs.join(","));
          //每次上传完都要清空,解决重复上传同样的文件时不触发上场的方法
          $("#" + _this.inputId + "-input").val("");
          return;
        }
        console.log("开始上传")
        //key:"file"必须和后端controller参数名一致
        /*formData.append('file',document.querySelector('#file-upload-input').files[0]);*/
        formData.append('file',file);
        _this.$ajax.post('http://localhost:9000/file/admin/upload',formData)
          .then((response)=>{
            let resp = response.data;

            console.log("文件上传成功===",resp)
            _this.afterUpload(resp);
            //每次上传完都要清空,解决重复上传同样的文件时不触发上场的方法
            $("#" + _this.inputId + "-input").val("");

           /* console.log("头像上传的路径===",response)
            _this.teacher.image=image;*/
          });
        console.log("结束上传")
      },

开始的时候使用的是formData.append('file',document.querySelector('#file-upload-input').files[0]);根据id获取要上传的文件

后来是用ref="file"定义一个别名,根据别名来获取上传的文件

主要是通过_this.$ajax.post('http://localhost:9000/file/admin/upload',formData)请求后台contrller层的方法,



/**
 * @author admin
 * @version 1.0.0
 * @ClassName TestController.java
 * @Description TODO
 * @createTime 2022年01月22日 21:11:00
 */
@RequestMapping("/admin")
@RestController
public class UploadController {
  

    @RequestMapping("/upload")
    public ResponseDto upload(@RequestParam MultipartFile file) throws IOException {

      

        //保存文件到本地
        String fileName=file.getOriginalFilename();
        String key= UuidUtil.getShortUuid();//自己生成的八位id
        String fullPath="D:/2022/course1/image/"+key+"-"+fileName;//本地路径
        File dest=new File(fullPath);//目标路径
        file.transferTo(dest);
  


        ResponseDto responseDto = new ResponseDto();
        responseDto.setContent("http://localhost:9000/file/f/"+key+"-"+fileName);
        return responseDto;

    }
}

无论怎们样看的时候只要前端能访问到后台就行,这样我们一个完整的文件上传的功能就结束了,做一些 优化最终的效果

很多地方都会用到文件上传的功能怎样给他做成一个公共组件呢,公共组件怎样使用呢,总体就是把变化的部分做成公共组件的属性,让使用者能在公共组件自由定义,

export default
 {
   name: 'file',//标签名,自定义组件的名称
   props: {//在这里定义,自定义组件的属性,就是使用者能自由定义的部分,能定义一些方法
            /*标签要暴露的属性*/
           text:{
             default: "文件上传"
              },
               /*回调函数*/
          afterUpload: {
                type: Function,
               default: null
               },
          }
}

最终代码效果

<template>
  <div>

        <button type="button" v-on:click="selectFile()"  class="btn btn-white btn-default btn-round">
          <i class="ace-icon fa fa-upload"></i>
          {{text}}
        </button>
        <!--hidden隐藏 input-->
        <input class="hidden" ref="file" type="file" v-on:change="uploadFile()" v-bind:id="inputId+'-input'">


  </div>

</template>

<script>
  export default {
    // eslint-disable-next-line vue/multi-word-component-names
    name: 'file',//标签名
    props: {
      /*标签要暴露的属性*/
      text:{
        default: "文件上传"
      },
      inputId:{
        default: "file-upload"
      },
      suffixs:{
        default: []
      },
      /*回调函数*/
      afterUpload: {
        type: Function,
        default: null
      },

    },
    data: function () {
      return {

      }
    },
    methods: {
      /*
      * 文件上传方法
      * */
      uploadFile(){
        let _this=this;
        let formData=new window.FormData;

        console.log("开始判断文件格式")
        // let file=_this.$refs.file.files[0];取得控件上传的数据
        let file=_this.$refs.file.files[0];
        console.log("开始判断文件格式2")
        //判断文件格式
        //let suffixs=["jpg","jpeg","png"];
        let suffixs=_this.suffixs;
        let fileName=file.name;
        let suffix=fileName.substring(fileName.lastIndexOf(".")+1,fileName.length).toLowerCase();
        let validateSuffix=false;
        for(let i=0;i<suffixs.length;i++){
          if(suffixs[i].toLowerCase()===suffix) {
            validateSuffix = true;
            break;
          }
        }
        if(!validateSuffix){
          toast.warning("文件格式不正确!只支持上传:"+suffixs.join(","));
          //每次上传完都要清空,解决重复上传同样的文件时不触发上场的方法
          $("#" + _this.inputId + "-input").val("");
          return;
        }
        console.log("开始上传")
        //key:"file"必须和后端controller参数名一致
        /*formData.append('file',document.querySelector('#file-upload-input').files[0]);*/
        formData.append('file',file);
        _this.$ajax.post('http://localhost:9000/file/admin/upload',formData)
          .then((response)=>{
            let resp = response.data;

            console.log("文件上传成功===",resp)
            _this.afterUpload(resp);
            //每次上传完都要清空,解决重复上传同样的文件时不触发上场的方法
            $("#" + _this.inputId + "-input").val("");

           /* console.log("头像上传的路径===",response)
            _this.teacher.image=image;*/
          });
        console.log("结束上传")
      },
      /*
      * 用一个按钮控制文件上传,触发文件上传方法根据id 触发一次点击事件
      *
      * */
      selectFile(){
        let _this = this;
        $("#" + _this.inputId + "-input").trigger("click");

      },

    }
  }
</script>

那要怎么使用呢,在我们需要使用文件上传功能的页面,先导入我们的公共组件

import File from "../../components/file.vue";
export default
  {
    component:{File},
    
    components: {File},
  }

在需要实现上传功能的位置使用自定义标签,标签名和 自定义属性的name一致

最终实现效果

v-bind:后面接自己定义的属性,我不知道为什么,就查查百度,真记不住那么多

1.插值操作主要作用
    :将Vue实例中的数据插入到我们模板的内容当中,并改变data可以动态改变显示。
      
2.动态绑定属性
    :除了内容需要动态来决定外,元素的某些属性我们也希望动态来绑定。
      比如,动态绑定a元素的href属性、动态绑定img元素的src属性。
      
     Mustache双括号语法,只能在内容插值里使用,属性值是不可以用的
     <img src="{{imgURL}}">、<img src="imgURL">是错误的,
     vue不会解析将data值放里面去;会被当做字符,而不是变量;

 3.动态绑定属性则使用v-bind指令:
     作用:动态绑定属性
     缩写::

     在前面加上v-bind后,就表明将该属性的属性值当成一个变量
     vue会对它解析,将解析到的变量 赋予data属性中对应的值。


 一般图片的img中src属性值都是不固定的,像轮播图等
  src属性值:可以是服务器端请求过来的
  服务器端请求过来的值放在vue实例的data中,然后将data中的属性赋给src属性值来使用
  则响应式:修改data中的属性也可以实时响应,动态变化;
————————————————
版权声明:本文为CSDN博主「卡布达。」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/qq_45700583/article/details/108968570

最终实现效果是

就可以在多个地方复用了。

 

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值