0

我已经为使用多方的文件上传编写了一个 nodejs 代理。在代理中,我们调用 sqlite store 获取环境详细信息并将数据发送到上游服务器进行上传。

前端代码

uploadFile(file, name, alias) {
    const bodyFormData = new FormData();
    bodyFormData.maxDataSize = Infinity;
    bodyFormData.append('fileName', new Blob([
        file,
    ], {
        type: "application/x-tgz"
    }), name)
    
    bodyFormData.append('name', name);

    return axios.post(`/ve/api/v1/files?alias=${alias}`, bodyFormData,
        { headers: { "Content-Type": "multipart/form-data" } }
    )
}

代理代码

app.post("/ve/api/v1/files", (req, res, next) => {
  var count = 0;
  var form = new multiparty.Form();

  form.on('error', function(err) {
      console.log('Error parsing form: ' + err.stack);
  });

  form.on('part', function(part) {
      if (!part.filename) {
          console.log('got field named ' + part.name);
          part.resume();
      }

      if (part.filename) {
          count++;
          console.log('got file named ' + part.name);
          var contentType = part.headers['content-type'];
  
          var formData = {
            fileName: {
                value: part,
                options: {
                    filename: part.filename,
                    contentType: contentType,
                    knownLength: part.byteCount
                }
            },
            name: part.name
          };
          const options = {
            formData: formData,
            headers: {} 
          }
          repo.getEnv(req.query.alias)
          .then(row => {
            host = row.description.split(":")[0].trim();
            port = row.description.split(":")[1].trim();
            options['url'] = `https://${host}:${port}/api/v1/files`
            options['strictSSL'] = false 
            options.headers['authorization'] = req.headers['authorization']
            
            request.post(options, (error, response, body) => {
              if(error) {
                console.log(error);
                res.write(error.message);
                res.end();
              }
              if(response && response.statusCode >= 400) {
                console.log(response.body);
                res.write(response.body);
                res.writeHead(res.statusCode);
                res.end();
              }
            });
            part.resume();
          })
      }

      part.on('error', function(err) {
        console.log(err);
        res.write(err.message);
        res.end();
      });
  });

  form.on('error', (err) => {
    console.log(err);
    res.write(err.message);
    res.end();
  })

  // Close emitted after form parsed
  form.on('close', function() {
      console.log('Upload completed!');
      res.end('Received ' + count + ' files');
  });

  // Parse req
  form.parse(req);
});

该代码适用于小文件,但不适用于大文件。对于出现以下错误的大文件:

Error: form-data: DelayedStream#maxDataSize of 2097152 bytes exceeded.
    at FormData.CombinedStream._checkDataSize (/Users/dummy/Projects/upgrade-ui/node_modules/combined-stream/lib/combined_stream.js:185:19)
    at PassThrough.emit (/Users/dummy/Projects/upgrade-ui/lib/events.js:394:28)
    at PassThrough.source.emit (/Users/dummy/Projects/upgrade-ui/node_modules/delayed-stream/lib/delayed_stream.js:30:21)
    at addChunk (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/readable.js:312:12)
    at readableAddChunk (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/readable.js:287:9)
    at PassThrough.Readable.push (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/readable.js:226:10)
    at /Users/dummy/Projects/upgrade-ui/lib/internal/streams/transform.js:192:12
    at PassThrough._transform (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/passthrough.js:46:3)
    at PassThrough.Transform._write (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/transform.js:184:23)
    at writeOrBuffer (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/writable.js:389:12)
    at _write (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/writable.js:330:10)
    at PassThrough.Writable.write (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/writable.js:334:10)
    at Form.onParsePartData (/Users/dummy/Projects/upgrade-ui/node_modules/multiparty/index.js:479:43)
    at Form._write (/Users/dummy/Projects/upgrade-ui/node_modules/multiparty/index.js:426:10)
    at writeOrBuffer (/Users/dummy/Projects/upgrade-ui/lib/internal/streams/writable.js:389:12)
    at _write (node:internal/streams/writable:330:10) {stack: 'Error: form-data: DelayedStream#maxDataSize o…write (node:internal/streams/writable:330:10)', message: 'form-data: DelayedStream#maxDataSize of 2097152 bytes exceeded.'}
message: 'form-data: DelayedStream#maxDataSize of 2097152 bytes exceeded.'
stack: 'Error: form-data: DelayedStream#maxDataSize of 2097152 bytes exceeded.\n    at FormData.CombinedStream._checkDataSize (/Users/dummy/Projects/upgrade-ui/node_modules/combined-stream/lib/combined_stream.js:185:19)\n    at PassThrough.emit (node:events:394:28)\n    at PassThrough.source.emit (/Users/dummy/Projects/upgrade-ui/node_modules/delayed-stream/lib/delayed_stream.js:30:21)\n    at addChunk (node:internal/streams/readable:312:12)\n    at readableAddChunk (node:internal/streams/readable:287:9… writeOrBuffer (node:internal/streams/writable:389:12)\n    at _write (node:internal/streams/writable:330:10)\n    at PassThrough.Writable.write (node:internal/streams/writable:334:10)\n    at Form.onParsePartData (/Users/dummy/Projects/upgrade-ui/node_modules/multiparty/index.js:479:43)\n    at Form._write (/Users/dummy/Projects/upgrade-ui/node_modules/multiparty/index.js:426:10)\n    at writeOrBuffer (node:internal/streams/writable:389:12)\n    at _write (node:internal/streams/writable:330:10)'
__proto__: Object

如果我对主机和端口进行硬编码而不是从 sqlite db 获取它,则相同的代码可以工作。知道问题可能是什么以及如何解决?

4

0 回答 0