I am trying to test REST API, and I can't figure out how to send a file from client side to express server side.
This is my pug file, with which i simulate client side for specific purposes, in this case just send the picture.
doctype html
html
head
title Test
body
form(action=`${baseRoute}/api/users/${nick}/generate` enctype="multipart/form-data" method='POST')
input(type='file' accept="image/png, image/jpeg" id='profile_picture' name='image')
input(type='submit', value='Load')
baseRoute is created for pug, so it does not add action link to existing link, and changes the whole link.
From what I saw, to get files from form, I have to access req.files in express back end part. Yet, it shows me absolutely nothing
const express = require('express');
const app = express();
const multer = require('multer');
const upload = multer({ dest: 'uploads/' });
app.set('views', 'views');
app.set('view engine', 'pug');
app.get('/', function(req, res, next) {
res.redirect('/test/update_user');
});
app.post('/api/users/:nick/generate', upload.single('image'), async function(req, res, next) {
console.log("GENERATE USER");
console.log(req.files);
res.send("Success");
});
app.get('/test/update_user', function(req, res, next) {
let params = {
baseRoute: "",
nick: 'somenick',
};
res.render('test/update_user', params);
});
app.listen(3000, () => {
console.log("go to localhost:3000/test/update_user");
});
I tried reading all of req, but there was no sight of files property. Using multer it adds a file to upload directory, but in a weird way without any extension and some weird name. And still it logs 'undefined' when I am trying to access req.files
Related
I'm make api to upload files using node js.
i using multer for handle multipart/form-data
but when i console.log(req.file) it appears undefined
Route
const uploadController = require('../controller/upload.server.controller');
const multer = require('multer');
const upload = multer({ dest: 'uploads/' });
/**
* Routes
*/
module.exports = function (app) {
app
.route('/api/upload')
.post(upload.single('image'), uploadController.upload);
};
Controller
exports.upload = async function (req, res) {
console.log(req.file);
};
my request with postman
Try using req.file as per the docs source: multer
// init
const multer = require('multer');
const path = require('path');
// "images" are the folder name
const fileStorage = multer.diskStorage({
destination: (req, file, cb) => {
cb(null, 'images');
},
});
// put this to config the multer
app.use(multer({ storage: fileStorage }).single('image'));
// this is for serving file staticly with "path" module
app.use('/images', express.static(path.join(__dirname, 'images')));
Also make sure you write enctype=multipart/form-data in the form tag not in the input tag AND
add type=file attribute in the input tag
Try this:
app.post('/api/upload', upload.single('image'), function (req, res, next) {
console.log(req.file);
})
I have also encountered similar problem. Everytime I restart my server postman provided req.file gives undefined. I thought maybe I habe made a bug but I couldn't figure out what was wrong.
Then I tried creating a new request in postman and when I requested req.file works perfectly. I am trying to figure out what is wrong with Postman or am I making a mistake while sending a request.
I am trying to create an SPA using Express with following code
var express = require('express');
const path = require('path');
var app = express();
app.use('/assets', express.static(path.resolve(__dirname, 'www', 'assets')));
app.get('/*', (req, res)=>{
res.sendFile(path.resolve('www', 'index.html'));
});
var server = app.listen(3000, function(){});
This code works good but the problem is this responds with my index.html even when a file is not found in my assets folder. I want it to respond with error of 404 Not Found if some url is not present in assets folder
I tried using this code after line app.use('/assets'...
app.use(function (req, res, next) {
res.status(404).send("404 Not Found");
});
but not working
Issue is with
app.get('/*', (req, res)=>{
res.sendFile(path.resolve('www', 'index.html'));
});
Instead, use
app.get('/', (req, res)=>{
res.sendFile(path.resolve('www', 'index.html'));
});
So, I finally got the way to solve it
app.get('/*', (req, res)=>{
if(req.path.includes('/assets'))
{
fs.access(req.path, (err) => {
if(err)
{
res.status(404).send("Sorry can't find that!");
return;
}
});
}
res.sendFile(path.resolve('www', 'index.html'));
});
In the code, I have told to check if the request is about a file located in assets folder then check if the file exists, if does not exists then send 404 error with message and just return, otherwise do nothing but return the file.
I'm trying to set up a simple routing app but I keep running int the error when rendering a page.
Error: Module "html" does not provide a view engine.
What is odd is I've specified the view engine in my app.js file but I'm still getting the error
// app.js
var express = require('express');
var app = express();
var router = express.Router();
// Need to import the route file
var chef = require('./chef');
app.use('/chef', chef);
// Set directory to contain the templates ('views')
app.set('views', __dirname + '/views');
// Set view engine to use
app.set('view engine', 'html');
app.use(function(err, req, res, next) {
console.error(err.stack);
res.status(500).send('Something broke!');
});
// chef.js
var express = require('express');
var routes = express.Router();
routes.get('/', (req, res) => {
//res.send("I'm here!")
res.render('chef');
});
module.exports = routes;
// views/chef.html
Some HTML file here here ..
In the chef.js file when I just want to test if the route is working I uncomment res.send ... which sends "I'm here" to the DOM.
However whenever I try res.render to render the chef.html page I get the error above. Which I find odd because I've set the view engine in app.js.
Suggestions on how to render my HTML file?
use res.sendFile('/fileName.html'); instead of res.render()
for sending file , we used res.sendFile(fullPath) and if you are using other than HTML language then you should have to use res.render().
res.render() for template like ejs, pug etc.
I am trying to set up a react app with express running. However, I can't understand why it won't load the page I want it to
this is my app.js:
var express = require('express');
var app = express();
app.use('/', express.static('public'));
app.get('/', function(req, res) {
res.sendfile('./index.html');
});
app.get('/canYouPlay.js', function(req, res) {
res.sendfile('/canYouPlay.html');
});
app.listen(process.env.PORT || 8080);
This works. however if I change the first app.get to:
app.get('/', function(req, res) {
res.sendfile('./canYouPLay.html');
});
It still renders the same HTML file even when restarting the app even though they are different files.
also when i run this function:
handleClick: function() {
document.location.replace('./canYouPlay');
},
it says it cannot get /canYouPLay even though a HTML and js file exist with that name.
what have I missed or doing wrong?
I want to protect a folder and its content by redirecting the user back to index.
I've tried this, but it only works partially.
var express = require('express');
var path = require('path');
var http = require('http');
var app = express();
app.set('port', 8080);
app.set('view engine', 'ejs');
app.use(express.static(path.join(__dirname, 'views')));
app.get('/', function(req, res) {
res.render('index.ejs');
});
app.get('/protected/*', function(req, res, next) {
res.redirect('/');
next();
});
//activating server
http.createServer(app).listen(app.get('port'), function(){
console.log('Express server listening on port ' + app.get('port'));
});
This routes, for example, "localhost:8080/protected" and "localhost:8080/protected/asdf", but not "localhost:8080/protected/otherPage.html".
In this case asdf is not an actual file, but otherPage.html is. So if the file is there it doesn't redirect, but if it is not then it redirects. Why is this?
Your line dealing with static files app.use(express.static(path.join(__dirname, 'views'))); appears before app.get('/protected') so its being matched first.
If you moved the static handler to later in the code this would work as you require.
However, I would recommend splitting the static items into a separate folder to guard against accidentally revealing any server-side code you might be including in ejs files in the views folder.