前端使用elementUI框架,後端使用thinkjs,上傳圖片至ali-oss系統

博主在最近的工作中,接觸到了使用thinkjs框架作爲後臺架構的網店後臺Node服務,因爲其使用的qiniu上傳圖片接口不符合需求,需要改爲ali-oss接口,一路遇到不少坑,在此做一下記錄總結。

首先是elementUI前端部分

上傳至後臺,需要將flie文件,轉爲FormData對象後傳至後臺,因使用的組件庫爲element,其upload的組件中,action爲必傳(博主此項傳空),同時將auto-uploadfalse(意思爲不自動上傳),然後上傳操作在on-change事件中完成,回調完畢後重顯DOM。具體代碼片段如下:

<el-form-item
  label="印花圖片"
  prop="url"
  v-if="infoForm.url"
  class="image-uploader-diy new-height"
>
  <img v-if="infoForm.url" :src="infoForm.url" class="image-show" />
  <el-button
    class="dele-list-pic"
    type="primary"
    @click="delePicList"
  >
    <i class="fa fa-trash-o"></i>
  </el-button>
</el-form-item>
<el-form-item label="印花圖片" prop="url" v-else>
  <el-upload
    name="file"
    class="upload-demo"
    action=""
    :on-change="handleOnChangeUpload"
    list-type="picture-card"
    :auto-upload="false"
  >
    <el-button size="small" type="primary">點擊上傳</el-button>
    <div slot="tip" class="el-upload__tip">
      只能上傳jpg/png文件,且不超過500kb
    </div>
  </el-upload>
</el-form-item>

博主是通過infoForm.url的有無,來判斷是顯示上傳區域還是圖片。

用於上傳的onChange事件如下:

handleOnChangeUpload(file) {
  let formData = new FormData() // new一個FormData實例
  formData.append('file', file.raw)
  // 配置請求頭
  let config = {
    headers: {
      'Content-Type': 'multipart/form-data',
    },
  }
  // 發送axios的POST請求
  this.axios
    .post(this.root + 'goods/uploadImageToAliOss', formData, config)
    .then((response) => {
      this.infoForm.url = response.data.data
    })
}

後臺Node部分

由於後臺是使用了thinkjs作爲架構搭建,其官方文檔上,對於FormData數據的接收並不需要通過babel-parse插件或者multer插件來作接收,只需要簡單地調用一下this.file(參數),參數爲你所傳遞的file名字。

file接收了,那就要上傳至OSS系統中,博主這裏使用了ali-oss插件,只要簡單安裝導入const OSS = require('ali-oss')後便可以使用。

圖片file文件的讀取,藉助了fs庫和path,將文件轉爲blob類型後,通過OSS的put方法將圖片上傳至OSS系統中,具體示例代碼如下:

// 上傳圖片到OSS接口 start
async uploadImageToAliOssAction() {
  const file = this.file('file')
  let file_re = this.readFileAsBuffer(file)
  let client = new OSS({
    region: '這裏填region',
    //雲賬號AccessKey有所有API訪問權限,建議遵循阿里雲安全最佳實踐,部署在服務端使用RAM子賬號或STS,部署在客戶端使用STS。
    accessKeyId: '這裏填accessKeyId',
    accessKeySecret: '這裏填accessKeySecret',
    bucket: '這裏填bucket',
  })
  const imgName = think.uuid('v4') // uuid.v4生成文件名(thinkjs自帶,若爲純node服務則安裝'UUID'插件,使用UUID.v4()即可生成)
  const imgType = file.type.substr(6, 4) // 取圖片類型
  const filePath = `goodsMask/${imgName}.${imgType}` // 圖片存儲的路徑
  // 想要成功上傳base64數據到OSS,必須通過put接口傳轉換後的buffer文件
  let response = await client.put(filePath, file_re)
  if (response.res.status == 200) {
    return this.success(response.url) // 返回OSS的圖片地址到前端
  }
}
//將文件轉爲blob類型
readFileAsBuffer(file) {
  let filePath = path.resolve(file.path) // 讀取路徑
  let data = fs.readFileSync(filePath) // 讀取文件
  let base64File = new Buffer.from(data, 'base64') // base64轉buffer
  return base64File
}
// 上傳圖片到OSS接口 end

至此,完整的上傳過程就完成了,是不是感覺很簡單,但是菜鳥博主花了好久才摸索出來。。。
最後一點,使用ali-oss插件,在後臺中使用不了new OSS.Buffer()將文件轉Buffer類型,博主起初直接使用了new Buffer()去轉,結果控制檯報錯,查了一下,原來是安全性問題,後邊換成了new Buffer.form()
Buffer

參考資料:
elementUI的Upload組件
ali-oss的Node配置介紹
Buffer介紹

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章