0

I am working on a online food ordering application. On that project I was trying to fetch the product information from the frontend using fetch method. But it was an unsuccessful attempt and I didn't get the information. So as a beginner I am looking for someone who can help me on this problem to completer this project by solving the error.

productController.js

const productController = require("express").Router();
const Product = require("../models/Product");
const {
  verifyToken,
  verifyTokenAdmin,
} = require("../middlewares/authmiddleware");

// get all
productController.get("/", verifyToken, async (req, res) => {
  try {
    const products = await Product.find(req.query);
    return res.status(200).json(products);
  } catch (error) {
    console.error(error);
  }
});

// get one
productController.get("/find/:id", verifyToken, async (req, res) => {
  try {
    const productId = req.params.id;
    const product = await Product.findById(productId);
    if (!product) {
      return res.status(500).json({ msg: "No product with such id!" });
    }
    return res.status(200).json(product);
  } catch (error) {
    console.error(error);
  }
});

// create product
productController.post("/", verifyTokenAdmin, async (req, res) => {
  try {
    const newProduct = await Product.create({ ...req.body });
    return res.status(201).json(newProduct);
  } catch (error) {
    console.error(error);
  }
});

module.exports = productController;

FoodCatalog.js

import React, { useState, useEffect } from "react";
import { NavLink, useLocation } from "react-router-dom";
import { useSelector } from "react-redux";
import "./FoodCatalog.css";

const FoodCatalog = () => {
  const [filteredFoods, setFilteredFoods] = useState([]);
  const location = useLocation();
  const foodEndpoint = location.pathname.split("/")[2];
  const { token } = useSelector((state) => state.auth);

  useEffect(() => {
    const fetchFoodType = async () => {
      const res = await fetch(
        `http://localhost:8080/product?category=${foodEndpoint}`,
        {
          headers: {
            Authorization: `Bearer ${token}`,
          },
          method: "GET",
        }
      );

      const data = await res.json();
      setFilteredFoods(data);
    };
    fetchFoodType();
  }, [foodEndpoint, token]);

  return (
    <div className="food-catalog-container">
      <div className="food-catalog-wrapper">
        {filteredFoods?.length !== 0 && (
          <h2 className="food-catalog-title">
            The best {foodEndpoint} in the region
          </h2>
        )}
        <div className="food-catalog-foods">
          {filteredFoods.length !== 0 ? (
            filteredFoods.map((f) => (
              <NavLink to={`/food/${f._id}`} key={f._id} className="food">
                <div className="food-catalog-imgContainer">
                  <img
                    src={`/public/images/${f?.img}`}
                    alt=""
                    className="food-catalog-foodImg"
                  />
                </div>
                <div className="food-catalog-foodDetails">
                  <h4 className="food-catalog-foodTitle">{f?.title}</h4>
                  <span className="food-catalog-price">
                    <span>$</span> {f?.price}
                  </span>
                </div>
              </NavLink>
            ))
          ) : (
            <h1 className="food-catalog-noQuantity">
              No {foodEndpoint} right now
            </h1>
          )}
        </div>
      </div>
    </div>
  );
};

export default FoodCatalog;

Product.js

const mongoose = require("mongoose");

const ProductSchema = new mongoose.Schema({
  title: {
    type: String,
    required: true,
    min: 4,
  },
  desc: {
    type: String,
    required: true,
    min: 8,
  },
  price: {
    type: Number,
    required: true,
  },
  img: {
    type: String,
    required: true,
  },
  review: {
    type: Number,
    required: true,
  },
  category: {
    type: String,
    required: true,
  },
});

module.exports = mongoose.model("Product", ProductSchema);

It was showing error with the status code 304. And I couldn't figure out the problem that where have I done wrong.

The error: GET /product?category=burger 304 277.474 ms - -

  • Show `/product` endpoint handler – Aleksandar May 05 '23 at 08:03
  • you may find it in productController.js –  May 05 '23 at 08:47
  • 304 is not an error, per se, but rather it is acknowledging to the requester that the resource has not changed and the requester can save time and bandwidth by using its previously cached version of the resource. The question [NodeJS/express: Cache and 304 status code](https://stackoverflow.com/q/18811286/1563833) has more info. – Wyck May 05 '23 at 14:41

1 Answers1

0

You can add a timestamp inside the URL string as a query parameter.

This will make the unique URL for every request, with this the browser will make a new request to the server, even if the response was previously cached

Like this below :-

const timestamp = Date.now();
const res = await fetch(
  `http://localhost:8080/product?category=${foodEndpoint}&timestamp=${timestamp}`,
  {
    headers: {
      Authorization: `Bearer ${token}`,
    },
    method: "GET",
  }
);

Updated code of productController.get()

productController.get("/", verifyToken, async (req, res) => {
  try {
    const products = await Product.find(req.query);
    res.setHeader("Cache-Control", "no-store");
    return res.status(200).json(products);
  } catch (error) {
    console.error(error);
  }
});
Abhishek Garg
  • 207
  • 1
  • 5
  • After Using this, it shows the response status of 201 but it is not show the output which it should show according to the FoodCatalog.js page. Rather it shows: that there is No burger . But in the status it show the burger id . –  May 05 '23 at 05:54
  • @MahadiHasan, okay m I just update the code, please go through again, Updated code of productController.get() – Abhishek Garg May 05 '23 at 14:17