LoginSignup
2
1

More than 1 year has passed since last update.

arraybuffer 画像を form-data で Node.js サーバにアップロードできない問題

Last updated at Posted at 2022-06-16

LINE WORKS のトーク Bot を使って送信した画像をLINE WORKSのストレージからダウンロードして、 Node.js サーバーにアップロードするサンプルです。
LINE WORKSのストレージからダウンロードした画像はarraybufferの形です。
axiosを利用します。

ダメなコード

import Axios from 'axios';
import FormData from 'form-data';

......

try {
  const lwResponse = await Axios.get(
    'http://storage.worksmobile.com/openapi/message/download.api',
    {
      headers: {
        consumerKey: consumerKey,
        authorization: 'Bearer ' + accessToken,
        'x-works-apiid': apiId,
        'x-works-resource-id': resourceId,
      },
      responseType: 'arraybuffer',
    }
  );

  const formdata = new FormData();
  formdata.append('file', arraybuffer);

  await Axios.post(
    toUrl,
    formdata,
    {
      headers: {
        'content-Type': 'multipart/form-data',
      }
    }
  )
  .then((response) => {
    console.log(response.data);
  })
  .catch((error) => {
    throw error;
  });
} catch (error) {
  console.error(error);
}

form-data の boundary(境界線) エラーと403エラーが出ました。
ヘッダーを出力して見ると、確かにboundaryのデータがありませんでした。

Content-Type: multipart/form-data; boundary=

403エラーの原因は、アップロードしようとするファイルのメタ情報が足りないからです。

Bufferデータを処理しないとアップロードできないと思いましたが関係ありませんでした。

修正後のコード:

import Axios from 'axios';
const FormData = require('form-data');

......

try {
  const lwResponse = await Axios.get(
    'http://storage.worksmobile.com/openapi/message/download.api',
    {
      headers: {
        consumerKey: consumerKey,
        authorization: 'Bearer ' + accessToken,
        'x-works-apiid': apiId,
        'x-works-resource-id': resourceId,
      },
      responseType: 'arraybuffer',
    }
  );

  const formdata = new FormData();
  formdata.append('file', imageBuffer, {
    filename: 'dummy.jpg', //ポイント1:ダミーファイルを設定してメタ情報をつける
  });

  await Axios.post(
    toUrl,
    formdata,
    {
      headers: formdata.getHeaders(), //ポイント2:getHeadersでヘッダーを取得
    }
  )
  .then((response) => {
    console.log(response.data);
  })
  .catch((error) => {
    throw error;
  });
} catch (error) {
  console.error(error);
}
  • ポイント1:ダミーファイルを設定してメタ情報をつける
    画像をNode.js サーバにダウンロードして保存先の実際のファイル名で指定する方法もあります。ダウンロードした画像を参照しない場合はダミーファイル名のがおすすめです。

  • ポイント2:FormDataのgetHeadersでヘッダーを取得
    通常のcontent-Type: multipart/form-dataだとboundary情報がなくなるようです。

参考
https://qiita.com/itoudium/items/d9f04f379d34265387d8

2
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
1