React antdesign upload組件自定義上傳到S3

簡介

關於上傳到S3,本文服務模塊使用的是‘aws-sdk’ putObject()上傳。UI模塊使用的是antd中的upload組件,在使用antd組件的時候發現官方提供的上傳方式有兩種:javascript

  1. 使用路徑上傳,antd中有一個屬性action須要上傳到的地址。
  2. 使用自定義上傳,antd中的customRequest。 本文選用的是第二種,自定義上傳會覆蓋組件默認的上傳行爲,因此咱們須要去定義progress、onSuccess、onError。 本文會使用到的技術:React,Rxjs,採用TSLint校驗。

先看簡單的dom模塊

很少說直接上代碼,一個簡單的自定義上傳。html

import React from 'react';
import { Subject } from 'rxjs';
import { Upload } from "antd";
import {IS3Config, Upload$ } from "../../../core/services/s3service";

interface IParam {
  onProgress: ({ }, f: UploadFile) => void;
  onSuccess: () => void;
  onError: () => void;
  file: UploadFile & { webkitRelativePath: string };
}
export default class UploadComponent extends React.Component {
  public S3token: IS3Config  = {}; // 您的S3臨時令牌
  public bucket: string = ''; // 您要上傳到的bucket名字
  public key: string = ''; // bucket下面的路徑
  private upload = (param: IParam) => {
    Upload$(this.S3token, this.bucket, this.key, param).subscribe(
        () => console.log('成功'),
        () => console.log('失敗'),
    );
  }
  public render () {
    return (
      <Upload customRequest={this.upload}> <Button> <Icon type="upload" /> Upload </Button> </Upload> ); } } 複製代碼

'aws-sdk'上傳 服務模塊

  1. 首先須要對上傳進行配置,如下是一個對S3進行配置的函數。 這個函數中須要您的S3臨時令牌,令牌須要有對S3進行操做的權限。
// s3service.tsx
// 引入模塊
import { Subject } from 'rxjs';
import { config, S3, AWSError } from 'aws-sdk';
import { PutObjectOutput} from '../../../node_modules/aws-sdk/clients/s3';
import { UploadFile } from '../../../node_modules/antd/lib/upload/interface';
// 配置S3的接口
export interface IS3Config {
  AccessKeyId?: '';
  SecretAccessKey?: '';
  SessionToken?: '';
}
// 對S3進行配置
export const createS3 = (cfg: IS3Config) => {
  const setting = { //您的S3臨時令牌
    accessKeyId: cfg.AccessKeyId,
    secretAccessKey: cfg.SecretAccessKey,
    sessionToken: cfg.SessionToken,
  };
  config.update(setting);
  config.region = "us-east-1";

  const s3 = new S3({
    apiVersion: '2006-03-01',
  });
  return s3;
};

複製代碼
  1. putObject 上傳文件及自定義progress、success、error
interface IUpload {
  onProgress?: ({ }, f: UploadFile) => void; // 須要重寫的antd的progress函數
  onSuccess?: () => void; // antd中progress百分百時的成功函數
  file: UploadFile; // 上傳失敗的progress函數
  onError: () => void;
}
export const Upload$ = (s3Config: IS3Config, bucket: string, key: string, body: IUpload): Subject<PutObjectOutput> => {
  const s3 = createS3(s3Config); //傳入您的S3令牌
  const s3subject = new Subject(); //建立一個Subject主體
  s3.putObject( // s3上面的putObject方法 第一個參數是一個對象,第二個參數是一個函數,函數有兩個值,1.表示上傳失敗,2.表示上傳成功
    {
      Body: body.file, // 是文件類型
      Bucket: bucket, // 對應S3上的bucket
      Key: key, // 須要上傳到的路徑
    },
    (err: AWSError, resp: PutObjectOutput) => {
      if (err) {
        log(err);
        s3subject.error(err); // 上傳失敗時調用
      } else {
        s3subject.next(resp); // 上傳成功時調用
      }
    }).on('httpUploadProgress', (progress) => { // 上傳S3時‘httpUploadProgress’函數裏能夠定義progress
      const percent = 100 * progress.loaded / progress.total;
      // https://github.com/react-component/upload/blob/master/examples/customRequest.js onProgress 第一個參數是進度條的值,第二個參數是當前上傳的文件 
      // body.onProgress 是antd中的onProgress 重寫的progress
      body.onProgress ? body.onProgress({ percent }, body.file) : void 0;
      if (percent === 100 && body.onSuccess) body.onSuccess(); // 上傳到百分百時調用 antd中的onSuccess 
    }).on('httpError', (err) => {
      if (err && body.onError) {
        log(err);
        body.onError();
        s3subject.error(err);
      }
    });
  return s3subject;
};
複製代碼

感謝https://github.com/yalishizhude的指導

參考文獻

https://github.com/react-component/upload/blob/master/examples/customRequest.js前端

https://ant.design/components/upload-cn/java

https://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/S3.html#putObject-propertynode

原文連接:tech.gtxlab.com/upload.htmlreact


做者信息:寧文飛,人和將來大數據前端工程師git

相關文章
相關標籤/搜索