🚀阿里云OSS直传之PUT

2,977 阅读4分钟

🍉场景需求

最初上传文件是借助后台API来实现文件的存储,相对现在主流的OSS直传来说,还是比较繁琐的。之前介绍的文件上传是基于OSS直传的POST方式实现的,需要借助FormData来实现文件的上传,相关代码案例请参考我之前写的文章 iView文件上传(OSS直传)。 此次是借助阿里云提供的 ali-oss 来实现文件上传,此方法还支持大文件大断点续传,如有需要请参考OSS云存储官方提供的文档API。OSS的put上传方式支持异步上传和同步上传,上传成功后直接返回上传文件在阿里云云存储上的绝对路径;之前的POST上传方式是将文件对象转换成FormData对象来上传的,其返回的是上传文件的相对路径,若想获取文件在云存储上的绝对路径,还需要自己进行手动拼接,相比较PUT上传方式来说比较麻烦,而且还容易出错。

🛵前期处理

首先要根据自己的实际情况来选择符合自己的OSS文件上传方式。此次我主要就OSS的PUT文件上传方式做介绍。 先登录阿里云OSS云存储的管理后台,进入自己索要配置的bucket类型,然后查找配置跨域资源共享(CORS)规则, 来对该bucket的跨域资源共享规则按照官方文档给的要求来进行相应的设置。 p232679.jpg

注: 此页面为配置跨域规则的页面,请确认已勾选PUT请求方式。 若没勾选此方式,当采用PUT方式上传文件时,控制台会报请求跨域错误。

🌰代码案例

  • 安装所需依赖
/* 时间处理工具 */
import dayjs from "dayjs";
/* 阿里云OSS文件直传工具 */
import OSS from "ali-oss";
/* 基于VUE的前端UI框架 */
import { ElMessage } from "element-plus";

注意:

  1. dayjs 在后续处理文件路径和文件重命名时需用到,若无需文件重命名则不用安装;
  2. element-plus 为基于Vue3的ElementUI升级版,此处主要用于文件上传时候相关校验的提示;
  • 文件重命名
const fileRename = (file, rootPath = "", fileType = [], size = 0) => {
    /* 判断传过来的值是否为file对象 */
    if (!(file instanceof Object)) return null;
    // 文件大小限制
    if (size && file.size >= size * 1024 * 1024) {
        ElMessage.warning(`上传的文件大小不能超过 ${size}M,请重新上传!`);
        return null;
    }
    // 将文件名字做英文字符小写处理,为了方便判断上传文件的格式
    let fileName = file.name.toLowerCase(),
        dotIndex = fileName.lastIndexOf("."),
        // 获取文件后缀名
        fileSuffix = fileName.substr(dotIndex);
    // 传过来的用于判断文件类型的数组,拼接成字符串
    let fileTypeString = fileType.join(".");
    // 文件类型限制
    if (fileTypeString && !fileTypeString.includes(fileSuffix)) {
        ElMessage.error("上传文件类型有误,请重新上传!");
        return null;
    }
    /**
     * 文件路径处理
     * 基于dayjs来分配文件路径和对文件进行重命名
     *  */
    let filePath = dayjs().format("YYYY_MM/DD_HHmmss_SSS");
    // 返回文件在OSS上的相对文件路径
    return rootPath + filePath + fileSuffix;
};

文件重命名参数介绍:

  1. file:文件对象;
  2. rootPath:文件根路径即在OSS存储的根目录;
  3. fileType:要校验的文件类型格式;
  4. size:上传文件的大小限制。
  • OSS文件上传
/**
 * @module 文件上传
 * @param {Object} file - 文件对象
 * @param {String} rootPath - 文件根路径
 * @param {Array} fileType - 文件类型
 * @param {Number} size - 文件大小
 * @returns {String} - 上传文件地址
 **/
const OSSUpload = async (file, rootPath, fileType, size) => {
    // 调用fileRename生成的文件相对路径格式:xxxx.png,必须带后缀名,否则无法读取上传后的文件
    let fileName = fileRename(file, rootPath, fileType, size);
    if (!fileName) return null;
    // *配置client-OSS
    let client = new OSS({
        accessKeyId: "your access key" /* 通过阿里云控制台创建的access key */,
        accessKeySecret: "your access secret" /* 通过阿里云控制台创建的access secret */,
        region: "oss-cn-beijing" /* bucket 所在的区域 */,
        stsToken: "" /* 鉴权,sts方式需要使用,若不需要请删除或注释掉 */,
        bucket: "your bucket name" /* 通过控制台创建的bucket,【OSS文件前缀】 */
    });

    try {
        /**
         * OSS的put直传
         * fileName:文件名【带后缀名】
         * file:文件对象
         *  */
      	// File 对象
        let { res, url } = await client.put(fileName, file);      
      	// Blob 对象
      	// let { res, url } = await client.put(fileName, new Blob(file));  
      	// OSS Buffer 对象
      	// let { res, url } = await client.put(fileName, new OSS.Buffer(file));
      
        if (res.status == 200) {
            ElMessage.success("上传成功");
            return url;
        }
        ElMessage.error("上传失败");
        return null;
    } catch (e) {
        ElMessage.error("文件上传失败");
        return null;
    }
};

🚀:多行注释处请留心配置,否则会报错。OSS.JS附件已上传,下载后配置好OSS相关参数就可直接使用。oss.js

🍅:OSS的put上传方式第二参数即file,支持File 对象Blob 数据以及OSS Buffer 等格式。

  • OSS直传使用
// 导入封装的OSS插件
import oss from "./oss.js";

/**
 * @param {Object} file - 文件对象
 * @param {String} rootPath - 文件根路径(默认为空、例:“filepath/”)
 * @param {Array} fileType - 文件类型限制(默认 [] 不限制,例:['.png','.jpeg'])
 * @param {Number} size - 文件大小限制(单位:兆、默认 0 不限制、例:1)
 **/
//获取到上传文件后调用OSS直传
// 方式一:
oss(file, "", [], 0).then(ossUrl = >{
	if ( !! ossUrl) {
		// 上传成功,返回上传后的绝对路径
	} else {
		// 上传失败,返回null
	}
});
// 方式二:不做任何限制时,参数可省略
oss(file).then(ossUrl = >!!ossUrl && (uploadURL = ossUrl));

🔔结语

🥇🥈🥉:前期努力搬的砖,都是为后期造轮子准备的。若对您有所帮助,请帮忙点个赞👍!