Parse form value with formidable to filename

Wandkleister picture Wandkleister · May 8, 2015 · Viewed 30.3k times · Source

I´m using formidable to handle my file uploads in NodeJs. I´m a little stuck at parsing field values.

How do I get the value of project_id to the form handler, so I can write the parameter in my filename?

<input type="text" id="project_id" value="{{projects._id}}" readonly>

EDIT

To be more specific, here´s a detailed view of my form-upload handling:

app.post('/uploads/', function (req, res){
    var form = new formidable.IncomingForm();
    form.parse(req, function (err, fields, files) {
        res.writeHead(200, {'content-type': 'image/jpeg'});
        res.write('received upload: \n\n');
        var project = fields.project_id;
        res.end(util.inspect(project, {fields: fields, files: files}));
    });

    form.on('end', function(project, fields, files){ 
        console.log(project); 
        /*Temporary location of our uploaded file */
        var temp_path = this.openedFiles[0].path;
        /*The file name of the uploaded file */
        var file_name =  project + '.' + this.openedFiles[0].name;

I can log the var project in the form.parse part. But I don´t get the variable in the form.on('end'... part.

HTML form

<form   id="uploadForm"
    enctype="multipart/form-data"
    action="/uploads/"
    method="post">
    <input type="text" name="project_id" id="project_id" value="{{projects._id}}" readonly>
    <input multiple="multiple" type="file" name="upload" />
    <button type="submit">Upload</button>
</form>

Answer

Andrew Lavers picture Andrew Lavers · May 8, 2015

Formidable's end callback doesn't take any parameters, but I'm not sure you even need to call it if you're using the parse callback. I think what you're looking for is something like this:

var fs = require('fs');
app.post('/uploads', function(req, res, next) {
    var form = new formidable.IncomingForm();
    form.parse(req, function(err, fields, files) {
        if (err) next(err);

        // TODO: make sure my_file and project_id exist    
        fs.rename(files.my_file.path, fields.project_id, function(err) {
            if (err) next(err);
            res.end();
        });
    });
});

You would need to listen for the end() event if you chose not to use the parse callback, like this:

new formidable.IncomingForm().parse(req)
    .on('file', function(name, file) {
        console.log('Got file:', name);
    })
    .on('field', function(name, field) {
        console.log('Got a field:', name);
    })
    .on('error', function(err) {
        next(err);
    })
    .on('end', function() {
        res.end();
    });