Every button is clickable and functional before I inserted data.
Render update page after insert:
But then whatever I click the Web got stuck:
But data has already been inserted.
The insert code is here:
var assert = require('assert');
var mongoose = require('mongoose');
var db = mongoose.connection;
// ...
router.post('/update', function (req, res, next) {
var item = {
result: req.body.books
};
db.collection('details-data').insertOne(item, function (err, result) {
db.close();
});
res.render('update');
});
Related
Having a DB with multiple tables, I managed to get that for one table at a time and also to get the names of the tables.
However, it doesn't work to get the data for all the tables.
This is the code for getting the table names which works fine:
var express = require('express');
var router = express.Router();
var sqlite3 = require('sqlite3').verbose();
var db = new sqlite3.Database('./db/ocs_athletes.db');
router.get('/', function (req, res, next) {
db.serialize(function () {
db.all(
'SELECT name FROM sqlite_master WHERE type="table"',
function (err, rows) {
return res.send(rows);
}
);
});
});
module.exports = router;
it returns an array of this form:
[{"name":"Athlete"},{"name":"Game"},{"name":"AthletePhoto"},{"name":"AthleteResult"}]
I don't know how to get the data of these tables, I made a forEach through the elements and create a query for each table and save the data in result but doesn't work how it is.
router.get('/', function (req, res, next) {
db.serialize(function () {
db.all(
'SELECT name FROM sqlite_master WHERE type="table"',
function (err, rows) {
const result = [];
rows.forEach(
(table) => db.all('SELECT * FROM ' + table.name),
function (err, innerRows) {
result.push(innerRows);
}
);
return res.send(result);
}
);
});
});
module.exports = router;
The result is []. I guess it must be written in a way that it waits for the db to be read but I'm not sure.
Any suggestions?
I am attempting to build a basic Vue.js Express profile interface that returns profile info of a specific user based on a route parameter id associated with each user. The .get() request in Vue.js is set up as the following:
created () {
let uri = `http://localhost:3000/users/${this.$route.params.id}`;
this.axios.get(uri).then((response) => {
this.profile = response.data;
});
},
The corresponding GET route in Express.js is set up as the following:
// mongodb
const mongo = require('mongodb').MongoClient;
const url = '...'; // connection url
const usersDB = 'users'; // users db name
app.get('/users/:id', function(req, res) {
let id = req.params.id;
var users;
const findUsers = function(db, callback) {
const collection = db.collection('documents');
// no query filter
collection.find({}).sort( {username: 1} )
.toArray(function(err, docs) {
users = docs;
callback(docs);
});
}
mongo.connect(url, function(err, client) {
// assert.equal(null, err);
const db = client.db(usersDB);
findUsers(db, function() {
// send users
res.status(200).send(users);
client.close();
});
});
});
In the above Express route, I added let id = req.params.id with the intention of prompting this route to respond with specific user info based on req.params.id. I am not sure how to further configure this route to actually return such info based on id. I tried implementing the following in the route:
collection.find({_id: mongo.ObjectId(req.params.id)})
instead of using:
collection.find({}).sort( {username: 1} )
...but that did not work. Any idea how to set up this route to return data based on req.params.id? Thanks!
UPDATED EXPRESS ROUTE
// get all users
app.get('/users/:id', function(req, res) {
var o_id = new mongo.ObjectID(req.params.id))
// get all users
var users;
const findUsers = function(db, callback) {
const collection = db.collection('documents');
// no query filter
collection.find({'_id': o_id})
.toArray(function(err, docs) {
users = docs;
callback(docs);
});
}
mongo.connect(url, function(err, client) {
const db = client.db(usersDB);
findUsers(db, function() {
// send users
res.status(200).send(users);
client.close();
});
});
});
It seems the results aren't returned because of ObjectId comparision not working. Creating new ObjectID using the id from req.params and then doing collection.find should bring back the results
var o_id = new mongo.ObjectID(req.params.id);)
collection.find({'_id': o_id});
I am writing a web application to display a web page with content from a PostgreSQL database using NodeJS, express and pg-promise.
I have a database javascript called "db/location.js" which query the location table.
var db_global = require('./db'); # db.js is for building the database connection
var db = db_global.db;
var locationList = [];
// add query functions
module.exports = {
getAllLocationList: getAllLocationList,
locationList: locationList
};
function getAllLocationList() {
db.any('select * from location')
.then(function (data) {
console.log(data);
locationList = data;
}
);
}
In the routes folder, I have a route javascript called "locationRoute.js".
var express = require('express');
var router = express.Router();
var db = require('../db/location');
/* GET home page. */
router.get('/', function(req, res, next) {
res.render('index', { title: 'Express' });
});
/* GET the map page */
router.get('/locations', function(req, res) {
db.getAllLocationList();
console.log(db.locationList);
res.render('locations', {
title: "Express and Leaflet API", // Give a title to our page
//jsonData: db.getAllLocations // Pass data to the View
jsonData: db.locationList // Pass data to the View
});
});
module.exports = router;
When "http://localhost:3000/locations" is called, this is supposed to render the "locations.jade" which is to display "db.locationList" in a table.
My issue is that "console.log(db.locationList);" is always called before the query was completed. This caused "db.locationList" (jsonData) to be empty.
I don't want to mess the controller layer with the database layer but how to fix the issue?
I think you should change your db/location.js to be something like this...
function getAllLocationList() {
return db.any('select * from location');
}
Then you would do something like this in your routes...
router.get('/locations', function(req, res) {
db.getAllLocationList()
.then(function(data) {
res.render('locations', {
title: "Express and Leaflet API", // Give a title to our page
jsonData: data // Pass data to the View
});
});
...
In your example console.log(db.locationList); runs before the data is available, because it's asynchronous. It doesn't work the way you're expecting it to work.
Created a basic express.js application and added a model (using thinky and rethinkdb) trying to pass the changesfeed to the jade file and unable to figure how to pass the results of the feed. My understanding is that changes() returns infinite cursor. So it is always waiting for new data. How to handle that in express res. Any idea what am I missing here?
var express = require('express');
var router = express.Router();
var thinky = require('thinky')();
var type = thinky.type;
var r = thinky.r;
var User = thinky.createModel('User', {
name: type.string()
});
//end of thinky code to create the model
// GET home page.
router.get('/', function (req, res) {
var user = new User({name: req.query.author});
user.save().then(function(result) {
console.log(result);
});
//User.run().then(function (result) {
//res.render('index', { title: 'Express', result: result });
//});
User.changes().then(function (feed) {
feed.each(function (err, doc) { console.log(doc);}); //pass doc to the res
res.render('index', { title: 'Express', doc: doc}) //doc is undefined when I run the application. Why?
});
});
module.exports = router;
The problem that I believe you are facing is that feed.eachis a loop that is calling the contained function for each item contained in the feed. So to access the doc contained in console.log(doc) you are going to need to either place your code in the function in which doc exists(is in the scope of the variable doc), or you are going to need to make a global variable to store doc value(s).
So for example, assuming doc is a string and that you wish to place all doc's in an array. You would need to start off by creating a variable which has a scope that res.render is in, which for this example will be MYDOCS. Then you would need to append each doc to it, and after that you would simply use MYDOC anytime you are attempting to access a doc outside of the feed.each function.
var MYDOCS=[];
User.changes().then(function (feed){
feed.each(function (err, doc) { MYDOCS.push(doc)});
});
router.get('/', function (req, res) {
var user = new User({name: req.query.author});
user.save().then(function(result) {
console.log(result);
});
//User.run().then(function (result) {
//res.render('index', { title: 'Express', result: result });
//});
res.render('index', { title: 'Express', doc: MYDOCS[0]}) //doc is undefined when I run the application. Why?
});
module.exports = router;
I am having trouble with a project I am working on. I want to create a database in which I can store dates and links to YouTube videos in a MongoDB database. I am using Mongoose as the ORM. The problem seems to be that the database and collection is created and I can read and update it outside the routes but not inside (if anyone can understand what I am saying). I want to be able to make a GET request for the current items in the database on the /database route as well as make a POST to the /database route.
My code is below. Please help:
//grab express and Mongoose
var express = require('express');
var mongoose = require('mongoose');
var Schema = mongoose.Schema;
//create an express app
var app = express();
app.use(express.static('/public/css', {"root": __dirname}));
//create a database
mongoose.connect('mongodb://localhost/__dirname/data');
//connect to the data store on the set up the database
var db = mongoose.connection;
//Create a model which connects to the schema and entries collection in the __dirname database
var Entry = mongoose.model("Entry", new Schema({date: 'date', link: 'string'}), "entries");
mongoose.connection.on("open", function() {
console.log("mongodb is connected!");
});
//start the server on the port 8080
app.listen(8080);
//The routes
//The route for getting data for the database
app.get("/database", function(req, res) {
Entry.find({}, function(err, data) {console.log(err, data, data.length); });
});
//The route for posting data on the database
app.post("/database", function(req, res) {
//test new post
var newMonth = new Entry({date: '1997-10-30', link: 'https://wwww.youtube.com/'});
newMonth.save(function(err) {
if (err !== null) {
//object was not save
console.log(err);
} else {
console.log("it was saved!")
};
});
});
//create an express route for the home page at http://localhost:8080/
app.get('/', function(req, res) {
res.send('ok');
res.sendFile('/views/index.html', {"root": __dirname + ''});
});
//Send a message to the console
console.log('The server has started');
Your GET request should have worked because a browser executes a GET request by default. Try the following.
app.get("/database", function(req, res) {
Entry.find(function(err, data) {
if(err) {
console.log(err);
} else {
console.log(data);
}
});
});
As far as testing your POST route is concerned, install a plugin for Google Chrome called Postman. You can execute all sorts of requests using it. It's great for testing purposes.