使用Multer和Ajax(节点)上传多个图像文件

时间:2018-04-06 11:08:47

标签: jquery node.js ajax file-upload multer

我有以下Ajax上传(来自cropper.js的Base64画布数据),因此Ajax上传不是来自表单。

    $('.gogo').on('touchstart mousedown', function(e){
    e.preventDefault();
    e.stopPropagation();
    var img = new Array();
    img[0] = fetchCrop1();
    img[1] = fetchCrop2();      
    $.ajax({
        cache: false,
        type : 'POST',
        url  : 'http://localhost:3001/img', 
        data: { img : img },
        contentType: false,
        processData: false,
        success : function(data) {
            console.log('AJAX: '+data);
        }
    });
});

和我见过的例子中的Multer脚本

var storage =   multer.diskStorage({
  destination: function (req, file, callback) {
    callback(null, '/img');
},
  filename: function (req, file, callback) {
    callback(null, file.fieldname + '-' + Date.now());
  }
});

app.post('/img',function(req,res){
  var upload = multer({ storage : storage }).array('img',2);
  upload(req,res,function(err) {
    console.log(req.body);
    console.log(req.files);
    if(err) {
        return res.end("Error uploading file.");
    }
    res.end("File is uploaded");
  });
});

我已经阅读了很多帖子,运气不大,因为我一直将req.body和req.files作为{}和未定义。

我尝试了不同的contentType和单上传,但显然我遗漏了一些东西,或者JQuery Ajax不适用于Multer多个文件?

我是Node(LAMP man)的新手,并且确实发现JavaScript语法有点异类。

我只想将两个Base64图像上传到server / img文件夹。

Base64在cropper.js上运行正常。我相信,下面的代码用于该功能

function fetchCrop1(){
/* Note that images greater than 1000px are rejected by the server */
    var $image = $('#image');
    result = $image.cropper("getCroppedCanvas", "{ "width": 1000, 
    "height": 700 }", '');
    $(document).find('#dataImg').val(result.toDataURL('image/jpeg'));
    $('#dataImg').attr('value');
    $('#download').attr('href', result.toDataURL('image/jpeg'));    
    return $('#dataImg').attr('value');     
}    

1 个答案:

答案 0 :(得分:0)

我选择不使用Multer,而是使用body-parser并发送字符串以在服务器端进行转换

app.post('/crop',function(req,res){
 var ts = null;
for(i=1;i<3;i++){
 if(i == 1){
 var x = req.body.img1;
 console.log(parseInt((x).replace(/=/g,"").length * 0.75));
 }else{
 var x = req.body.img2;  
 console.log(parseInt((x).replace(/=/g,"").length * 0.75));
 }
 var decodedImg = decodeBase64Image(x);
 var imageBuffer = decodedImg.data;
 var type = decodedImg.type;
 var extension = mime.extension(type);
 if(i == 1){
    var ts = Date.now();
    var fileName =  "image"+ts+"." + extension;
 }else{
    var fileName =  "image"+ts+"-th." + extension;
 }
 try{
    console.log(fileName,extension,type);
       fs.writeFileSync("img/" + fileName, imageBuffer, 'utf8');
    }
 catch(err){
    console.log(err)
 }
}
}); 

function decodeBase64Image(dataString) {
 var matches = dataString.match(/^data:([A-Za-z-+\/]+);base64,(.+)$/),
 response = {};

 if (matches.length !== 3) {
  return new Error('Invalid input string');
 }

 response.type = matches[1];
 response.data = new Buffer(matches[2], 'base64');

 return response;
}

和客户端

 $('.gogo').on('touchstart mousedown', function(e){
    e.preventDefault();
    e.stopPropagation();
    //var img = new Array();
    img1 = fetchCrop1();
    img2 = fetchCrop2();        
    $.ajax({
        cache: false,
        type : 'POST',
        url  : 'http://localhost:3001/crop', 
        data: { img1 : img1, img2 : img2 },
        contentType: "application/x-www-form-urlencoded",
        success : function(data) {
            console.log('AJAX: '+data);
        }
    });
});

function fetchCrop1(){
/* Note that images greater than 1000px are rejected by the server */
    var $image = $('#image');
    result = $image.cropper("getCroppedCanvas", {width: 1000, height: 800});
    $(document).find('#dataImg1').val(result.toDataURL('image/jpeg'));
    return $('#dataImg1').attr('value');        
}    
function fetchCrop2(){
/* Note that images greater than 1000px are rejected by the server */
    var $image = $('#image');
    result = $image.cropper("getCroppedCanvas", {width: 300, height: 250});
    $(document).find('#dataImg2').val(result.toDataURL('image/jpeg'));
    return $('#dataImg2').attr('value');        
}

我确信有更优雅的方式,但它有效(并且仍然是WIP)(使用cropper.js插件)。