Error in NodeJS next is not a function when using middleware - node.js

I am following this video to create a simple server in NodeJS (v16.19.0) and ExpressJS (v4.18.2).
app.js
const express = require("express");
const app = express();
// Middleware
const middleware = (req, res, next) => {
console.log(`Hello my middleware`);
next(); //error on this line: next is not a function
}
middleware();
app.get("/", (req, res) => {
res.send(`Hello world from server`);
});
app.listen(3000, () => {
console.log("server runnin at port 3000");
});
error: next is not a function, when I run app.js. How do I solve this

The error you're encountering is because the middleware function you've defined is being invoked as a regular function, rather than being used as middleware in an Express route. The next function is provided by Express and allows you to pass control to the next middleware function or route handler in the chain.
To use the middleware function, you need to attach it to an Express route as follows:
const express = require("express");
const app = express();
// Middleware
const middleware = (req, res, next) => {
console.log(`Hello my middleware`);
next();
};
app.use(middleware);
app.get("/", (req, res) => {
res.send(`Hello world from server`);
});
app.listen(3000, () => {
console.log("server runnin at port 3000");
});

Related

Why we should write app.get("/", function (req, res){}) before app.listen(3000)?

I tried to listen to the port and then giving back the response to the browser and that too worked.
Then why we listen afterwards?
eg:
const express = require("express");
const app = express();
app.get("/", function (req, res) {
res.send("Hello");
});
app.listen(3000);

What am I doing incorrectly with my https request?

I'm learning how to build a RESTful api with Node and Express, and I am having an issue with this https request. I am trying to make a GET request to Scryfall's api (documentation here: https://scryfall.com/docs/api), but whenever I run my server and check the browser I get a message stating
"localhost didn’t send any data. ERR_EMPTY_RESPONSE".
As I'm new to using Node and Express, I'm not really sure what I am doing wrong. Here is the code for my server.js and app.js files.
//server.js
const https = require('https');
const app = require('./backend/app');
const port = process.env.PORT || '3000';
app.set('port', port);
const server = https.createServer(app); //pass the express app to the server
server.listen(port);
and
//app.js
const express = require('express');
const app = express();
app.use((req, res, next) => {
console.log('This is the first middleware');
next();
});
app.get('https://api.scryfall.com/cards/named?fuzzy=aust+com', (req, res, next) => {
res.send('${res.body.name} is the name of the card!');
});
module.exports = app;
Any help would be greatly appreciated! Thanks in advance!
👨‍🏫 For an example, you can do it with this code below 👇:
const express = require('express');
const axios = require('axios');
const app = express();
app.use(express.json());
app.use(express.urlencoded({ extended: true }));
app.use((req, res, next) => {
console.log('This is the first middleware');
next();
});
app.get('/', async (req, res, next) => {
try {
const result = await axios.get('https://api.scryfall.com/cards/named?fuzzy=aust+com');
res.status(200).send(result.data);
}catch(ex) {
console.log(ex.message);
}
});
app.listen(3000, () => {
console.log('Server is up');
})
💡 From the code above, you can call the endpoint: localhost:3000 and than you will get the result.
I hope it's can help you 🙏.
You can easily make a get request like this.
const express = require('express');
const app = express();
const port = 8080;
const bodyParser = require('body-parser');
//Expect a JSON body
app.use(bodyParser.json({
limit: '50mb' //Request size - 50MB
}));
app.get('/test', (req, res, next) => {
// do whatever you need here
res.status(200).send("ok");
});
app.listen(port, function () {
console.log(`Server is running.Point your browser to: http://localhost:${port}`)
});

GET localhost:4200/api 404 (Not Found) after submit data

I download the https://github.com/SinghDigamber/Angular8MeanstackAngularMaterial
and deployed it.
But while I tried to save the data and review the data, i always get the
GET http://localhost:4200/api 404 (Not Found)
add data to db error picture
get data to db error picture
Angular v8.0.0
mongoDB v4.0.10
nodejs v12.2.0
//app.js
let express = require('express'),
path = require('path'),
mongoose = require('mongoose'),
cors = require('cors'),
bodyParser = require('body-parser'),
dataBaseConfig = require('./database/db');
// Connecting mongoDB
mongoose.Promise = global.Promise;
mongoose.connect(dataBaseConfig.db, {
useNewUrlParser: true
}).then(() => {
console.log('Database connected sucessfully ')
},
error => {
console.log('Could not connected to database : ' + error)
}
)
// Set up express js port
const studentRoute = require('./routes/student.route')
const app = express();
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({
extended: false
}));
app.use(cors());
// Setting up static directory
app.use(express.static(path.join(__dirname, 'dist/angular8-meanstack-angular-material')));
// RESTful API root
app.use('/api', studentRoute)
// PORT
const port = process.env.PORT || 8000;
app.listen(port, () => {
console.log('Connected to port ' + port)
})
// Find 404 and hand over to error handler
app.use((req, res, next) => {
next(createError(404));
});
// Index Route
app.get('/', (req, res) => {
res.send('invaild endpoint');
});
app.get('*', (req, res) => {
res.sendFile(path.join(__dirname, 'dist/angular8-meanstack-angular-material/index.html'));
});
// error handler
app.use(function (err, req, res, next) {
console.error(err.message);
if (!err.statusCode) err.statusCode = 500;
res.status(err.statusCode).send(err.message);
});
I think you forgot to export get and post functions for your API routes.
you can create routes like this in studentRoute File.
var express = require('express');
var router = express.Router();
router.get('/', function (req, res, next) {
return "Hello World";
})
router.post('/', function (req, res, next) {
return "Hello World";
})
module.exports = router;````

Why function declaration doesn't work in app.use?

When I use foo function declaration in app.use as a middleware the compiler doesn't seem to recognize the req, res, next variables:
var express = require('express');
var path = require('path');
var app = express();
function foo (req, res, next){ // the middleware
console.log(req.path);
}
app.use('/', foo(req, res, next)); //ReferenceError: req is not defined
app.use('/', express.static("./public"));
app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});
By comparison if I use function declaration inside app.use the code works as intended:
var express = require('express');
var path = require('path');
var app = express();
app.use('/', function(req, res, next){
console.log(req.path);
}); //ReferenceError: req is not defined
app.use('/', express.static("./public"));
app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});
My understanding is not enough to see why this is an error
In your example, app.use('/', foo(req, res, next)); is calling the function and executing it as it parses through the JS file.
The other 'comparison', is a function declaration which isn't called while parsing through the file.
You can change the code to: app.use('/', foo); and it'll work properly.

express - getting path of parrent router?

Lets say I want to have 2 different instances in "subfolders" in the url. In app js I have it defined like this:
var routes = require('./routes/index');
app.use('/myapp1', routes);
app.use('/myapp2', routes);
The inner routing would be the same.
But still in the router I want to "get" the path defined in the app.use - eg.: myapp1, myapp2
How do I get this in the router?
From routes/index.js:
router.use(/\/.*/, function (req, res, next) {
// want to see "myapp1/myapp2" without the *sub* path defined in this particular router eg.: /products /user etc.
next();
});
You might want to use the req.baseUrl property.
Example:
routes.get('/1', function(req, res) {
res.send([
req.baseUrl,
req.path,
req.baseUrl + req.path,
].join('\n'));
});
app.use('/api', routes);
Making an HTTP request to /api/1 would print:
/api
/1
/api/1
var express = require('express');
var app = express();
var router = express.Router();
app.use(function(req, res, next) {
req.appInstance = (req.url.indexOf('/app2/') == 0) ? 2 : 1;
next();
});
app.get('/', function(req, res, next) {
res.redirect('/app1/user');
});
router.get('/user', function(req, res, next) {
res.send(req.url +' on app' + req.appInstance);
});
app.use('/app1', router);
app.use('/app2', router);
app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});

Resources