checking if busboy finish event has already occured or not

拈花ヽ惹草 提交于 2020-01-06 16:29:42

问题


I have a form in which I am expected to do some file processing which takes some time, so I want that finish event executes only after the processing is complete, right now node is processing the file and while it is processing the file and executes commands node if finds finish event it fires it. so, how do i make sure that the finish event is fired only after processing of all files.

busboy.on('file', function(fieldname, file, filename,transferEncoding,mimeType) {
        var fName = uuid.v4();
        var fileext = filename.substr(filename.lastIndexOf('.') + 1);
        var filepath = path.normalize(__dirname + '/../../');
        var fstream = fs.createWriteStream(filepath+'/server/uploads/'+fName+'.'+fileext);
        var uploadFileCompletion = file.pipe(fstream);
        uploadFileCompletion.on('finish',function(){
            console.log('uploaded now');
            var cmd = 'libreoffice --headless --convert-to pdf --outdir '+ filepath + 'server/uploads ' + filepath + 'server/uploads/' + fName + '.' + fileext;
            exec(cmd, function(error,stdout,stderr){
                sys.puts(stdout);
                var encryptCmd = 'java -jar server/uploads/pdfbox-app-1.8.6.jar Encrypt -canAssemble false -canExtractContent false -canExtractForAccessibility false ' +
                    '-canModify false -canModifyAnnotations false -canPrint false -canPrintDegraded false server/uploads/' + fName + '.' + 'pdf'
                    + ' ' + 'server/uploads/' +fName + '.' + 'pdf';
                exec(encryptCmd, function(error,stdout,stderr){
                    fs.unlink(filepath+'server/uploads/'+fName + '.' + fileext, function(){
                        console.log("removed " +filepath+'server/uploads/'+fName + '.' + fileext);
                        actualFileName.push(filename);
                        storedFileName.push(fName+'.'+'pdf');
                    });
                });

            });
        });
    });
    busboy.on('field', function(fieldname, val, valTruncated,keyTruncated) {
        noteData = JSON.parse(val);
    });
    busboy.on('finish',function(){
        noteData.uploader = req.user.username;
        noteData.actualFileName = actualFileName;
        noteData.storedFileName = storedFileName;
        noteData.noteId = uuid.v4();
        Campusnotes.create(noteData,function(err,note){
            if(err){
                res.status(400);
                return res.send({reason:err.toString()});
            }
            console.log('finish');
            res.status(200);
            res.end();
        })
    });

now the console log for this is as follows -

finish
uploaded now
convert /home/unknown/public_html/campustop/server/uploads/8465f9a9-d6b7-4d53-8cb5-a8dbf3aed6a5.odt -> /home/unknown/public_html/campustop/server/uploads/8465f9a9-d6b7-4d53-8cb5-a8dbf3aed6a5.pdf using writer_pdf_Export

removed /home/unknown/public_html/campustop/server/uploads/8465f9a9-d6b7-4d53-8cb5-a8dbf3aed6a5.odt

indicating that the finish event is getting fired again and again


回答1:


You could try something like:

var files = 0;
busboy.on('file', function(fieldname, file, filename,transferEncoding,mimeType) {
  ++files;
  var fName = uuid.v4();
  var fileext = filename.substr(filename.lastIndexOf('.') + 1);
  var filepath = path.normalize(__dirname + '/../../');
  var fstream = fs.createWriteStream(filepath+'/server/uploads/'+fName+'.'+fileext);
  file.pipe(fstream).on('finish',function() {
    console.log('uploaded now');
    var cmd = 'libreoffice --headless --convert-to pdf --outdir '+ filepath + 'server/uploads ' + filepath + 'server/uploads/' + fName + '.' + fileext;
    exec(cmd, function(error,stdout,stderr) {
      console.log(stdout);
      var encryptCmd = 'java -jar server/uploads/pdfbox-app-1.8.6.jar Encrypt -canAssemble false -canExtractContent false -canExtractForAccessibility false ' +
          '-canModify false -canModifyAnnotations false -canPrint false -canPrintDegraded false server/uploads/' + fName + '.' + 'pdf'
          + ' ' + 'server/uploads/' +fName + '.' + 'pdf';
      exec(encryptCmd, function(error,stdout,stderr) {
        fs.unlink(filepath+'server/uploads/'+fName + '.' + fileext, function() {
          console.log("removed " +filepath+'server/uploads/'+fName + '.' + fileext);
          actualFileName.push(filename);
          storedFileName.push(fName+'.'+'pdf');
        });
      });
      --files;
      onFinish();
    });
  });
});
busboy.on('field', function(fieldname, val, valTruncated,keyTruncated) {
  noteData = JSON.parse(val);
});
busboy.on('finish', onFinish);

function onFinish() {
  if (!busboy.writable && files === 0) {
    noteData.uploader = req.user.username;
    noteData.actualFileName = actualFileName;
    noteData.storedFileName = storedFileName;
    noteData.noteId = uuid.v4();
    Campusnotes.create(noteData,function(err,note){
      if (err){
        res.status(400);
        return res.send({reason:err.toString()});
      }
      console.log('finish');
      res.status(200);
      res.end();
    });
  }
}

On an unrelated note, you should probably do some sanitizing/checking of the filename, someone could be malicious and use something like '../../../../../../../../../etc/passwd' (I'm not sure if createWriteStream() resolves/normalizes the path given to it or not).



来源:https://stackoverflow.com/questions/24632474/checking-if-busboy-finish-event-has-already-occured-or-not

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!