0

I'm trying to create a basic nodejs API(No Framework)

My Folder Structure is

controllers
     productController.js
models
     productModels.js 
data
   products.js
node_modules
package.json
package-lock.json
server.js

I'm trying to send product data to the client associated with a particular product id. But the problem that I'm facing here is in the productModel.js file. Inside that file, I'm unable to filter out the particular product with an id. Once I use the id in the array.prototype.find() method as a conditional, it doesn't seem to recognize the value of the id. I wonder why?

products.js file

export const products =  [
    {
      "userId": 1,
      "id": 1,
      "title": "sunt aut facere repellat provident occaecati excepturi optio reprehenderit",
      "body": "quia et suscipit\nsuscipit recusandae consequuntur expedita et cum\nreprehenderit molestiae ut ut quas totam\nnostrum rerum est autem sunt rem eveniet architecto"
    },
    {
      "userId": 1,
      "id": 2,
      "title": "qui est esse",
      "body": "est rerum tempore vitae\nsequi sint nihil reprehenderit dolor beatae ea dolores neque\nfugiat blanditiis voluptate porro vel nihil molestiae ut reiciendis\nqui aperiam non debitis possimus qui neque nisi nulla"
    },
    {
      "userId": 1,
      "id": 3,
      "title": "ea molestias quasi exercitationem repellat qui ipsa sit aut",
      "body": "et iusto sed quo iure\nvoluptatem occaecati omnis eligendi aut ad\nvoluptatem doloribus vel accusantium quis pariatur\nmolestiae porro eius odio et labore et velit aut"
    },
    {
      "userId": 1,
      "id": 4,
      "title": "eum et est occaecati",
      "body": "ullam et saepe reiciendis voluptatem adipisci\nsit amet autem assumenda provident rerum culpa\nquis hic commodi nesciunt rem tenetur doloremque ipsam iure\nquis sunt voluptatem rerum illo velit"
    }]

productController.js file

import {findAll, findById} from '../models/productModel.js'
export const getProduct = async (req, res, id) => {
    try{
        const product = await findById(id)

        if(!product){
            res.end(JSON.stringify({message: 'Prdouct not found'}))

        }else{
            res.writeHead(200, { 'Content-Type': 'application/json' });
            res.end(JSON.stringify(product));
        }

    }catch(err){
        console.log(err)
    }
}

productModel.js file

import {products} from '../data/products.js'
export const findById = (id) => {
    const promise = new Promise((resolve, reject) => {       
        setTimeout(() => {
            console.log(id)
            const product = products.find(p => p.id === id)
            resolve(product)
            // reject('SERVER ERROR')
        }, 1000) 
    })
    return promise
}

server.js file

import http from 'http'
import { getProducts, getProduct } from './controllers/productControllers.js';

const server = http.createServer((req, res) => {
    if(req.url === '/api/products' && req.method === 'GET'){
        getProducts(req, res)
    }else if(req.url.match(/\/api\/products\/([0-9]+)/) && req.method === 'GET'){
        const id = req.url.split('/')[3]
        getProduct(req, res, id)
    }
    else{
        res.writeHead(200, { 'Content-Type': 'text/html' });
        res.end("Not found");
    }
});

const port = process.env.PORT || 8000
  
server.listen(port, () => {console.log(`Server running on port ${8000}`)});
Nishant Kumar
  • 691
  • 1
  • 11
  • 31

2 Answers2

2

Seems to be that you're comparing a string with a number. Therefore "1" === 1 // false.

Try converting the id from the path to an Int using parseInt() and then pass it to your function

const id = parseInt(req.url.split('/')[3], 10)
Japsz
  • 785
  • 6
  • 14
  • Thank you so much I wasn't expecting any help but oh my god you guys are so helpful. Thank you so much from the core of my heart. I'd have never figured this out on my own. could you please tell me if there is any way to debug these kinds of mistakes in vs code? – Nishant Kumar Oct 26 '21 at 16:35
  • 1
    Try using [Typescript](https://www.typescriptlang.org/), is the only way to be aware and avoid these nuisances javascript has – Japsz Oct 26 '21 at 16:40
2

Your id you get from req.url.split('/')[3] is a string, but the product ids in your model are numbers. And you are comparing with === which will return false if the two operands have different types. Thus your comparison will always return false and you won't find a product. Use

const id = +(req.url.split('/')[3])

instead, which will make id a number.

derpirscher
  • 14,418
  • 3
  • 18
  • 35
  • You are a hero and a true master, thank you so much for doing so much effort in looking at my code taking your precious time, I was scratching my head yesterday. I'm such an ass, I'm so ashamed of myself. Looks I'm not meant for coding. These are the reasons I'm not getting any job, I guess. – Nishant Kumar Oct 26 '21 at 16:33
  • could you please tell me if there is any way to debug these kinds of mistakes in vs code? – Nishant Kumar Oct 26 '21 at 16:35
  • 1
    Of course there is: https://code.visualstudio.com/docs/nodejs/nodejs-debugging – derpirscher Oct 26 '21 at 16:43