I want to upload a file to a NodeJS server. Following File uploading with Express 4.0: req.files undefined , I try this code in mre.js
:
'use strict';
const path = require('path');
const express = require('express');
const app = express();
// Set up the view engine
app.set('view engine', 'pug');
app.set('views', path.join(__dirname, 'views'));
const UPLOAD = "/upload";
app.get(UPLOAD, async (req, res) => {
return res.render("upload");
});
const fileUpload = require('express-fileupload');
app.post(UPLOAD, fileUpload(), async (req, res) => {
let keys = Object.keys(req.files);
fs.readFile(req.files[keys[0]].path, (err, e) => {
if(err) console.log(err);
fs.writeFile(keys[0], e, (err) => {
console.log(err)
})
})
req.flash("success", "File uploaded");
return res.redirect(UPLOAD);
});
const http = require('http');
const httpServer = http.createServer(app);
let server = httpServer.listen(8080, () => {
console.log("\n# HTTP server started");
});
and the view is:
doctype html
html
body
form(method='POST')
input(type='file', id="file", name="filename", accept=".xls,.xlsx,.txt")
input(type="submit", name="submit", value="Upload")
I launch with node mre.js
, I see the form at http://localhost:8080/upload
, but when I upload a file, I get this error:
mre.js:24
let keys = Object.keys(req.files);
TypeError: Cannot convert undefined or null to object
I tried several variations to no avail, for example I log the full request with console.log(req)
, and the filename I uploaded does not appear. But it seems to work on multiple answers of that thread, so I think there's something obvious I am overlooking. The NodeJS version is 22.2.0.
How can I get the file uploaded to a NodeJS server?
The problem is with the request: your form is sending URL-encoded request, so the file content is not included, so the req.files
is undefined, breaking your code.
You need to send multipart request. So, add enctype="multipart/form-data"
attribute to the form:
form(method='POST', enctype="multipart/form-data")