JpaRepository Whitelabel Error Page – This application has no explicit mapping for /error

I am trying to extend my implementation by adding a second repository (Review). However, when I try to access http://localhost:8080/api/reviews I get the above error. Can anyone spot where I’ve messed up? I’m really knew to this so no doubt I’ve made a rookie mistake.

Folder structure

ProductController:

package gerry.stockcontrol.controller;

import gerry.stockcontrol.exception.ProductNotFoundException;
import gerry.stockcontrol.model.Product;
import gerry.stockcontrol.service.ProductServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@CrossOrigin(origins = "*", allowedHeaders = "*")
@RestController
@RequestMapping("/api/products")

//http://localhost:8080/api/products
public class ProductController {

    public ProductController(ProductServiceImpl productServiceImpl) {
        this.productServiceImpl = productServiceImpl;
    }

    @Autowired
    private final ProductServiceImpl productServiceImpl;

    @GetMapping("/searchname")
    public List<Product> searchProductsByName(@RequestParam(value="name") String name){
        return productServiceImpl.findByName(name);
    }

    @GetMapping("/searchdescription")
    public List<Product> searchProductsByDescription(@RequestParam(value="description") String description){
        return productServiceImpl.findByDescription(description);
    }

    @GetMapping
    public List<Product> getAllProducts(){
        return productServiceImpl.getAllProducts();
    }

    @GetMapping("/{id}")
    public Product getProductById(@PathVariable Long id) throws ProductNotFoundException {
        return productServiceImpl.getProductById(id);
    }

    @GetMapping("/searchstocklevel")
    public List<Product> searchProductsByStockLevel(@RequestParam(value="stocklevel") int stocklevel){
        return productServiceImpl.findByStockLevel(stocklevel);
    }

    @PostMapping
    public Product createProduct(@RequestBody Product product){
        return productServiceImpl.createProduct(product);
    }

    @PutMapping("/{id}")
    public Product updateProduct(@PathVariable Long id, @RequestBody Product product) throws ProductNotFoundException{
        return productServiceImpl.updateProduct(id, product);
    }

    @DeleteMapping("{id}")
    public void deleteProduct(@PathVariable Long id) throws ProductNotFoundException
    {
        productServiceImpl.deleteProduct(id);
    }

}

ReviewController:

package gerry.stockcontrol.controller;

import gerry.stockcontrol.exception.ReviewNotFoundException;
import gerry.stockcontrol.model.Review;
import gerry.stockcontrol.service.ReviewServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@CrossOrigin(origins = "*", allowedHeaders = "*")
@RestController
@RequestMapping("/api/reviews")

//http://localhost:8080/api/reviews
public class ReviewController {

    public ReviewController(ReviewServiceImpl reviewServiceImpl) {
        this.reviewServiceImpl = reviewServiceImpl;
    }

    @Autowired
    private final ReviewServiceImpl reviewServiceImpl;

    @GetMapping
    public List<Review> getAllReviews(){
        return reviewServiceImpl.getAllReviews();
    }


    @GetMapping("/{id}")
    public Review getReviewById(@PathVariable Long id) throws ReviewNotFoundException {
        return reviewServiceImpl.getReviewById(id);

    }
}

Product Model:

package gerry.stockcontrol.model;


import com.fasterxml.jackson.annotation.JsonIgnore;

import javax.persistence.*;
import java.util.List;

@Entity
@Table(name = "products")
public class Product {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @Column(nullable = false)
    private String name;

    @Column(nullable = false)
    private String description;

    @Column(nullable = false)
    private Double price;

    @Column(nullable = false)
    private Integer stock;

    @OneToMany(mappedBy = "product")
    @JsonIgnore
    private List<Review> reviews;

    //Getters and Setters

    public Long getID(){
        return id;
    }

    public void setId(Long id)
    {
        this.id = id;
    }

    public String getName()
    {
        return name;
    }

    public void setName(String name){
        this.name = name;
    }

    public String getDescription(){
        return description;
    }

    public void setDescription(String description){
        this.description = description;
    }

    public Double getPrice(){
        return price;
    }

    public void setPrice(Double price){
        this.price = price;
    }

    public Integer getStock(){
        return stock;
    }

    public void setStock(Integer stock){
        this.stock = stock;
    }

    @Override
    public String toString()
    {
        return "Product{" +
                "id=" + id +
                ", name='" + name + ''' +
                ", description='" + description + ''' +
                ", price='" + price + ''' +
                ", stock='" + stock + ''' +
                ", reviews='" + reviews + ''' +
                '}';
    }



}

Review Model:

package gerry.stockcontrol.model;


import javax.persistence.*;

@Entity
@Table(name = "reviews")
public class Review {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @Column(nullable = false)
    private Integer rating;

    @Column(nullable = false)
    private String comment;

    @ManyToOne
    private Product product;



    public Review(Product product, int rating, String comment) {
        this.rating = rating;
        this.comment = comment;
        this.product = product;
    }

    public int getRating() {
        return rating;
    }

    public void setRating(int rating) {
        this.rating = rating;
    }

    public String getComment() {
        return comment;
    }

    public void setComment(String comment) {
        this.comment = comment;
    }


@Override
public String toString()
{
    return "Review{" +
            "id=" + id +
            ", rating='" + rating + ''' +
            ", comment='" + comment + ''' +
            '}';
}

}


ProductRepository:

package gerry.stockcontrol.repository;

import gerry.stockcontrol.model.Product;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.List;

public interface ProductRepository extends JpaRepository<Product, Long> {
     List<Product>findByNameContainingIgnoreCase(String name);
     List<Product>findByDescriptionContainingIgnoreCase(String description);
     List<Product>findByStockGreaterThanEqual(int stockLevel);
}

ReviewRepository:

package gerry.stockcontrol.repository;

import gerry.stockcontrol.model.Review;
import org.springframework.data.jpa.repository.JpaRepository;

import java.util.List;

public interface ReviewRepository extends JpaRepository<Review, Long> {
     List<Review>findByProductId(Long productId);
}

ProductServiceImpl:

package gerry.stockcontrol.service;

import gerry.stockcontrol.exception.ProductNotFoundException;
import gerry.stockcontrol.model.Product;
import gerry.stockcontrol.repository.ProductRepository;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class ProductServiceImpl {
    private final ProductRepository productRepository;

    public ProductServiceImpl(ProductRepository productRepository) {
        this.productRepository = productRepository;
    }

    public List<Product> getAllProducts() {
        return productRepository.findAll();
    }

    public Product getProductById(Long id) throws ProductNotFoundException{
        return productRepository.findById(id)
                .orElseThrow(() -> new ProductNotFoundException("Product not found with id: " + id));
    }

    public Product createProduct(Product product){
        return productRepository.save(product);
    }

    public Product updateProduct(Long id, Product product) throws ProductNotFoundException{
        Product existingProduct = getProductById(id);
        existingProduct.setName(product.getName());
        existingProduct.setDescription(product.getDescription());
        existingProduct.setPrice(product.getPrice());
        existingProduct.setStock(product.getStock());
        return productRepository.save(existingProduct);
    }

    public void deleteProduct(Long id) throws ProductNotFoundException{
        getProductById(id);
        productRepository.deleteById(id);
    }

    public List<Product> findByName(String name){
        return productRepository.findByNameContainingIgnoreCase(name);
    }

    public List<Product> findByDescription(String description){
        return productRepository.findByDescriptionContainingIgnoreCase(description);
    }

    public List<Product> findByStockLevel(int stockLevel){
        return productRepository.findByStockGreaterThanEqual(stockLevel);
    }

}

ReviewServiceImpl:

package gerry.stockcontrol.service;

import gerry.stockcontrol.exception.ProductNotFoundException;
import gerry.stockcontrol.exception.ReviewNotFoundException;
import gerry.stockcontrol.model.Product;
import gerry.stockcontrol.model.Review;
import gerry.stockcontrol.repository.ReviewRepository;
import org.springframework.stereotype.Service;
import java.util.List;

@Service
public class ReviewServiceImpl {
    private final ReviewRepository reviewRepository;

    public ReviewServiceImpl(ReviewRepository reviewRepository) {
        this.reviewRepository = reviewRepository;
    }

    public List<Review> getAllReviews() {
        return reviewRepository.findAll();
    }


    public Review getReviewById(Long id) throws ReviewNotFoundException {
        return reviewRepository.findById(id)
                .orElseThrow(() -> new ReviewNotFoundException("Product not found with id: " + id));
    }

    public List<Review> getReviewsByProductId(Long productId) {
        return reviewRepository.findByProductId(productId);

    }




}

StockControlApplication:

package gerry.stockcontrol;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class StockControlApplication {
    public static void main(String[] args)
    {
        SpringApplication.run(StockControlApplication.class, args);
    }
}

I’ve made sure the folder structure is correct re. main. I’ve pretty much just did for Review exactly as I did for Product so was expecting to be able to call http://localhost:8080/api/reviews and get back all Reviews like I did for Products.

New contributor

Tony McConville is a new contributor to this site. Take care in asking for clarification, commenting, and answering.
Check out our Code of Conduct.

Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa Dịch vụ tổ chức sự kiện 5 sao Thông tin về chúng tôi Dịch vụ sinh nhật bé trai Dịch vụ sinh nhật bé gái Sự kiện trọn gói Các tiết mục giải trí Dịch vụ bổ trợ Tiệc cưới sang trọng Dịch vụ khai trương Tư vấn tổ chức sự kiện Hình ảnh sự kiện Cập nhật tin tức Liên hệ ngay Thuê chú hề chuyên nghiệp Tiệc tất niên cho công ty Trang trí tiệc cuối năm Tiệc tất niên độc đáo Sinh nhật bé Hải Đăng Sinh nhật đáng yêu bé Khánh Vân Sinh nhật sang trọng Bích Ngân Tiệc sinh nhật bé Thanh Trang Dịch vụ ông già Noel Xiếc thú vui nhộn Biểu diễn xiếc quay đĩa Dịch vụ tổ chức tiệc uy tín Khám phá dịch vụ của chúng tôi Tiệc sinh nhật cho bé trai Trang trí tiệc cho bé gái Gói sự kiện chuyên nghiệp Chương trình giải trí hấp dẫn Dịch vụ hỗ trợ sự kiện Trang trí tiệc cưới đẹp Khởi đầu thành công với khai trương Chuyên gia tư vấn sự kiện Xem ảnh các sự kiện đẹp Tin mới về sự kiện Kết nối với đội ngũ chuyên gia Chú hề vui nhộn cho tiệc sinh nhật Ý tưởng tiệc cuối năm Tất niên độc đáo Trang trí tiệc hiện đại Tổ chức sinh nhật cho Hải Đăng Sinh nhật độc quyền Khánh Vân Phong cách tiệc Bích Ngân Trang trí tiệc bé Thanh Trang Thuê dịch vụ ông già Noel chuyên nghiệp Xem xiếc khỉ đặc sắc Xiếc quay đĩa thú vị
Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa
Thiết kế website Thiết kế website Thiết kế website Cách kháng tài khoản quảng cáo Mua bán Fanpage Facebook Dịch vụ SEO Tổ chức sinh nhật