node.jsexpressmultipartform-dataform-databody-parser

Express req.body is empty


I've tried many StackOverflow answers, and this method normally works using body-parser, however I've been having issues with getting any output from req.body with either AJAX or form data.

In server.js:

app.use(helmet()); // Helmet middleware
app.use('/assets', express.static('resources/web/assets')); // Makes /assets public
app.use(require('./resources/modules/session.js')); // Custom session middleware
app.set('view engine', 'ejs'); // Sets EJS to the view engine
app.set('views', `${__dirname}/resources/web/pages`); // Sets the views folder
app.use(cookieParser()); // cookie-parser middleware
app.use(bodyParser.urlencoded({ extended: true })); // body-parser's middleware to handle encoded data
app.use(bodyParser.json()); // body-parser's middleware to handle JSON
app.use(fileUpload({ limits: { fileSize: 100 * 1024 * 1024 } })); // express-fileupload middleware (bushboy wrapper)
app.use('/api', require('./resources/routes/api.js')); // External API router
// ...
app.post('/login', (req, res) => {
    console.log(req.body);
    res.render('login', {
        config,
        page: {
            name: 'Login'
        },
        error: ''
    });
    res.end();
});

My login.ejs code:

            <form method="POST">
                <div class="input-group">
                    <i class="las la-user"></i>
                    <input placeholder="Username" name="username" type="text" required>
                </div>
                <div class="input-group">
                    <i class="las la-lock"></i>
                    <input placeholder="Password" name="password" type="password" required>
                </div>
                <button type="submit">
                    <i class="las la-paper-plane"></i> Login
                </button>
            </form>

No matter what I try, I always get an empty {} in the console with no avail. I've tried debugging; I need a fresh pair of eyes to see what I've done wrong. Here's the form data: Form Data And I've tried using jQuery's AJAX ($.get) too:

$.post('', {username:'test', password:'test'})
.fail(console.error)
.done(() => console.log('Success'));

enter image description here

Edit: After trying multer's app.use(require('multer')().array()); and app.use(require('multer')().none()); middleware, I'm still at the same old issue, except with multer req.body is now undefined instead of {}. This is due to the data being sent as application/x-www-form-urlencoded instead of what I previously thought was application/form-data. As that is the case, the body-parser middleware method should work. If contributing, please do not contribute an answer relating to parsing application/form-data!

Edit 2: For those asking for the session.js code, here it is:

const enmap = require('enmap'),
      sessions = new enmap('sessions');

module.exports = (req, res, next) => {
    if (!req.cookies) next();
    const { cookies: { session: sessionID } } = req;
    if (sessionID) {
        const session = sessions.get(sessionID);
        if (session) {
            req.session = session;
        } else {
            req.session = undefined;
        };
    } else {
        req.session = undefined;
    };
    next();
};

Solution

  • For the specific case you're talking about, you usually need only 'body-parser' module to be able to access the form input fields. The minimum example that I advice you to build above it is the following:

    var express = require('express');
    var bodyParser = require('body-parser');
    
    var app = express();
    app.use(bodyParser.urlencoded({extended : true}));
    app.use(bodyParser.json());
    app.get('/login', (req, res) => { /* ... */ });
    app.post('/login', (req, res) => {
        console.log(req.body);
        // ...
    });
      
    app.listen(3000);
    

    So my advice is to narrow on the cause of the problem by removing any other middleware except for the bodyParser. Try to comment them one-by-one and then you will be able to find the guilty!

    Also note that no need to bother yourself trying to make it work with Ajax as it will make no difference. Keep it simple and just try the normal browser submission.

    When you found the problematic middleware, debug it. If it's made by you, make sure that you don't make any changes to the req.body. If it a thirdparty middleware, so please consult their installation steps very carefully and I'm happy for further explanation and support

    Edit: Some other hints