Errors with socket.io? - javascript

I recently implemented socket.io and running into some strange errors.
The error messages I am getting aren't incredibly helpful and trying to figure out what is causing this.
Here are the contents of my app.js -
app.js
// Express Requirements
var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
var multer = require('multer');
// Formidable Requirements
var formidable = require('formidable');
var util = require('util');
var routes = require('./routes/index');
var app = require('express')();
var server = require('http').Server(app);
var io = require('socket.io')(server);
server.listen(8888);
// view engine setup
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'hjs');
// Non Default Code
// Socket.io Code
io.on('connection', function (client) {
console.log("Client connected!");
client.emit('newcommer',{status: true, newuser: 'paul'});
});
// End Socket.io Code
// End Non Default Code
// uncomment after placing your favicon in /public
//app.use(favicon(__dirname + '/public/favicon.ico'));
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use('/', routes);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
var err = new Error('Not Found');
err.status = 404;
next(err);
});
// error handlers
// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
app.use(function(err, req, res, next) {
res.status(err.status || 500);
res.render('error', {
message: err.message,
error: err
});
});
}
// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
res.status(err.status || 500);
res.render('error', {
message: err.message,
error: {}
});
});
module.exports = app;
Error Message
events.js:72
throw er; // Unhandled 'error' event
^
Error: listen EADDRINUSE
at errnoException (net.js:904:11)
at Server._listen2 (net.js:1042:14)
at listen (net.js:1064:10)
at Server.listen (net.js:1138:5)
at Object.<anonymous> (/Users/blah/blah/app.js:20:8)
at Module._compile (module.js:456:26)
at Object.Module._extensions..js (module.js:474:10)
at Module.load (module.js:356:32)
at Function.Module._load (module.js:312:12)
at Module.require (module.js:364:17)
28 Nov 19:10:39 - [nodemon] app crashed - waiting for file changes before starting...
Does anyone see anything that is off that could be causing this error?
Edits For Culprits:
Once these lines are removed then the code does not produce any errors:
var server = require('http').Server(app);
var io = require('socket.io')(server);
// Socket.io Code
io.on('connection', function (client) {
console.log("Client connected!");
client.emit('newcommer',{status: true, newuser: 'paul'});
});
// End Socket.io Code

Are you sure, you are getting this error ???
I think you have another server running on the same port server.listen(8888);
Either close that running server or changer the port as server.listen(8000);

Related

Route.post() requires a callback function but got a [object String]

I'm trying to make my vocabulary app using and changing MDN node/express tutorial.
MDN tutorial works perfectly but mines doesn't work.
Here are the errors :
Error: Route.post() requires a callback function but got a [object String]
at Route.(anonymous function) [as post] (d:\web-projects\vocastudy\node_modules\express\lib\router\route.js:202:15)
at Function.proto.(anonymous function) [as post] (d:\web-projects\vocastudy\node_modules\express\lib\router\index.js:510:19)
at Object.<anonymous> (d:\web-projects\vocastudy\routes\catalog.js:9:8)
at Module._compile (module.js:652:30)
at Object.Module._extensions..js (module.js:663:10)
at Module.load (module.js:565:32)
at tryModuleLoad (module.js:505:12)
at Function.Module._load (module.js:497:3)
at Module.require (module.js:596:17)
at require (internal/module.js:11:18)
at Object.<anonymous> (d:\web-projects\vocastudy\app.js:9:21)
at Module._compile (module.js:652:30)
at Object.Module._extensions..js (module.js:663:10)
at Module.load (module.js:565:32)
at tryModuleLoad (module.js:505:12)
at Function.Module._load (module.js:497:3)
And app.js :
var createError = require('http-errors');
var express = require('express');
var path = require('path');
var cookieParser = require('cookie-parser');
var logger = require('morgan');
var indexRouter = require('./routes/index');
var usersRouter = require('./routes/users');
var catalogRouter = require('./routes/catalog');
var app = express();
// Set up mongoose connection
var mongoose = require('mongoose');
var mongoDB = 'mongodb://127.0.0.1/vocastudy';
mongoose.connect(mongoDB);
mongoose.Promise = global.Promise;
var db = mongoose.connection;
db.on('error', console.error.bind(console, 'MongoDB connection error'));
// view engine setup
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'pug');
app.use(logger('dev'));
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use('/', indexRouter);
app.use('/users', usersRouter);
app.use('/catalog', catalogRouter);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
next(createError(404));
});
// error handler
app.use(function(err, req, res, next) {
// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
// render the error page
res.status(err.status || 500);
res.render('error');
});
module.exports = app;
And my routes catalog.js :
var express = require('express');
var router = express.Router();
var vocabulary_controller = require('../controllers/vocabularyController');
// GET request for creating a Word. NOTE This must come before routes tha display Word (uses id).
router.get('/create', vocabulary_controller.create_get);
/* POST create page */
router.post('/create', vocabulary_controller.create_post);
/* GET home page. */
router.get('/', vocabulary_controller.list);
/* GET detail page */
router.get('/:id', vocabulary_controller.detail);
module.exports = router;
And controllers vocabulary.js :
exports.create_post = [
// Validate fields
body('word').isLength({ min: 1 }).trim().withMessage('word must be specified'),
body('meaning').isLength({ min: 1 }).trim().withMessage('meaning must be specified'),
body('reference').isLength({ min: 1 }).trim().withMessage('reference must be specified'),
// Sanitize (trim and escape) the fields
sanitizeBody('word').trim().escape(),
sanitizeBody('meaning').trim().escape(),
sanitizeBody('reference').trim(),escape(),
// Process request after validation and sanitization
(req, res, next) => {
// Extract the validation errors from a request.
const errors = validationResult(req);
// Create vocabulary object with escaped and trimmed data.
if(!errors.isEmpty()) {
// There are errors.
res.render('create', { title: 'Create Word', word: req.body, errors: errors.array() });
return;
} else {
// Data from form is valid.
// Create a Vocabulary object with escaped and trimmed data.
var vocabulary = new Vocabulary({
word: req.body.word,
meaning: req.body.meaning,
reference: req.body.reference
});
vocabulary.save(function(err) {
if(err) { return next(err); };
// Successful - redirect to new word record.
res.redirect(vocabulary.url);
});
};
}
];
I think that create post controller is array so I got error but it perfectly works on MDN's tutorial version. I can't find my problem.
why did i get route.post error?
NB that mdn's tutorial is using array too.
It seems that in Express, app.post() accepts parameters that can be arrays of callbacks, but router.post() only accepts functions as callbacks. Try providing the array directly to an express app instead of the router, or as #TimothyLee suggested, use the spread syntax to turn the array into individual parameters to the router.post() function.

Express Route 404

I'm having trouble with my node.js express routes. I'm really new to it and I can't see my mistake. I'm always getting a 404 Error when requesting localhost:2700/api/subs, but I think that my route is correct, isn't it? Can anybody see a mistake?
Beginning of the Error Message:
Error: Not Found
at ****/app.js:45:13
at Layer.handle [as handle_request] (****/node_modules/express/lib/router/layer.js:95:5)
Here is the app.js
var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
const mongoose = require('mongoose');
// establish connection to the Database
mongoose.connect('mongodb://localhost/test', {
useMongoClient: true
});
mongoose.connection.once('open', function() {
console.log('Connection to Database has been established..');
}).on('error', function(error){
console.log(error);
});
var index = require('./routes/index');
var users = require('./routes/users');
Subscriber = require('./routes/subscriber.js');
var app = express();
// view engine setup
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'jade');
// uncomment after placing your favicon in /public
//app.use(favicon(path.join(__dirname, 'public', 'favicon.ico')));
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use('/', index);
app.use('/users', users);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
var err = new Error('Not Found');
err.status = 404;
next(err);
});
// error handler
app.use(function(err, req, res, next) {
// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
// render the error page
res.status(err.status || 500);
res.render('error');
});
app.get('/api/subs', function(req, res){
Subscriber.getSubscribers(function(err, subscribers){
if(err){
throw err;
}
res.json(subscribers);
});
});
// ... here is a function which creates the database objects and saves
// them. took it out for better overview....
app.listen(2700, function(){
console.log("Listening on Port 2700")
});
module.exports = app;
and the subscriber.js which is in the subdirectory ./routes:
const mongoose = require('mongoose');
var subscriberSchema = mongoose.Schema({
//seqnr shall go here. dunno how to declare integer x)
nr: Number,
name: String,
email: String,
uLink: String,
anwalt: String
});
var Subscriber = module.exports = mongoose.model('Subscriber', subscriberSchema);
//get Subscriber
module.exports.getSubscribers = function(callback, limit){
Subscriber.find(callback).limit(limit);
};
index.js
var express = require('express');
var router = express.Router();
/* GET home page. */
router.get('/', function(req, res, next) {
res.render('index', { title: 'Express' });
});
module.exports = router;
You need to put your 404 app.use after all the other uses, otherwise it will ignore the api/subs after it.
Also, this bit will never run, because it also comes after an api.use that will always throw an error:
// error handler
app.use(function(err, req, res, next) {
// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
// render the error page
res.status(err.status || 500);
res.render('error');
});
Plus, you really shouldn't be throwing errors for 404s. It should tell the end user the page doesn't exist, but it shouldn't crash your script.
Also I agree with the other answer that says you should move those code blocks into separate router files, but that's more for good practice and structuring than for this particular bug.
Try putting it in a separate file and including it where you do with other routes, before the 404 handler
app.use('/', index);
app.use('/users', users);
So... make a subs.js route
var express = require('express');
var router = express.Router();
Subscriber = require('./routes/subscriber.js');
router.get('/', function(req, res){
Subscriber.getSubscribers(function(err, subscribers){
if(err){
throw err;
}
res.json(subscribers);
});
});
module.exports = router;
Then include it in your app.js
var subs= require('./routes/subs');
...
api.use('/api/subs', subs);
...
app.use(function(req, res, next) {
var err = new Error('Not Found');
err.status = 404;
next(err);
});

Socket is not listening using nodejs

Thanks for help in advance. I am getting following state from my console See Server running console log. Below Snippet is my app.js code where express and node server running. If you see my socket code my console.log underneath socket connection is not showing in server logs. Socket is not listening my messages.
I have also upload my sample of code at github, here you can find that (github.com/ferozpuri/node-app) client socket code is in SocketController.js an Angular controller file.
Here is my app.js file code, As you can see console log for "Connection was made" never show. and same with socket console.
var express = require('express');
var http = require('http');
var path = require('path');
var favicon = require('static-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
var engines = require('consolidate');
var routes = require('./routes');
var users = require('./routes/user');
var app = express();
var server = require('http').Server(app);
var io = require('socket.io')(server);
// view engine setup
//app.set('views', path.join(__dirname, 'views'));
//app.set('view engine', 'jade');
app.engine('html', engines.nunjucks);
app.set('view engine', 'html');
app.set('views', path.join(__dirname, 'views'));
app.use(favicon());
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded());
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use(app.router);
app.get('/', routes.index);
app.get('/users', users.list);
/// catch 404 and forwarding to error handler
app.use(function (req, res, next) {
var err = new Error('Not Found');
err.status = 404;
next(err);
});
/// error handlers
// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
app.use(function (err, req, res, next) {
res.render('error', {
message: err.message,
error: err
});
});
}
// production error handler
// no stacktraces leaked to user
app.use(function (err, req, res, next) {
res.render('error', {
message: err.message,
error: {}
});
});
io.on('connection', function (socket) {
console.log('A connection was made!');
socket.on('chat.message', function (message) {
console.log('New Message : ' + message);
});
});
module.exports = app;
I am not getting socket response from node server. PLease let me know if i not explain this properly or any thing is not here.
Server listing on port you can see this in screenshort or my project structure
Project structure & app listening port OR NPM START CODE
You have set up all handlers but you did not initialize app.
http.listen(app.get('port'), function() {
console.log('App is listening on port', app.get('port'));
});
You did not start your server. In your code, your server is created with this line:
var server = require('http').Server(app);
So, sometime after that, you need to add:
server.listen(80); // or use whatever port number you want the server on
I have resolved this issue by adding following line of code under constructing my express/after var app = express();
var server = require('http').Server(app);
var io = require('socket.io')(server);
server.listen(3000);
#jfriend00 and #Sablor, Thanks both of you for show me right direction. my server already running on port "3000" so with port 80 its was not working. because it is conflicting with my XAMPP server. Thanks you guys for participating

req.body undefined multipart

I have a problem with my POST request on multipart (form-data). All ideas in other topics don't work.
I use express, multer and postman
I totally delete body-parser
Uploading files works but accessing the data with a key don't work.
When I try console.log(req.body); I obtain undefined
This is my code:
app.js
var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cors=require('cors');
//var index = require('./routes/index');
//var users = require('./routes/users');
var UsersDB=require('./routes/UsersDB');
var app = express();
// view engine setup
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'jade');
// uncomment after placing your favicon in /public
//app.use(favicon(path.join(__dirname, 'public', 'favicon.ico')));
app.use(cors());
app.use(logger('dev'));
app.use(express.static(path.join(__dirname, 'public')));
//app.use('/', index);
//app.use('/users', users);
app.use('/Users',UsersDB);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
var err = new Error('Not Found');
err.status = 404;
next(err);
});
// error handler
app.use(function(err, req, res, next) {
// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
// render the error page
res.status(err.status || 500);
res.render('error');
});
module.exports = app;
UsersDB.js
var express = require('express');
var router = express.Router();
var Users=require('../models/Users');
var multer = require('multer');
var storage = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, './uploads')
},
filename: function (req, file, cb) {
cb(null, file.fieldname + '-' + Date.now() + ".png")
}
});
var upload = multer({ storage: storage }).single('avatar');
//** POST ** ROUTE : http://localhost:3000/Users/
router.post('/',function(req,res,next)
{
console.log(req.body.firstName);
/*
Users.addUsers(req.body,function(err,count)
{
if(err)
{
res.json(err);
}
else
{
res.json(req.body);//or return count for 1 &amp;amp; 0
}
});
*/
upload(req, res, function (err) {
if (err) {
// An error occurred when uploading
return
}
// Everything went fine
})
});
module.exports=router;
Error on Postman:
<!DOCTYPE html>
<html>
<head>
<title></title>
<link rel="stylesheet" href="/stylesheets/style.css">
</head>
<body>
<h1>Cannot read property 'firstName' of undefined</h1>
<h2></h2>
<pre>TypeError: Cannot read property 'firstName' of undefined
at /mnt/c/Users/Elodie/Desktop/server/routes/UsersDB.js:69:25
at Layer.handle [as handle_request] (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/layer.js:95:5)
at next (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/route.js:137:13)
at Route.dispatch (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/route.js:112:3)
at Layer.handle [as handle_request] (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/layer.js:95:5)
at /mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/index.js:281:22
at Function.process_params (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/index.js:335:12)
at next (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/index.js:275:10)
at Function.handle (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/index.js:174:3)
at router (/mnt/c/Users/Elodie/Desktop/server/node_modules/express/lib/router/index.js:47:12)</pre>
</body>
</html>
Since you're using multer to parse the request body, you're going to need to invoke multer prior to accessing req.body. The way you are currently using multer, it will extract the information from the request to process the file but will not be part of the middleware stack so you don't get the benefit of the body parsing prior to your route being called.
Add the multer middleware into the route signature and so it the request body will be parsed by multer prior to the route callback being invoked. For example like this
router.post('/', upload.single('avatar'), (req, res, next) => {
console.log(req.body.firstName)
})

Express.js 'socket.io/socket.io.js 404'

I'm trying to incorporate a live user count on my website http://clickthebutton.herokuapp.com which uses Express JS. When trying to install socket.io I get this error:
GET /socket.io/socket.io.js 404 1.911 ms - 1091
Yes, I have used 'npm install socket.io --save'
I have looked around for answers, tried them and nothing has helped. If anyone thinks they know what's happening, a response would be well appreciated! Here's my code:
app.js
var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
var io = require('socket.io')(app);
var routes = require('./routes/index');
var users = require('./routes/users');
var app = require('express')();
var server = require('http').Server(app);
var io = require('socket.io')(server);
var server = app.listen(app.get('port'), function () {
console.log('server listening on port ' + server.address().port);
})
var io = require('socket.io').listen(server);
// view engine setup
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'ejs');
// uncomment after placing your favicon in /public
//app.use(favicon(path.join(__dirname, 'public', 'favicon.ico')));
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use('/', routes);
app.use('/users', users);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
var err = new Error('Not Found');
err.status = 404;
next(err);
});
// error handlers
// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
app.use(function(err, req, res, next) {
res.status(err.status || 500);
res.render('error', {
message: err.message,
error: err
});
});
}
// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
res.status(err.status || 500);
res.render('error', {
message: err.message,
error: {}
});
});
module.exports = app;
index.ejs
<!-- socket.io -->
<script src="socket.io/socket.io.js"></script>
<script type="text/javascript">
var socket = io.connect();
</script>
</div>
</center>
</body>
routes/index.js
var express = require('express');
var router = express.Router();
var redis = require('redis'), client = redis.createClient(secret, "secret"); client.auth("secret", function() {console.log("Connected!");});
var app = express();
var server = require('http').Server(app);
var http = require('http');
var io = require('socket.io').listen(server);
io.on('connection', function(socket){
console.log('a user connected');
console.log(Object.keys(io.sockets.connected));
});
io.on('connection', function (socket) {
console.log('Socket.io connected!')
});
I only copy/pasted the code that referenced socket.io
Thanks!
In app.js alone you're creating three instances of socket.io, and once again in routes/index.js. There should be only one throughout your entire app.
A common setup for Express looks like this:
var app = require('express')();
var server = app.listen(app.get('port'), function () {
console.log('server listening on port ' + server.address().port);
});
var io = require('socket.io')(server);
If you need to reference either app, server or io in other files, you need to pass it as a variable.
EDIT: because you're using an express-generator based setup, the HTTP server will be created in bin/www and not app.js. In that case, you also need to create the socket.io server there:
/**
* Create HTTP server.
*/
var server = http.createServer(app);
var io = require('socket.io')(server); // add this line
Again, if you need to reference io somewhere else in your codebase, you need to pass it along from there.

Categories

Resources