Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

重複使用 createReadStream #38

Open
iamso1 opened this issue Jan 3, 2021 · 1 comment
Open

重複使用 createReadStream #38

iamso1 opened this issue Jan 3, 2021 · 1 comment

Comments

@iamso1
Copy link

iamso1 commented Jan 3, 2021

感謝使用 Node.js Taiwan AMA,以下附上簡單提問範例供參考,請把內容改成你自己遇到的問題

目的

我希望使用Nodejs 呼叫 API 上傳圖片到server �

使用的工具

�希望使用 form 的方式上傳檔案 ( https://www.npmjs.com/package/form-data )
我使用的是範例程式裡面的第三種方法

使用 fs.createReadStream的方法讀取圖片
最後post 這個 form 物件到 API去

form.append('my_file', fs.createReadStream('/foo/bar.jpg'));

操作流程

我會多次呼叫上傳 API 因為不希望每次都要重新讀取一次圖片 (fs.createReadStream)
所以在迴圈外面先讀取一次檔案, 像下面這樣:

const fileStream= fs.createReadStream('/foo/bar.jpg'));

(async()=>{
    for(let i=0;i<3;i++){
      const formData=new FormData();
      formData.append('file', fileStream);
      await axios.post('url', {data:formData} ) // 呼叫API 上傳剛剛的檔案
    }
})();

遇到的問題

API都會回應 http 504 timeout

嘗試過的解法

  1. 將createReadStream放在迴圈裡面, 即每次呼叫都重新讀取檔案 可正常執行 (但是拉出來回圈外面就會失敗)
    查了原因應該是因為readStream 被讀取一次後 該stream 狀態就變成 readable: false

  2. 嘗試改存成 buffer (像form-data的第二種方法 如下:)

    form.append('my_buffer', new Buffer(10));

配合使用fs.readfile的方法
但是使用form-data 送到 API 時 就會失敗 好像只能用createReadStream能成功

@shinder
Copy link

shinder commented Jan 5, 2021

用 buffer 是可以正常執行的

    const fs = require('fs');
    const axios = require('axios');
    const FormData = require('form-data');
    try {
        (async () => {
            const buffer = await fs.promises.readFile(__dirname + '/ttt.png');
    
            const formData = new FormData();
            formData.append('avatar', buffer, {filename: 'ttt.png'});
            formData.append('name', 'shinder');
    
            for (let i = 0; i < 3; i++) {
                await axios.post(
                    'http://localhost:3000/form1',
                     formData.getBuffer(),
                     {
                        headers: formData.getHeaders()
                    });
            }
        })()
    } catch(ex) {
        console.log('ex:', ex);
    }

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants