I can't solve my problem. I stuck in this issue for a long time, so now I'm asking you.
Here, this was my question before I posted.
I made a mistake that I didn't export module at that time.
Now, I tested in localhost, it works well.
However, if I test with postman, it doesn't work at all like bellow
If you guys have this experience and resolved, then please give me some tips to resolve this issue.
It's my app.js, routes/imgFiles.js and models/imgFiles.js
app.js
const express = require('express');
const bodyParser = require('body-parser');
const app = express();
const port = process.env.PORT || 3000;
const path = require('path');
const favicon = require('serve-favicon');
const logger = require('morgan');
const cookieParser = require('cookie-parser');
app.use(bodyParser.json({ limit: '10mb' }));
app.use(bodyParser.urlencoded({ extended: false }));
app.use(express.static(path.join(__dirname, '../awesome-drill/dist')));
app.use(logger('dev'));
const appRoutes = require('./routes/app');
const imgRoutes = require('./routes/imgFiles');
const userRoutes = require('./routes/user');
app.use(imgRoutes);
app.use(userRoutes);
app.use(appRoutes);
app.use(cookieParser());
app.use((req, res) => {
res.setHeader('Access-Control-Allow-Origin', '*');
res.setHeader('Access-Control-Allow-Headers', 'Origin, X-Requested-Width, Content-Type, Accept');
res.setHeader('Access-Control-Allow-Methods', 'POST, GET, PATCH, DELETE, OPTIONS');
});
app.use(express.static('routes'));
app.get('*', (req, res) => {
res.sendFile(path.join(__dirname, '../awesome-drill/dist/index.html'));
});
app.listen(port, () => {
console.log(`Server is up on port ${port}`);
});
models/imgFiles.js
var express = require('express');
var router = express.Router();
var ImageFile = require('../models/imageFiles');
var multer = require('multer');
var storage = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, '../img/') // Set directory
},
filename: function (req, file, cb) {
cb(null, file.name) // Set file name
}
});
var img = multer({ storage: storage });
router.post('/uploadFiles',img.single('imgfile'), (req, res) => {
var imageFile = new ImageFile({
imgName: req.body.imgName,
imgType: req.body.imgType,
imgSize: req.body.imgSize,
imgContent: req.body.imgContent
});
imageFile.save((err, result) => {
if (err) {
return res.status(500).json({
title: 'An error occured',
error: err
});
}
res.status(201).json({
message: 'Img saved',
obj: result
});
});
});
module.exports = router;
models/imgFiles.js
var {mongoose} = require('../db/mongoose');
var uniqueValidator = require('mongoose-unique-validator');
var schema = mongoose.Schema({
imgName: {
type: String,
},
imgType: {
type: String,
},
imgSize: {
type: Number,
},
imgContent: {
type: String,
},
});
schema.plugin(uniqueValidator);
module.exports = mongoose.model('ImageFile', schema);
Related
I have created a Node.JS REST API server, and tried to test it by sending a GET request on https://localhost:3443/public/images/logo.png that logo.png image exist and I can see it in the directory. But the Postman gives me Not Found 404 error message.
This is my imagesRouter.js:
const express = require('express');
const bodyParser = require('body-parser');
const Images = require('../models/images');
var authenticate = require('../authenticate');
const imagesRouter = express.Router();
const cors = require('./cors');
imagesRouter.use(bodyParser.json());
imagesRouter.options('*', cors.corsWithOptions, (req, res) => { res.sendStatus(200); } );
imagesRouter.route('/')
//.options(cors.corsWithOptions, (req, res) => { res.sendStatus(200); })
.get(cors.cors, (req,res,next) => {
Images.find({})
.then((images) => {
res.statusCode = 200;
res.setHeader('Content-Type', 'application/json');
res.json(images);
}, (err) => next(err))
.catch((err) => next(err));
})
module.exports = imagesRouter;
And this is my app.js file:
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 index = require('./routes/index');
var usersRouter = require('./routes/usersRouter');
var imagesRouter = require('./routes/imagesRouter');
const uploadRouter = require('./routes/uploadRouter');
const Images = require('./models/images');
//const uploadRouter = require('./routes/uploadRouter');
//const favoriteRouter = require('./routes/favoriteRouter')
var config = require('./config');
const mongoose = require('mongoose');
//mongoose.set('useCreateIndex', true);
mongoose.Promise = require('bluebird');
var passport = require('passport');
var authenticate = require('./authenticate');
// Connection URL
const url = config.mongoUrl;
const connect = mongoose.connect(url, {
//useMongoClient: true,
/* other options */
useNewUrlParser: true ,
useUnifiedTopology: true
});
connect.then((db) => {
console.log("Connected correctly to server");
}, (err) => { console.log(err); });
var app = express();
// Secure traffic only
app.all('*', (req, res, next) => {
if (req.secure) {
return next();
}
else {
res.redirect(307, 'https://' + req.hostname + ':' + app.get('secPort') + req.url);
}
});
// 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(passport.initialize());
app.use('/', index);
app.use('/users', usersRouter);
app.use(express.static(path.join(__dirname, 'public')));
app.use('/public/images',imagesRouter);
app.use('/imageUpload',uploadRouter);
//app.use('/imageUpload',uploadRouter);
//app.use('/favorites',favoriteRouter);
// 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;
EDIT: This is my app files tree:
You'll need to specify the base of the static router to point to the public folder. You are currently "mounting" the public folder on the root route in the current code. You can change this line
app.use(express.static(path.join(__dirname, 'public')));
To:
app.use('/public', express.static(path.join(__dirname, 'public')));
Alternatively, you can call the endpoint from postman (or any other client) as: https://localhost:3443/images/logo.png
What am I doing wrong here? I saw somewhere that body-parser is now inbuilt in express in express, I tried that also still the same result.
app.js
const express = require("express");
const app = express();
const mongoose = require("mongoose");
require("dotenv/config");
const posts = require("./routes/posts");
const bodyParser = require("body-parser");
//middleware to use "/posts" whenever we go to posts
app.use("/posts", posts);
app.use(bodyParser.json()); //parsing json
//routes
app.get("/", (req, res) => {
//handle root
res.send("We are home");
});
//how do we start listening/connect to the server
mongoose.connect(
process.env.DB_CONNECTION,
{ useNewUrlParser: true, useUnifiedTopology: true },
() => console.log("connected to DB!")
);
app.listen(3000);
Post.js
const mongoose = require("mongoose");
const PostSchema = mongoose.Schema({
title: {
type: String,
required: true,
},
description: {
type: String,
required: true,
},
date: {
type: Date,
default: Date.now(),
},
});
module.exports = mongoose.model("Posts", PostSchema);
posts.js
const express = require("express");
let router = express.Router();
const Post = require("../models/Post");
//middleware
/*router.use(function(req, res, next){
console.log(req.url, "#", Date.now());
next();
})*/
router
.route("/")
.get((req, res, next) => {
res.send("hi get /posts");
})
.post((req, res, next) => {
console.log(req.body);
});
module.exports = router;
Terminal always shows that its undefined.
here's a screenshot of postman:
Yes bodyParser is included in the current versions of expressjs, and you can apply it like this:
app.use(express.json());
Also this middleware must be applied before using routes. So the order must be like this:
app.use(express.json()); //parsing json
app.use("/posts", posts);
When I did res.json (newschema) on post action, the properties are not displayed any more on Postman and also in Mongodb.
This is formations.routes
const express = require('express');
const router = express.Router();
const Formation = require('../models/formations');
const mongoose = require('mongoose');
const config = require('../config/database');
router.get('/', function(req, res){
//Formation.getFormations(function(err, formations){
// if(err)throw err;
// res.json(formations);
//});
Formation.find({})
.exec(function(err, Formations){
if(err){
console.log('error');
}else{
res.json(Formations);
}
})
});
router.post('/', function(req, res){
console.log('post a formations');
var newFormation = new Formation();
newFormation.title = req.body.title;
newFormation.url = req.body.url;
newFormation.description = req.body.description;
newFormation.save(function(err, newFormation){
if(err){
console.log('error insertion');
} else {
res.json(newFormation);
//res.json({success: true, msg:'user registred'});
}
});
});
This is formation.models
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
const config = require('../config/database');
const FormationSchema = mongoose.Schema ({
title: String,
url: String,
description: String
});
module.exports = mongoose.model('Formation', FormationSchema, 'Formations');
This is my app.js ( endpoint)
const express = require('express');
const path = require('path');
const bodyParser = require('body-parser');
const cors = require('cors');
const passport = require('passport');
const mongoose = require('mongoose');
const config = require('./config/database');
const User = require('./models/user');
const Formation = require('./models/formations');
mongoose.connect(config.database , { useNewUrlParser: true });
mongoose.connection.on('connected', () => {
console.log('connected to database... ' + config.database);
});
mongoose.connection.on('error', (err) => {
console.log('database error'+err);
});
/*mongoose.connect('mongodb://localhost:27017/hello', { useNewUrlParser: true });
var db = mongoose.connection;
db.on('error', console.error.bind(console, 'connection error:'));
db.once('open', function() {
console.log('we are connected!');
});*/
const app = express();
const users = require('./routes/users');
const formations = require('./routes/formations');
//port number
const port = 3001;
//cors middleware
app.use(cors({
origin: 'http://localhost:4200'
}));
//passwport middelware
app.use(passport.initialize());
app.use(passport.session());
require('./config/passport')(passport); //pour implémenter fichier passport.js
//set static folder
app.use(express.static(path.join(__dirname + '/public')));
//BodyParser middleware
app.use(express.json());
app.use(bodyParser.json());
app.use('/users', users);//hedhiya ki nekteb /users barka f url yemchili direct lel const users = require('./routes/users'); fichier hedhka
app.use('/formations', formations);
//c un route
//just meloul 7atineha bch ntastiw beha
//index route
app.get('/', function(req, res){
res.send('invalid endpoint');
});
//start Server
app.use(bodyParser.urlencoded({extended:true}));
app.listen(port, () => {
console.log('Server started on port' +port);
});
And this is how I make a post action in Postman
The save method only has an error parameter in the callback. You are adding a newFormations parameter which will always be undefined and in the scope of the method you are returning undefined in the res.json call. To fix it remove the newFormation parameter as below:
newFormation.save(function(err){
if(err){
console.log('error insertion');
} else {
res.json(newFormation);
//res.json({success: true, msg:'user registred'});
}
});
I am working on a Mean stack application, I have defined an expressjs backend post route to store some data on server, but its not working and returning an error message which is provided for handling errors 'An error occurred in form api'.
router.post('/userform', function (req, res, next) {
var form = new Form({
controlType: req.body.controlType,
label: req.body.label,
required:req.body.required ,
placeholder: req.body.placeholder,
options: req.body.options
});
form.save(function(err, result) {
if (err) {
return res.status(500).json({
title: 'An error occurred in form api',
error: err
});
}
res.status(201).json({
message: 'Form created',
obj: result
});
});
});
Its the mongoose schema that I am using:
var mongoose = require('mongoose');
var Schema = mongoose.Schema;
var mongooseUniqueValidator = require('mongoose-unique-validator');
var formSchema = new Schema({
controlType: {type: String, required: true},
label: {type: String, required: true},
required: {type: Boolean},
placeholder: {type: String},
options: [String], //to store options for select or radio input
} , {collection: 'inputForm'});
formSchema.plugin(mongooseUniqueValidator);
module.exports = mongoose.model('Form', formSchema);
It is the app.js file:
// Get dependencies
const express = require('express');
const path = require('path');
const http = require('http');
const bodyParser = require('body-parser');
var mongoose = require('mongoose');
// Get our API routes
const api = require('./routes/api');
const formApi = require('./routes/form');
const app = express();
mongoose.connect('localhost:27017/test-mean');
// Parsers for POST data
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
// Point static path to dist
app.use(express.static(path.join(__dirname, 'dist')));
//to avoid cross origin requests errors
app.use(function (req, res, next) {
res.setHeader('Access-Control-Allow-Origin', '*');
res.setHeader('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
res.setHeader('Access-Control-Allow-Methods', 'POST, GET, PATCH, DELETE, OPTIONS');
next();
});
// Set our api routes
app.use('/api', api);
app.use('/form', formApi);
// Catch all other routes and return the index file
app.get('*', (req, res) => {
res.sendFile(path.join(__dirname, 'dist/index.html'));
});
/**
* Get port from environment and store in Express.
*/
const port = process.env.PORT || '3000';
app.set('port', port);
/**
* Create HTTP server.
*/
const server = http.createServer(app);
/**
* Listen on provided port, on all network interfaces.
*/
server.listen(port, () => console.log(`API running on localhost:${port}`));
Please help. Thanks
Add your body-parser code above all router
// Get dependencies
const express = require('express');
const path = require('path');
const http = require('http');
const bodyParser = require('body-parser');
var mongoose = require('mongoose');
// Parsers for POST data
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
// Get our API routes
const api = require('./routes/api');
const formApi = require('./routes/form');
const app = express();
mongoose.connect('localhost:27017/test-mean');
// Point static path to dist
app.use(express.static(path.join(__dirname, 'dist')));
//to avoid cross origin requests errors
app.use(function (req, res, next) {
res.setHeader('Access-Control-Allow-Origin', '*');
res.setHeader('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
res.setHeader('Access-Control-Allow-Methods', 'POST, GET, PATCH, DELETE, OPTIONS');
next();
});
// Set our api routes
app.use('/api', api);
app.use('/form', formApi);
// Catch all other routes and return the index file
app.get('*', (req, res) => {
res.sendFile(path.join(__dirname, 'dist/index.html'));
});
/**
* Get port from environment and store in Express.
*/
const port = process.env.PORT || '3000';
app.set('port', port);
/**
* Create HTTP server.
*/
const server = http.createServer(app);
/**
* Listen on provided port, on all network interfaces.
*/
server.listen(port, () => console.log(`API running on localhost:${port}`));
I have created the database and written the mp3 file in the db.Now I have created a server and used the router using express.But I am unable to see the response.It is displayed below.
My code is as follows:
server.js
var express = require('express');
var app = express();
var mongoose = require('mongoose');
var morgan = require('morgan');
var bodyParser = require('body-Parser');
var methodOverride = require('method-override');
var cors = require('cors');
mongoose.connect('mongodb://localhost/aHolyBoly');
app.use(morgan('dev'));
app.use(bodyParser.urlencoded({ 'extended': 'true' }));
app.use(bodyParser.json());
app.use(bodyParser.json({ type: 'application/vnd.api+json' }));
app.use(methodOverride());
app.use(cors());
app.use(function (req, res, next) {
res.header("Access-Control-Allow-Origin", "*");
//res.header('Access-Control-Allow-Methods', 'DELETE, PUT');
res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
next();
});
var Songs = mongoose.model('Songs', {
title: String
});
app.get('/api/songs', function (req, res) {
console.log("fetching songs...");
Songs.find(function (err, songs) {
if (err)
res.send(err)
res.json(songs);
//console.log('Songs',+JSON.stringify(Songs));
});
});
app.listen(8080);
console.log("App listening on port 8080");
How can I see the response in the console.i.e my songs.mp3 file?
storeAudio.js
var mongoose = require('mongoose');
var fs = require('fs');
var Grid = require('gridfs-stream');
Grid.mongo=mongoose.mongo;
//establish mongoDB connection
mongoose.Promise = global.Promise;
var conn = mongoose.createConnection('mongodb://localhost:27017/aHolyBoly');
conn.once('open',function(){
var gfs = Grid(conn.db);
// var db = new mongo.Db('aHolyBoly', new mongo.Server("127.0.0.1", 27017));
//var gfs = Grid(db, mongo);
var writeStream = gfs.createWriteStream({
filename:'song1.mp3'
});
fs.createReadStream('../list/hero.mp3').pipe(writeStream);
writeStream.on('close',function(file){
console.log(file.filename +'Written to db');
});
});
Points:
1.)I have stored the mp3 file in the database using gridFs-stream.
2.)Now I want to create an API so that I can host my server on it and my frontend uses that data with the help of API.
3.) The frontend will only fetch the data i.e) mp3 file.
What you must understand is when you use mongo's GridFS, it will create two collection namely fs.files and fs.chuncks and what ever other models you created do not have your file rather what you can do is to link those files in your model. If you are willing(may be for now) to receive only one file that you have stored with filename song1.mp3 the below stated code will work for you. Hope this helps!
var express = require('express');
var app = express();
var mongoose = require('mongoose');
var morgan = require('morgan');
var bodyParser = require('body-Parser');
var methodOverride = require('method-override');
var cors = require('cors');
mongoose.Promise = global.Promise
var conn = mongoose.createConnection('mongodb://localhost/aHolyBoly');
var Grid = require('gridfs-stream');
Grid.mongo=mongoose.mongo;
let gfs;
conn.once('open', function () {
gfs = Grid(conn.db);
});
app.use(morgan('dev'));
app.use(bodyParser.urlencoded({ 'extended': 'true' }));
app.use(bodyParser.json());
app.use(bodyParser.json({ type: 'application/vnd.api+json' }));
app.use(methodOverride());
app.use(cors());
app.use(function (req, res, next) {
res.header("Access-Control-Allow-Origin", "*");
//res.header('Access-Control-Allow-Methods', 'DELETE, PUT');
res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
next();
});
//song model should not be created like this
//var Songs = mongoose.model('Songs', {
// title: String
//});
app.get('/api/songs', function (req, res) {
console.log("fetching songs...");
//read from mongodb
var readstream = gfs.createReadStream({
filename: 'song1.mp3'
});
// set response header
res.writeHead(200, {
'Content-Type': 'audio/mpeg',
});
readstream.pipe(res);
});
app.listen(8080);
console.log("App listening on port 8080");
To make clear on how linking a file to a model can be done, I have provided some code below:
var mongoose = require('mongoose')
var Schema = mongoose.Schema
const UserFile = new Schema({
username: { type: String, unique: true}
file: { type: String }
})
// create the model to export
var UserFileModel = mongoose.model('UserFile', UserFile)
module.exports = schemaModel
Suppose, you have stored a file for one user. And you stored that filename in file field of UserFileModel with the corresponding username. Then, you can easily get file of corresponding user in following route as below:
var UserFileModel = require('path-to-UserFileModel');
router.get('/api/user/file/:username', function (req, res) {
UserFileModel.findOne({username: req.params.username}, function(err, doc){
//read from mongodb
var readstream = gfs.createReadStream({
filename: doc.file
});
// set response header
res.writeHead(200, {
'Content-Type': 'audio/mpeg',
});
readstream.pipe(res);
})
});