Повторно собрать двоичный файл после отправки flow.js на node/express server - программирование
Подтвердить что ты не робот

Повторно собрать двоичный файл после отправки flow.js на node/express server

Я не могу понять, как использовать библиотеку flow.js с бэкэнд node и основывать мой код с образцом на flow.js github.

Я получаю blob файлы, но я не собираю двоичные файлы, после чего загрузка завершается. Окончательный get не запускается, или мой маршрут неверен:

  app.get('/download/:identifier', function(req, res){
    console.log('we writin')
    flow.write(req.params.identifier, res);
  });

у кого-либо есть опыт работы с этим, может получиться как миллион очков stackoverflow, потому что это, по-видимому, является общей проблемой при использовании node.js и flow.js, и вот еще два оставшихся неотвеченных вопроса:

Загрузка файла Flowjs - AngularJS и Node Повторная сборка фрагментов файлов, созданных при многостраничной загрузке

4b9b3361

Ответ 1

Я нашел метод, который работает, но не может быть идеальным.

Здесь я вызываю flow.write в flow.post, если status есть done и currentTestChunk > numberOfChunks. Я делаю больше, чем проверку, потому что иногда flow.post отправляет status done более одного раза, как упоминалось здесь.

Изменить: Я добавил способ очистки кусков после создания файла.

flow.post(req, function(status, filename, original_filename, identifier, currentTestChunk, numberOfChunks) {
        console.log('POST', status, original_filename, identifier);
        res.send(200);
        if (status === 'done' && currentTestChunk > numberOfChunks) {
            var stream = fs.createWriteStream('./tmp/' + filename);
            //EDIT: I removed options {end: true} because it isn't needed
            //and added {onDone: flow.clean} to remove the chunks after writing
            //the file.
            flow.write(identifier, stream, { onDone: flow.clean });            
        }            
    })

Мне пришлось изменить обратный вызов flow.post для отправки currentTestChunk и numberOfChunks.

Файл: flow- node.js

$.post = function(req, callback){

//There some codez here that we can overlook...

  fs.rename(files[$.fileParameterName].path, chunkFilename, function(){

    // Do we have all the chunks?
    var currentTestChunk = 1;
    var numberOfChunks = Math.max(Math.floor(totalSize/(chunkSize*1.0)), 1);
    var testChunkExists = function(){
          fs.exists(getChunkFilename(currentTestChunk, identifier), function(exists){
            if(exists){
              currentTestChunk++;
              if(currentTestChunk>numberOfChunks) {

                //Add currentTestChunk and numberOfChunks to the callback

                callback('done', filename, original_filename, identifier, currentTestChunk, numberOfChunks);
              } else {
                // Recursion
                testChunkExists();
              }
            } else {

              //Add currentTestChunk and numberOfChunks to the callback

              callback('partly_done', filename, original_filename, identifier, currentTestChunk, numberOfChunks);
            }
          });
        }
    testChunkExists();
  });
} else {
      callback(validation, filename, original_filename, identifier);
}

}

В flow.write вызовите flow.clean с onDone, если вы хотите удалить куски.

  $.write = function(identifier, writableStream, options) {
      options = options || {};
      options.end = (typeof options['end'] == 'undefined' ? true : options['end']);

      // Iterate over each chunk
      var pipeChunk = function(number) {

          var chunkFilename = getChunkFilename(number, identifier);
          fs.exists(chunkFilename, function(exists) {

              if (exists) {
                  // If the chunk with the current number exists,
                  // then create a ReadStream from the file
                  // and pipe it to the specified writableStream.
                  var sourceStream = fs.createReadStream(chunkFilename);
                  sourceStream.pipe(writableStream, {
                      end: false
                  });
                  sourceStream.on('end', function() {
                      // When the chunk is fully streamed,
                      // jump to the next one
                      pipeChunk(number + 1);
                  });
              } else {
                  // When all the chunks have been piped, end the stream
                  if (options.end) {
                          writableStream.end();
                      }

                  //Options.onDone contains flow.clean so here I'm deleting all the chunked files.

                  if (options.onDone) {
                      options.onDone(identifier);
                  }
              }
          });
      }
      pipeChunk(1);
  }

Ответ 2

Хорошо, поэтому я работал над этим и придумал это, надеюсь, что он запустит кого-то...

exports.post = function (req, res, next) {

    flow.post(req, function(status, filename, original_filename, identifier) {

        console.log('status: '+ status, filename, original_filename, identifier);

        if(status==='done'){

            var s = fs.createWriteStream('./uploads/' + filename);
            s.on('finish', function() {

                res.send(200, {
                    // NOTE: Uncomment this funciton to enable cross-domain request.
                    //'Access-Control-Allow-Origin': '*'
                });

            });

            flow.write(identifier, s, {end: true});
        }

    });

};