Home > Software engineering >  Why does my middleware produce an error when running get request by ID
Why does my middleware produce an error when running get request by ID

Time:04-23

I have just a simple API I am building for school. There is a collection of Books that are being accessed, displaying book by id, displaying all books, adding book, updating book. I changed some of my code to incorporate middleware. Without middleware I am able to retrieve book by id, but when I use middleware I get an error stating book is not defined.

App.js

const express = require('express');
const bookRouter = express.Router();
const mongoose = require('mongoose');
const bodyParser = require('body-parser');
const Book = require('./models/bookModel');

const app = express();
const port = process.env.PORT || 8081;
const url = 'mongodb://localhost/bookAPI';

app.use(bodyParser.urlencoded({extended:true}));
app.use(bodyParser.json());

mongoose.connect(url).then(() => console.log("Connected to db"));

bookRouter.route('/books')
.post((req, res) => {
    const book = new Book(req.body);
    book.save();
    return res.status(201).json(book);
})
.get((req, res) => {
    const query = {}
    if(req.query.genre) {
        query.genre = req.query.genre;
    }

    Book.find((err, books) => {
        if(err) {
            return res.send(err);
        }
        return res.json(books);
    });
});

bookRouter.use('/books/:bookId', (req, res, next) => {
    Book.findById(req.params.bookId, (err, book) => {
        if(err) {
            return res.send(err);
        }
        if(book) {
            req.book = book;
            return next();
        }
        return res.sendStatus(404);
    });
});


bookRouter.route('/books/:bookId')
.put((req, res) => {
    const { book } = req;
    book.title = req.body.title;
    book.author = req.body.author;
    book.genre = req.body.genre;
    book.read = req.body.read;
    book.save();
    return res.json(book);
})
.get((req, res) => {
    res.json(book);
});


app.use('/api', bookRouter);


app.get('/', (req, res) => {
    res.send("Hello World");
});


app.listen(port, () => {
    console.log(`Listening on port: ${port}`);
});

bookModel.js

const mongoose = require('mongoose');
const {Schema} = mongoose;

const bookModel = new Schema({
    title: {type:String},
    author: {type:String},
    genre: {type:String},
    read: {type:Boolean, default: false},
});

module.exports = mongoose.model("Book", bookModel);

Error when I request get by book id:

ReferenceError: book is not defined
   at D:\Desktop\lab10\app.js:63:14
   at Layer.handle [as handle_request] (D:\Desktop\lab10\node_modules\express\lib\router\layer.js:95:5)
   at next (D:\Desktop\lab10\node_modules\express\lib\router\route.js:137:13)
   at next (D:\Desktop\lab10\node_modules\express\lib\router\route.js:131:14)
   at Route.dispatch (D:\Desktop\lab10\node_modules\express\lib\router\route.js:112:3)
   at Layer.handle [as handle_request] (D:\Desktop\lab10\node_modules\express\lib\router\layer.js:95:5)
   at D:\Desktop\lab10\node_modules\express\lib\router\index.js:281:22
   at param (D:\Desktop\lab10\node_modules\express\lib\router\index.js:360:14)
   at param (D:\Desktop\lab10\node_modules\express\lib\router\index.js:371:14)
   at Function.process_params (D:\Desktop\lab10\node_modules\express\lib\router\index.js:416:3)

CodePudding user response:

Your error comes from this code:

.get((req, res) => {
    res.json(book);
});

Here you're trying to send book, but in this callback, book is out of it's scope. You can try to declare it in a higher scope or return it somehow in upper scopes

CodePudding user response:

@Molda found the error. I should be passing req.book in my response, and not book.

Correct code

.get((req, res) => {
    res.json(req.book);
});
  • Related