html

<input id="files" type="file" name="file" multiple/> 
<input type="submit" id="shangchuan" value="上传"/>

<ul>
    <li><img src="images/f.jpg" alt=""></li>
</ul>

需要注意的是里面的name属性,需要和js中的代码一一对应

js
$(function () {
    $("#shangchuan").click(function () {
        var file = document.getElementById("files").files[0];

        var formdata=new FormData();
        formdata.append("file",file);

        $.ajax({
            type: 'POST',
            url: '/upload',
            processData:false,//对data参数进行序列化处理
            contentType:false,//内容编码类型
            cache:false,//不使用缓存
            data: formdata,
            success: function(data) {
                var $li = $("<li><img src=\"images/"+ file.name +"\" alt=\"\"></li>");
                $("ul").append($li);
            }
        });
    });
});

formdata.append("file",file);最终的提交还是以from表单的形式,在给表单中添加需要上传的文件时,类似键值对。这里的键名对应的时name属性而不是id

其中的:processData,contentType:false,cache的添加是必须的,对于上传文件来说

应为Ajax请求时异步得,所以将添加放置在success的回调函数中,创建的节点很容易出错,需要十分注意转义符号的使用,做好打印看看

nodejs
app.post('/upload', multer({dest: './public/upload_tmp/'}).array('file', 10), function (req, res, next) {  //这里10表示最大支持的文件上传数目
    let files = req.files;
    console.log(files);
    if (files.length === 0) {
        res.render("error", {message: "上传文件不能为空!"});
        return
    } else {
        let fileInfos = [];
        for (var i in files) {
            let file = files[i];
            let fileInfo = {};

            fs.renameSync('./public/upload_tmp/' + file.filename, './public/images/' + file.originalname);//这里修改文件名字,比较随意。

            //获取文件基本信息
            fileInfo.mimetype = file.mimetype;
            fileInfo.originalname = file.originalname;
            fileInfo.size = file.size;
            fileInfo.path = file.path;

            fileInfos.push(fileInfo);
        }
        // 设置响应类型及编码
        res.set({
            'content-type': 'application/json; charset=utf-8'
        });
        res.json({"result":{message:"success"}});
        res.end("success!");
    }
});

.array('file', 10)中的file对应,表单对象中存储文件的键名

res.json({"result":{message:"success"}});这里的这个似乎没有用,但是经过测试,没有这个的时候不能返回success状态

如果要返回,那么设置相应类型及编码最好写上,自测出现了BUG,添加之后通过。