使用axios上传文件到阿里云对象文件存储服务器oss

背景

  • OSS可用于图片、音视频、日志等海量文件的存储。各种终端设备、Web网站程序、移动应用可以直接向OSS写入或读取数据。OSS支持流式写入和文件写入两种方式。使用阿里云oss做文件存储的时候,不可避免的涉及到文件的上传,大概分为两种方式:

服务端验证上传

  • 先将文件传递到应用服务器,再由应用服务器上传至oss服务器,这种方式的优点是简单易懂,nodejs只需要按照文档使用ali-oss中间件上传就行,本文重点不放在这种方式,如果有需要可以私信我。这种方式的缺点是,文件要先上传到应用服务器,再上传到oss,占用带宽资源,过程虽然简单易于操作但是比较繁琐。

服务端签名前端直传

  • 这种方式是我比较推荐使用的,但是需要自己对移动端进行签名,官方的例子给出了一个php版本的签名服务文件,同时上传使用的是plupload这个功能强大,但是不支持模块化使用的插件,于是经过一番琢磨,将php版本的签名服务改成了js版本,同时提供axios版本的文件上传供大家参考,亲测可行。

服务代码:


const crypto =require('crypto')
async getSingature(ctx){
        ctx.status=200;
        const _config={...}//里面存放阿里云oss的配置参数,不详细说明,用的都应该懂
        const OSSAccessKeyID=_config['spring.aliyun.oss.access-key-id']
        const OSSAccessKeySecret=_config['spring.aliyun.oss.access-key-secret']
        const OSSEndPoint=_config['spring.aliyun.oss.end-point']
        const OSSBucketName=_config['spring.aliyun.oss.bucket-name'];
        let now=new Date();
        const expire=300;
        //签名有效时间五分钟,可自行设定
        const end = now.getTime()/1000 + expire;
        //过期时间
        let expiration=new Date((now.getTime()/1000+expire)*1000);
        //oss服务器时间格式iso
        expiration=expiration.toISOString();
        //上传目录
        const dir= ''
        //上传的限制规则
        const condition=['content-length-range',0,1048576000]
        const start=['start-with','key',dir];
        const conditions=[condition]
        const arr={
            expiration,
            conditions
        }
        //上传策略(规则对象转json字符串)
        const policy=JSON.stringify(arr);
        //进行base64编码
        const base64_policy= (new Buffer(policy)).toString('base64');
        
        const string_to_sign=base64_policy;
        //使用crypto签名
        const signature=crypto.createHmac('sha1',     OSSAccessKeySecret).update(string_to_sign).digest().toString('base64');
        const host="http://"+OSSBucketName+'.'+OSSEndPoint.split('//')[1];
        const accessid=OSSAccessKeyID;
        //返回结果给前端
        return {
            accessid,
            signature,
            policy:base64_policy,
            expire:end,
            dir,
            host
        }
    }

前端上传:
注意:oss一次只能上传一个文件(只有一个key),可以循环执行post,key为上传到oss后的文件名。signatureObj这里是上面nodejs服务端返回的签名对象

    var file=ducument.getElementById('file').files[0] 
    var formData = new FormData();
    formData.append('key','上传文件名');
    formData.append('name',file.name)
    formData.append('policy',signatureObj.policy)
    formData.append('OSSAccessKeyId',signatureObj.accessid)
    formData.append('success_action_status','200')
    formData.append('callback','')
    formData.append('signature',signatureObj.signature)
    formData.append('file',file.file)
    axios({
    url:url,
    method:'post',
    data:formdata,
    headers: { 'Content-Type': 'multipart/form-data' }
})

弱鸡全栈攻城狮

2k 声望
4.6k 粉丝
0 条评论
推荐阅读
复杂场景下的h5与小程序通信
在套壳小程序盛行的当下, h5调用小程序能力来打破业务边界已成为家常便饭,h5与小程序的结合,极大地拓展了h5的能力边界,丰富了h5的功能。使许多以往纯h5只能想想或者实现难度极大的功能变得轻松简单。但在套壳...

懒懒的技术宅16阅读 3k评论 5

ESlint + Stylelint + VSCode自动格式化代码(2023)
安装插件 ESLint,然后 File -> Preference-> Settings(如果装了中文插件包应该是 文件 -> 选项 -> 设置),搜索 eslint,点击 Edit in setting.json

谭光志34阅读 20.7k评论 9

安全地在前后端之间传输数据 - 「3」真的安全吗?
在「2」注册和登录示例中,我们通过非对称加密算法实现了浏览器和 Web 服务器之间的安全传输。看起来一切都很美好,但是危险就在哪里,有些人发现了,有些人嗅到了,更多人却浑然不知。就像是给门上了把好锁,还...

边城32阅读 7.3k评论 5

封面图
涨姿势了,有意思的气泡 Loading 效果
今日,群友提问,如何实现这么一个 Loading 效果:这个确实有点意思,但是这是 CSS 能够完成的?没错,这个效果中的核心气泡效果,其实借助 CSS 中的滤镜,能够比较轻松的实现,就是所需的元素可能多点。参考我们...

chokcoco24阅读 2.2k评论 3

你可能不需要JS!CSS实现一个计时器
CSS现在可不仅仅只是改一个颜色这么简单,还可以做很多交互,比如做一个功能齐全的计时器?样式上并不复杂,主要是几个交互的地方数字时钟的变化开始、暂停操作重置操作如何仅使用 CSS 来实现这样的功能呢?一起...

XboxYan25阅读 1.7k评论 1

封面图
在前端使用 JS 进行分类汇总
最近遇到一些同学在问 JS 中进行数据统计的问题。虽然数据统计一般会在数据库中进行,但是后端遇到需要使用程序来进行统计的情况也非常多。.NET 就为了对内存数据和数据库数据进行统一地数据处理,发明了 LINQ (L...

边城17阅读 2k

封面图
过滤/筛选树节点
又是树,是我跟树杠上了吗?—— 不,是树的问题太多了!🔗 相关文章推荐:使用递归遍历并转换树形数据(以 TypeScript 为例)从列表生成树 (JavaScript/TypeScript) 过滤和筛选是一个意思,都是 filter。对于列表来...

边城18阅读 7.8k评论 3

封面图

弱鸡全栈攻城狮

2k 声望
4.6k 粉丝
宣传栏