Home > Net >  Why does the Rest Controller give an error : "No adapter for handler"?
Why does the Rest Controller give an error : "No adapter for handler"?

Time:12-06

I want to make a simple example of spring interacting with MongoDB. I have a product model:

@NoArgsConstructor
@ToString(exclude = {"id"})
public class Product {
    @Id
    private String id;
    private String name;
    private Integer price;
    private LocalDateTime localDateTime;

    public Product(String name, Integer price, LocalDateTime localDateTime) {
        this.name = name;
        this.price = price;
        this.localDateTime = localDateTime;
    }
}

a simple repository and a service for working with DB:

public interface productRepository extends MongoRepository<Product,String> {
    Product findByName(String name);
    List<Product> findByPrice(Integer price);
}

Service:

@AllArgsConstructor
@Service
public class productServiceImpl implements productService<Product>{

    productRepository repository;

    @Override
    public Product saveOrUpdateProduct(Product product) {
        return repository.save(product);
    }

    @Override
    public List<Product> findAll() {
        return repository.findAll();
    }

    @Override
    public Product findByName(String name) {
        return repository.findByName(name);
    }

    @Override
    public List<Product> findByPrice(Integer price) {
        return repository.findByPrice(price);
    }
}

When I check the work of findAll , everything works fine .But when working with Rest Service:


@RestController("/products")
@AllArgsConstructor
public class productRestController {


    productServiceImpl productService;

    @GetMapping("/")
    public List<Product> getAllProducts(){
        System.out.println("*********************inside get all ***********************");
        return productService.findAll();
    }

    @GetMapping("/products/{name}")
    public Product getProductsByName(@PathVariable("name")Optional<String> name ){
        if(name.isPresent())
            return productService.findByName(name.get());
        else return null;
    }

    @GetMapping("/products/{price}")
    public List<Product> getProductsByPrice(@PathVariable("price")Optional<Integer> price ){
        if(price.isPresent())
            return productService.findByPrice(price.get());
        else return null;
    }

    @PostMapping("/save")
    public ResponseEntity<?> saveProduct(@RequestBody Product product){
        Product p = productService.saveOrUpdateProduct(product);
        return new ResponseEntity(p, HttpStatus.OK);
    }

}

and call http://localhost:8080/products/ i get an error:

No adapter for handler [com.example.MongoTesr.REST.productRestController@6e98d209]: 
The DispatcherServlet configuration needs to include a HandlerAdapter that supports this handler

I tried to Google but did not find an error and a solution to the problem.Can you tell me what I did wrong?

application.propertires:

spring.data.mongodb.authentication-database=admin
spring.data.mongodb.username=root
spring.data.mongodb.password=rootpassword
spring.data.mongodb.database=test_db
spring.data.mongodb.port=27017
spring.data.mongodb.host=localhost

CodePudding user response:

@RestController("/products") doesn't do what you think!

/products is not a path or mapping to it or similar, but just:

The value may indicate a suggestion for a logical component name, to be turned into a Spring bean in case of an autodetected component.

From RestController.value javadoc.


If we want to structure our path mappings on class level, we achieve it with:

...
@RestController  // resp. @Controller
@RequestMapping("/products") //(resp. relative: "products")
public class ...

See also: Using @RequestMapping on class level

  • Related