Node.js restful webservice using express and mongoose. Routing not working - javascript

I'm trying to build a RESTful webservice following this tutorial:
https://www.codementor.io/olatundegaruba/nodejs-restful-apis-in-10-minutes-q0sgsfhbd
It's not working returning me a CANNOT GET/ reports error...
I'm trying to learn node.js and I can't find the error anywhere and everything I tried didn't work.
Also, when I call the server, it reaches to index.js which prints a "HEY". Wasn't this supposed to reach server.js first?
Here is my code:
Server.js
var express = require('express'),
app = express(),
port = process.env.PORT || 3000,
mongoose = require('mongoose'),
Report = require('./api/models/reportModel.js'),
bodyParser = require('body-parser');
mongoose.Promise = global.Promise;
mongoose.connect('mongodb://localhost/server');
app.use(bodyParser.urlencoded({ extended: true }));
app.use(bodyParser.json());
var routes = require('./api/routes/reportRoute.js');
routes(app);
app.listen(port);
console.log('Report RESTful API server started on: ' + port);
reportRoute.js
'use strict';
module.exports = function(app) {
var reports = require('../controllers/reportController.js');
// report Routes
app.route('/reports')
.get(reports.list_all_reports)
.post(reports.create_a_report);
app.route('/reports/:reportId').get(reports.read_a_report)
.put(reports.update_a_report)
.delete(reports.delete_a_report);
};
reportController.js
'use strict';
var mongoose = require('mongoose'),
Report = mongoose.model('Reports');
exports.list_all_reports = function(req, res) {
Report.find({}, function(err, report) {
if (err)
res.send(err);
res.json(report);
});
};
exports.create_a_report = function(req, res) {
var new_report = new Report(req.body);
new_report.save(function(err, report) {
if (err)
res.send(err);
res.json(report);
});
};
exports.read_a_report = function(req, res) {
Report.findById(req.params.reportId, function(err, report) {
if (err)
res.send(err);
res.json(report);
});
};
exports.update_a_report = function(req, report) {
Report.findOneAndUpdate({_id: req.params.taskId}, req.body, { new: true }, function(err, report) {
if (err)
res.send(err);
res.json(report);
});
};
exports.delete_a_report = function(req, res) {
Report.remove({
_id: req.params.reportId
}, function(err, report) {
if (err)
res.send(err);
res.json({ message: 'Report successfully deleted' });
});
};
Thank you for your help...
EDIT:
index.js
const express = require('express');
const app = express();
var route = require('./api/routes/reportRoute');
app.get('/', function(req, res) {
res.send('HEY!');
})
app.listen(3000, function(){console.log('Server running on port 3000')});

You haven't posted your reportController.js but this problem will occur if the function list_all_reports does not set a response body. For example, adding
res.json({hello: "world"});
to the handler function should make it work.

Related

Problem in APIRest file throught GET in node.js

I am trying to do my first API Rest and I am following some tutorials. I am requesting all the articles in a MongoDB database.
This is the code of the main:
var express = require("express"),
app = express(),
http = require("http"),
bodyParser = require("body-parser"),
methodOverride = require("method-override"),
server = http.createServer(app),
mongoose = require('mongoose');
app.use(bodyParser.urlencoded({ extended: false }));
app.use(bodyParser.json());
app.use(methodOverride());
// Import Models and controllers
var models = require('./models/article')(app, mongoose);
var articleCtrl = require('./controllers/articleController');
// Example Route
var router = express.Router();
router.get('/', function(req, res) {
res.send("Hello world!");
});
articles.route('/articles/:id')
.get(articleCtrl.findById);
articles.route('/articles')
.get(articleCtrl.findAllarticles)
.post(articleCtrl.addarticle);
app.use('/api', articles);
app.use(router);
mongoose.connect('mongodb://localhost/ustcg', { useNewUrlParser: true ,useUnifiedTopology: true}, function(err, res) {
if(err) {
console.log('ERROR: connecting to Database. ' + err);
}
app.listen(3000, function() {
console.log("Node server running on http://localhost:3000");
});
});
The code of the controller is here:
// Import article and mongoose
var mongoose = require('mongoose');
var Article = mongoose.model('Article');
//GET - Return a article with specified ID
exports.findById = function(req, res) {
Article.findById(req.params.id, function(err, Article) {
if(err) return res.send(500, err.message);
console.log('GET /article/' + req.params.id);
res.status(200).jsonp(Article);
});
};
//GET - Return all articles in the DB
exports.findAllarticles = function(req, res) {
Article.find(function(err, Article) {
if(err) res.send(500, err.message);
console.log('GET /article')
res.status(200).jsonp(Article);
});
};
//POST - Insert a new article in the DB
exports.addarticle = function(req, res) {
console.log('POST');
console.log(req.body);
var Article = new Article({
title: req.body.title,
paragraphs: req.body.paragraphs
});
Article.save(function(err, Article) {
if(err) return res.send(500, err.message);
res.status(200).jsonp(Article);
});
};
The model:
//We create the model
exports = module.exports = function(app, mongoose) {
var ArticleSchema = new mongoose.Schema({
title: { type: String },
paragraphs: { type: Array },
});
mongoose.model('Article', ArticleSchema);
};
When I tried to request the following http request it send me 404 error. I can not see any logs on the console so it is not entering the methods in order to see the exception is happening so I am stucked with this...
If someone could help me it would be nice.
what is articles variable in your main file.
I tried your code in my machine and struggled with articles variable and you have extra imports which are not required.
Try following code it works fine
var express = require("express");
var app = express();
var bodyParser = require('body-parser');
app.use(bodyParser.urlencoded({ extended: false }));
app.use(bodyParser.json());
var articleCtrl = require('./sample.controller');
var router = express.Router();
router.get('/', function(req, res) {
res.send("Hello world!");
});
router.get('/articles/:id', articleCtrl.findById);
router.post('/articles', articleCtrl.addarticle);
router.get('/articles', articleCtrl.findAllarticles)
// app.use('/api', router);
app.use(router);
app.listen(3000, function() {
console.log("Node server running on http://localhost:3000");
});
if you uncomment app.use('/api', router); then you can also use routes as localhost:3000/api/articles

NodeJS server returning empty data from MongoDB

I am making an app where the app is going to send the POST request data to the nodeJS server. The JSON format of the content looks like: {"encrypteddata": "someencryptedvalueofthetext"}. This data will be saved in a MongoDB.
I created two file one is app.js and another is /models/encdata.js. Content of both the file is given below.
app.js
var express = require('express');
var app = express();
var bodyParser = require('body-parser');
var mongoose = require('mongoose');
app.use(bodyParser.json());
ENCDATA = require('./models/encdata');
mongoose.connect('mongodb://localhost/encdata', { useMongoClient: true }); // the url access the database
var db = mongoose.connection;
app.get('/', function(req, res){
res.send('Visit /api/encdata');
app.get('/api/encdata', function(req, res){
ENCDATA.getENCDATA(function(err, encdata){
if(err){
throw err;
}
res.json(encdata);
});
});
app.post('/api/encdata', function(req, res){
var encdata = req.body;
ENCDATA.addENCDATA(encdata, function(err, encdata){
if(err){
throw err;
}
res.json(encdata);
});
});
});
app.listen(3000);
console.log('Running on port 3000');
encdata.js
var mongoose = require('mongoose');
var encdataencryptSchema = mongoose.Schema({
encrypteddata: {
type: String,
required: true
}
});
var ENCDATA = module.exports = mongoose.model('encdata', encdataencryptSchema);
module.exports.getENCDATA = function(callback, limit){
ENCDATA.find(callback).limit(limit);
}
module.exports.addENCDATA = function(encdata, callback){
ENCDATA.create(encdata, callback);
}
And data in MongoDB is:
{"encrypteddata": "someencryptedvalueofthetext"}
But when I make a GET request to the url localhost:3000/api/encdata it shows [] (an empty array although I have data). Even the POST request is not working and I am not able to save any data.
I rewrote your code by changing the name of the variable and it worked for me. The app.js file looks something like this:
var express = require('express');
var app = express();
var bodyParser = require('body-parser');
var mongoose = require('mongoose');
var http = require('http');
app.use(bodyParser.json());
AES = require('./models/aes');
mongoose.connect('mongodb://localhost/aes', { useMongoClient: true }); // the url access the database
var db = mongoose.connection;
app.get('/', function(req, res){
res.send('Visit /api/aes');
app.get('/api/aes', function(req, res){
AES.getAES(function(err, aes){
if(err){
throw err;
}
res.json(aes);
});
});
app.post('/api/aes', function(req, res){
var aes = req.body;
AES.addAES(aes, function(err, aes){
if(err){
throw err;
}
res.json(aes);
});
});
});
app.listen(3000);
console.log('Running on port 3000');
In the encdata.js you can change the variable to AES. Name the mongodb collection and database as aes.

Express routes returning 404s

I have a couple of simple routes that I have misconfigured and not sure why.
app.js:
//app setup
var http = require('http');
var bodyParser = require('body-parser');
var express = require('express');
var routes = require('./routes');
var agent = require('./routes/agent');
var config = require('./config');
var app = express();
app.server = http.createServer(app);
app.use(bodyParser.json({
limit : config.bodyLimit
}));
app.use(bodyParser.urlencoded({
extended : true
}));
app.use('/v1', routes);
app.use('/v1/agent', agent);
app.server.listen(config.port);
console.log('API listening on port ' + app.server.address().port);
module.exports = app;
This returns responses on the /v1/ route (index.js):
'use strict';
var express = require('express');
var router = express.Router();
router.get('/', function (req, res) {
res.status(403).json({
message: 'Invalid request.'
});
});
module.exports = router;
in the agent route, I have a POST handler that is being handled correctly at /v1/agent/login. But while a GET routed at /v1/agent/ works, a GET routed to /v1/agent/123 returns a 404:
'use strict';
var agentController = require('../controller/agent.js');
var express = require('express');
var router = express.Router();
function handleError(objError, res) {
res.status(500).json({ errorMessage : objError.message });
}
router.get('/', function (req, res) {
res.status(200).json({
message: 'OK' // works fine
});
});
router.get('/:id'), function (req, res) {
var agentNum = req.params.id;
res.send(req.params); // 404 here
try {
//res.status(200).json({ message: 'hello agent.'});
} catch (err) {
// handleError(err, res);
}
};
router.post('/login', function (req, res) {
var agentNum, password;
// works fine
});
router.post('/pwr', function (req, res) {
//also works fine
});
module.exports = router;
My understanding is that the app.use method should redirect the route and any GET requests appended to that route to the one I specified (agent), so why is it that the one with params fails while the root one succeeds?
Thank you
You're not passing the callback correctly.
router.get('/:id')
router.get('/:id', function(req, res) {
var agentNum = req.params.id;
res.send(req.params); // 404 here
try {
//res.status(200).json({ message: 'hello agent.'});
} catch (err) {
// handleError(err, res);
}
});

Express.js req.body is returning nothing

I am learning node and express to create an api for an angular app I will be creating.
When I try and post something the req.body seems to be blank.
This is my server.js file
'use strict';
var express = require('express'),
app = express(),
mongoose = require('mongoose'),
router = require('./api'),
bodyParser = require('body-parser');
mongoose.connect('mongodb://localhost/my_db');
app.use(bodyParser.json());
app.use('/api', router);
app.get('/', function(req, res) {
res.render(__dirname + '/index.jade');
});
app.listen(3001, function() {
console.log('Listening on port 3001');
});
and this is my api/index.js file:
'use strict';
var express = require('express'),
Todo = require('../models/todo'),
router = express.Router();
router.get('/todos', function(req, res) {
Todo.find({}, function(err, todos) {
if(err) {
return console.log(err);
}
res.json({todos: todos});
});
});
router.post('/todos', function(req, res) {
var todo = req.body;
res.json({todo: todo});
});
module.exports = router;
when I use postman to post this to http://localhost:3001/api/todos:
{
'name': 'Walk the Dog',
'completed': false
}
my response is:
{
"todo": {}
}
I can't see why this would be blank, any help is appreciated.
UPDATE
Turns out I was posting text in postman instead of JSON.
use this in your server.js file
app.use(bodyParser.urlencoded({extended:true}));
app.use(bodyParser.json());

Use a mysql connection across my express js app

I am pretty new with node.js and express so bear with me please.
I am wondering how i can get a mysql instance and use it in my controller. I have 4 files that look like this:
see my comment in the controller.js file
server.js :
var express = require('./config/express');
var app = express();
module.exports = app;
app.listen(3000);
console.log('server running');
express.js :
var express = require('express'),
bodyParser = require('body-parser'),
mysql = require('mysql');
module.exports = function() {
var app = express();
app.use(bodyParser.urlencoded({
extended: true
}));
app.use(bodyParser.json());
app.set('views','./app/views');
app.set('view engine','ejs');
//NOT SURE WHAT TO DO HERE OR WHERE TO PUT THE CONNECTION DETAILS
var dbConnection = mysql.createConnection({
host : 'localhost',
user : 'someuser',
database : 'somedb',
password : 'somepass'
});
//connection.connect();
//
//connection.query('SELECT 1 + 1 AS solution', function(err, rows, fields) {
// if (err) throw err;
// console.log('The solution is: ', rows[0].solution);
//});
//
//connection.end();
require('../app/routes/index.server.routes.js')(app);
app.use(express.static('./public'));
return app;
};
routes.js :
module.exports = function(app) {
var index = require('../controllers/index.server.controller');
app.get('/', index.render);
app.post('/', index.stuff);
};
controller.js :
exports.render = function(req, res) {
//DO DB STUFF HERE
res.render('index', {
title: 'this is the title'
});
};
exports.stuff = function(req, res) {
res.render('index', {
title: 'this is the title post'
});
};
To use the connection instance in your controller, you'll need to pass it from the express.js file to the controller.js file. The first step is to pass the connection instance to the router:
express.js
require('../app/routes/index.server.routes.js')(app, connection);
This will make it available in the routes.js file. You then need to pass the same connection instance to the controller.
index.server.routes.js
module.exports = function(app, connection) {
var index = require('../controllers/index.server.controller')(connection);
app.get('/', index.render);
app.post('/', index.stuff);
};
The controller will need to be refactored so it takes a connection instance as an argument:
index.server.controller.js
function IndexController(connection) {
controllerMethods = {};
controllerMethods.render = function (req, res) {
// You can use the connection instance here.
connection.connect()
// Run your query
connection.end()
...
};
// Define other methods for the controller
// Return the object that holds the methods.
return controllerMethods;
}
module.exports = IndexController;

Categories

Resources