error:
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'requestMappingHandlerMapping' defined in class path resource [org/springframework/boot/autoconfigure/web/WebMvcAutoConfiguration$EnableWebMvcConfiguration.class]: Invocation of init method failed; nested exception is java.lang.IllegalStateException: Ambiguous mapping. Cannot map 'searchController' method
public java.lang.String softuniBlog.controller.SearchController.search(java.lang.String,org.springframework.ui.Model)
to {[/search]}: There is already 'searchController' bean method
public java.lang.String softuniBlog.controller.SearchController.index() mapped.
**I`m trying to build search engine for my blog and have 3 questions.
1) Why In application properties last 3 rows are "can not resolve"
2) How can I fix the error I have, app is working but when try url /search?q=someText it trows exception:
[Handler dispatch failed; nested exception is java.lang.NoSuchMethodError: org.hibernate.engine.spi.SessionDelegatorBaseImpl.(Lorg/hibernate/engine/spi/SessionImplementor;)V] with root cause
java.lang.NoSuchMethodError: org.hibernate.engine.spi.SessionDelegatorBaseImpl.(Lorg/hibernate/engine/spi/SessionImplementor;)V
3) How can take search query from input form instead from url
please check the code:
search input box
<div id="wrap">
<form action="" autocomplete="on">
<input id="search" name="search" type="text" placeholder="What're we looking for ?"></input>
<input id="search_submit" value="Rechercher" type="submit"></input>
</form>
</div>
Article controller
package softuniBlog.controller;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.security.authentication.AnonymousAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.multipart.MultipartFile;
import softuniBlog.bindingModel.ArticleBindingModel;
import softuniBlog.entity.Article;
import softuniBlog.entity.User;
import softuniBlog.repository.ArticleRepository;
import softuniBlog.repository.UserRepository;
import java.io.File;
import java.io.IOException;
import java.util.Arrays;
#Controller
public class ArticleConstroller {
#Autowired
private ArticleRepository articleRepository;
#Autowired
private UserRepository userRepository;
#GetMapping("/article/create")
#PreAuthorize("isAuthenticated()")
public String create(Model model){
model.addAttribute("view", "/article/create");
return "base-layout";
}
#PostMapping("/article/create")
#PreAuthorize("isAuthenticated()")
public String createProcess(ArticleBindingModel articleBindingModel){
UserDetails user = (UserDetails) SecurityContextHolder
.getContext()
.getAuthentication()
.getPrincipal();
User userEntity = this.userRepository.findByEmail(user.getUsername());
String databasePathImage = null;
String[] allowedContentTypes = {
"image/png",
"image/jpg",
"image/jpeg"
};
boolean isContentTypeAllowed =
Arrays.asList(allowedContentTypes)
.contains(articleBindingModel.getImage().getContentType());
if(isContentTypeAllowed){
String imagesPath = "\\src\\main\\resources\\static\\img\\";
String imagePathRoot = System.getProperty("user.dir");
String imageSaveDirectory = imagePathRoot + imagesPath;
String fileName = articleBindingModel.getImage().getOriginalFilename();
String savePath = imageSaveDirectory + fileName;
File imageFile = new File(savePath);
try {
articleBindingModel.getImage().transferTo(imageFile);
databasePathImage = "/img/" + fileName;
} catch (IOException e) {
System.out.println(e.getMessage());
}
}
Article articleEntity = new Article(
articleBindingModel.getTitle(),
articleBindingModel.getContent(),
userEntity,
databasePathImage
);
this.articleRepository.saveAndFlush(articleEntity);
return "redirect:/";
}
#GetMapping("/article/edit/{id}")
#PreAuthorize("isAuthenticated()")
public String edit(#PathVariable Integer id, Model model){
if(!this.articleRepository.exists(id)){
return "redirect:/";
}
Article article = this.articleRepository.findOne(id);
if(!this.isUserAuthorOrAdmin(article)){
return "redirect:/";
}
model.addAttribute("view", "article/edit");
model.addAttribute("article", article);
return "base-layout";
}
#GetMapping("/article/{id}")
public String details(Model model, #PathVariable Integer id) {
if(!this.articleRepository.exists(id)){
return "redirect:/";
}
if(!(SecurityContextHolder.getContext().getAuthentication()
instanceof AnonymousAuthenticationToken)){
UserDetails principal = (UserDetails) SecurityContextHolder.getContext()
.getAuthentication().getPrincipal();
User entityUser = this.userRepository.findByEmail(principal.getUsername());
model.addAttribute("user", entityUser);
}
Article article = this.articleRepository.findOne(id);
model.addAttribute("view", "article/details");
model.addAttribute("article", article);
return "base-layout";
}
#PostMapping("/article/edit/{id}")
#PreAuthorize("isAuthenticated()")
public String editProcess(#PathVariable Integer id, ArticleBindingModel articleBindingModel) {
if(!this.articleRepository.exists(id)){
return "redirect:/";
}
Article article = this.articleRepository.findOne(id);
if(!this.isUserAuthorOrAdmin(article)){
return "redirect:/";
}
article.setTitle(articleBindingModel.getTitle());
article.setContent(articleBindingModel.getContent());
this.articleRepository.saveAndFlush(article);
return "redirect:/article/" + article.getId();
}
#GetMapping("/article/delete/{id}")
#PreAuthorize("isAuthenticated()")
public String delete(#PathVariable Integer id, Model model){
if(!this.articleRepository.exists(id)){
return "redirect:/";
}
Article article = this.articleRepository.findOne(id);
if(!this.isUserAuthorOrAdmin(article)){
return "redirect:/";
}
model.addAttribute("article", article);
model.addAttribute("view", "article/delete");
return "base-layout";
}
#PostMapping("/article/delete/{id}")
#PreAuthorize("isAuthenticated()")
public String deleteProcess(#PathVariable Integer id) {
if(!this.articleRepository.exists(id)){
return "redirect:/";
}
Article article = this.articleRepository.findOne(id);
if(!this.isUserAuthorOrAdmin(article)){
return "redirect:/";
}
this.articleRepository.delete(article);
return "redirect:/";
}
private boolean isUserAuthorOrAdmin(Article article){
UserDetails user = (UserDetails) SecurityContextHolder
.getContext()
.getAuthentication()
.getPrincipal();
User userEntity = this.userRepository.findByEmail(user.getUsername());
return userEntity.isAdmin() || userEntity.isAuthor(article);
}
}
Article model
import javax.validation.constraints.NotNull;
import javax.persistence.*;
import java.util.Date;
#Entity
#Indexed
#Table(name = "articles")
public class Article {
private Integer id;
#Field(index = Index.YES, analyze = Analyze.YES, store = Store.NO)
#NotNull
private String title;
#Field(index = Index.YES, analyze = Analyze.YES, store = Store.NO)
#NotNull
private String content;
private Date date;
private User author;
private String imagePath;
public Article(String title, String content, User author, String imagePath) {
this.title = title;
this.content = content;
this.author = author;
this.imagePath = imagePath;
this.date = new Date();
}
public Article(){
}
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
#Column(name = "title", nullable = false)
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
#Column(name = "content", nullable = false, columnDefinition = "text")
public String getContent() {
return content;
}
public void setContent(String content) {
this.content = content;
}
#Column(name = "date", nullable = true)
public Date getDate() {
return date;
}
public void setDate(Date date) {
this.date = date;
}
#ManyToOne()
#JoinColumn(nullable = false, name = "authorId")
public User getAuthor() {
return author;
}
public void setAuthor(User author) {
this.author = author;
}
#Transient
public String getSummary(){
return this.getContent().substring(0, this.getContent().length()/2) + "...";
}
public String getImagePath() {
return imagePath;
}
public void setImagePath(String imagePath) {
this.imagePath = imagePath;
}
}
Application properties
# Database connection with the given database name
spring.datasource.url = jdbc:mysql://localhost:3306/javablog
# Username and password
spring.datasource.username = root
spring.datasource.password =
# Show or not log for each sql query
spring.jpa.show-sql = true
# Hibernate ddl auto (create, create-drop, update): with "update" the database
# schema will be automatically updated accordingly to java entities found in
# the project
# Using "create" will delete and recreate the tables every time the project is started
spring.jpa.hibernate.ddl-auto = update
# Naming strategy
spring.jpa.hibernate.naming.strategy = org.hibernate.cfg.ImprovedNamingStrategy
# Allows Hibernate to generate SQL optimized for a particular DBMS
spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.MySQL5Dialect
spring.jpa.properties.hibernate.search.default.directory_provider = filesystem
# Using the filesystem DirectoryProvider you also have to specify the default
# base directory for all indexes (make sure that the application have write
# permissions on such directory)
spring.jpa.properties.hibernate.search.default.indexBase = ../java/softuniBlog/lucene/indexes
#Turn off Thymeleaf cache
spring.thymeleaf.cache = false
POM XML
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>softuni.blog</groupId>
<artifactId>blog</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>Blog</name>
<description>Blog Project from the Software Technologies Course</description>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.4.2.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.thymeleaf.extras</groupId>
<artifactId>thymeleaf-extras-springsecurity4</artifactId>
<version>2.1.2.RELEASE</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-search-orm</artifactId>
<version>5.7.0.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-search-infinispan</artifactId>
<version>5.7.0.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-search-elasticsearch</artifactId>
<version>5.7.0.Final</version>
</dependency>
<dependency>
<groupId>org.infinispan</groupId>
<artifactId>infinispan-directory-provider</artifactId>
<version>8.2.4.Final</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.hibernate/hibernate-validator -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator</artifactId>
<version>6.0.0.Alpha2</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>`enter code here`
</project>
I honestly don't understand you other questions (and you probably should ask them separately), but for question 2 I can tell you that a NoSuchMethodError is very likely to be caused by your using an incompatible version of Hibernate ORM with Hibernate Search.
To sum up:
Hibernate Search 5.7.0 and later should be used with Hibernate ORM 5.2.3 or later.
Hibernate Search 5.6.x and earlier should be used with Hibernate ORM 5.1.x or earlier.
EDIT: Your pom appears to contain a dependency to hibernate-entitymanager, and you didn't set the version for this dependency, so I suspect you're getting some older version. hibernate-entitymanager isn't required to use JPA starting with Hibernate ORM 5.2, so you should try to remove it.
Related
some strange issue has shown up, in the business model I use the list of addresses that cannot be empty or null, but each field in the object address cannot be null or empty either. But when I send a request with one of the fields empty, the request will pass to the repository, which shouldn't happen. Instead of passing a request, the server should return an internal server error.
Address object:
#Data
#NoArgsConstructor
public class Address {
#NotEmpty(message = "Street may not be empty")
#Size(min = 2, max = 256)
private String street;
#NotEmpty(message = "Number may not be empty")
#Size(min = 1, max = 5)
private String number;
#NotEmpty(message = "Postal code may not be empty")
#Field("postal_code")
#JsonProperty("postal_code")
#Size(min = 5, max = 6)
private String postalCode;
#NotEmpty(message = "City may not be empty")
#Size(min = 2, max = 256)
private String city;
#NotEmpty(message = "Province may not be empty")
#Size(min = 2, max = 256)
private String province;
#NotEmpty(message = "Country may not be empty")
#Size(min = 2, max = 256)
private String country;
}
Business object which contains list of addresses:
#Data
#NoArgsConstructor
#Document(collection = "businesses")
public class Business {
#Id
private String id;
#NotBlank
#Size(max = 64)
private String name;
#Field("created_at")
private Date createdAt;
#Field("updated_at")
private Date updatedAt;
private Boolean active;
#DBRef
private User owner;
#Valid
private List<Address> addresses;
public Business(String name, User owner, List<Address> addresses, Date createdAt, Date updatedAt, Boolean active) {
this.name = name;
this.owner = owner;
this.addresses = addresses;
this.createdAt = createdAt;
this.updatedAt = updatedAt;
this.active = active;
}
public Business(String name, User owner, List<Address> addresses, Date updatedAt, Boolean active) {
this.name = name;
this.owner = owner;
this.addresses = addresses;
this.updatedAt = updatedAt;
this.active = active;
}
}
And in the end, service:
#Override
public ResponseEntity<?> createBusiness(CreateBusinessRequest request, String token) throws RuntimeException {
Optional<User> user = userRepository.findByUsername(jwtUtils.getUserNameFromJwtToken(token.substring(7)));
if(businessRepository.existsByName(request.getName())) {
throw new ItemAlreadyExistsException("Business with " + request.getName() + " already exists!");
}
if(user.isEmpty()) {
throw new NotFoundException("User with "+ user.get().getUsername() +" does not exist!");
}
if(request.getAddresses().isEmpty() || request.getAddresses() == null) {
throw new InvalidInputException("Address is empty!");
}
Business business = new Business(
request.getName(),
user.get(),
request.getAddresses(),
new Date(),
new Date(),
true
);
businessRepository.save(business);
return ResponseEntity.ok(business);
}
Controller:
#PreAuthorize("hasRole('USER') or hasRole('MODERATOR') or hasRole('ADMIN')")
#PostMapping("/create")
public ResponseEntity<?> createBusiness(#Valid #RequestBody CreateBusinessRequest request, #RequestHeader (name="Authorization") String token) {
return businessService.createBusiness(request, token);
}
CreateBusinessRequest request model
#Data
public class CreateBusinessRequest {
#NotNull
private String name;
#Valid
private List<Address> addresses;
}
Request:
{
"name": "Test business",
"addresses": [
{
"street": "",
"number": "100",
"postal_code": "84104",
"city": "Test city",
"province": "Test",
"country": "Slovakia"
}
]
}
Pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.6</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.ratify</groupId>
<artifactId>backend</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>backend</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>11</java.version>
<json.webtoken.version>0.9.1</json.webtoken.version>
<lombok.version>1.18.22</lombok.version>
<jakarta.xml.bind.version>2.3.2</jakarta.xml.bind.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-mongodb</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>${json.webtoken.version}</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
</dependency>
<dependency>
<groupId>jakarta.xml.bind</groupId>
<artifactId>jakarta.xml.bind-api</artifactId>
<version>${jakarta.xml.bind.version}</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
I hope that I explained my issue correctly.
Is there any solution to this issue?
Thanks in advance.
My guess is that you are missing one key dependency:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
Per this question I recommend adding the #Valid annotation (javax.validation.Valid) to the addresses property of the Business class. Also see the example here
EDIT:
After adding the annotation you can use BindingResult for controller validation. An example would like this:
#PostMapping("/")
public String doSomething(#Valid #RequestBody SomeModel model, BindingResult bindingResult)
{
if (bindingResult.hasErrors())
{
// handle validation error
}
}
To fully configure method level security you need to add the following annotation/class:
#Configuration
#EnableGlobalMethodSecurity(
prePostEnabled = true,
securedEnabled = true,
jsr250Enabled = true)
public class MethodSecurityConfig extends GlobalMethodSecurityConfiguration {
}
This will turn on validation of your service methods. As mentioned earlier, you can add BindingResult to your controller and check for errors in the controller if needed.
I am studying Spring Boot and I want to create a Rest Controller, and using a sql database, but there is a problem when I start the project :
Error:
(the error text is great I will leave the link)
And code:
OrderController.java
package ***;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.List;
import java.util.Map;
import java.util.Optional;
#RestController
public class OrderController {
#Autowired
private OrderRepository orderRep;
#GetMapping("/")
public List<Order> index(){
return (List<Order>) orderRep.findAll();
}
#GetMapping("/{id}")
public Order show(#PathVariable int id){
Optional<Order> orderId= orderRep.findById(id);
Order order = orderId.get();
return order;
}
#PostMapping("/search")
public List<Order> search(#RequestBody Map<String, String> body){
String searchItem = body.get("item");
return orderRep.findByTitleContainingOrContentContaining(searchItem);
}
#PostMapping("/")
public Order create(#RequestBody Map<String, String> body){
String item = body.get("item");
int price = Integer.parseInt(body.get("price"));
int quantity = Integer.parseInt(body.get("quantity"));
return orderRep.save(new Order(item, price,quantity));
}
#PutMapping("/{id}")
public Order update(#PathVariable String id, #RequestBody Map<String, String> body){
int orderId = Integer.parseInt(id);
// getting blog
Optional<Order> order = orderRep.findById(orderId);
order.get().setItem(body.get("item"));
order.get().setPrice(Integer.parseInt(body.get("price")));
order.get().setQuantity(Integer.parseInt("quantity"));
return orderRep.save(order.get());
}
#DeleteMapping("/{id}")
public boolean delete(#PathVariable int id){
//int orderId = Integer.parseInt(id);
orderRep.deleteById(id);
return true;
}
}
Order.java
package ***;
import javax.persistence.*;
#Entity
#Table(name = "orders")
public class Order {
//Fields
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private int id;
#Column(name = "item")
private String item;
#Column(name = "price")
private int price;
#Column(name = "quantity")
private int quantity;
//Constructors
public Order() { }
public Order(String item, int price, int quantity) {
this.setItem(item);
this.setPrice(price);
this.setQuantity(quantity);
}
public Order(int id, String item, int price, int quantity) {
this.setId(id);
this.setItem(item);
this.setPrice(price);
this.setQuantity(quantity);
}
//Object to string data
#Override
public String toString() {
return "Order{" +
"id=" + getId() +
", item='" + getItem() + '\'' +
", price='" + getPrice() + '\'' +
", price='" + getQuantity() + '\'' +
'}';
}
//Getters & Setters
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getItem() {
return item;
}
public void setItem(String item) {
this.item = item;
}
public int getPrice() {
return price;
}
public void setPrice(int price) {
this.price = price;
}
public int getQuantity() {
return quantity;
}
public void setQuantity(int quantity) {
this.quantity = quantity;
}
}
OrderRepository.java
package ***;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.repository.CrudRepository;
import org.springframework.stereotype.Repository;
import java.util.List;
#Repository
public interface OrderRepository extends CrudRepository<Order, Integer> {
// custom query to search to blog post by title or content
List<Order> findByTitleContainingOrContentContaining(String item);
}
application.properties
spring.jpa.hibernate.ddl-auto=update
spring.datasource.url=jdbc:mysql://${MYSQL_HOST:localhost}:3306/testvoy?useUnicode=true&serverTimezone=UTC&useSSL=true&verifyServerCertificate=false
spring.datasource.username=root
spring.datasource.password=
spring.datasource.driver-class-name =com.mysql.jdbc.Driver
#spring.jpa.show-sql: true
pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.5</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.test</groupId>
<artifactId>project</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>project</name>
<description>project</description>
<properties>
<java.version>11</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.restdocs</groupId>
<artifactId>spring-restdocs-mockmvc</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.asciidoctor</groupId>
<artifactId>asciidoctor-maven-plugin</artifactId>
<version>1.5.8</version>
<executions>
<execution>
<id>generate-docs</id>
<phase>prepare-package</phase>
<goals>
<goal>process-asciidoc</goal>
</goals>
<configuration>
<backend>html</backend>
<doctype>book</doctype>
</configuration>
</execution>
</executions>
<dependencies>
<dependency>
<groupId>org.springframework.restdocs</groupId>
<artifactId>spring-restdocs-asciidoctor</artifactId>
<version>${spring-restdocs.version}</version>
</dependency>
</dependencies>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
I would be grateful for any help, thanks in advance
If you check the error, you can see that it comes from there:
List<Order> findByTitleContainingOrContentContaining(String item);
and if you read more closely to the error, you will see:
No property title found for type Order!;
inside here:
Caused by: org.springframework.data.repository.query.QueryCreationException: Could not create query for public abstract java.util.List com.test.project.OrderRepository.findByTitleContainingOrContentContaining(java.lang.String)! Reason: Failed to create query for method public abstract java.util.List com.test.project.OrderRepository.findByTitleContainingOrContentContaining(java.lang.String)! No property title found for type Order!; nested exception is java.lang.IllegalArgumentException: Failed to create query for method public abstract java.util.List com.test.project.OrderRepository.findByTitleContainingOrContentContaining(java.lang.String)! No property title found for type Order!
Infact, if you check your model, there is no title property
CONTROLLER CLASS CODE.
#GetMapping("/admin/home")
public String adhomePage(#ModelAttribute("schoolModel") SchoolModel school, Model model) {
return "admin/home";
}
#PostMapping("/admin/saveschool")
public String saveSchool(#Valid #ModelAttribute("schoolModel") SchoolModel schoolModel, BindingResult result) {
System.out.println(schoolModel.toString()+">>>>>>>>>>>>>>>>>>>>");
System.out.println(result.hasErrors()+"RESULT HASE ERROR");
System.out.println(result.getAllErrors().toString());
if (result.hasErrors()) {
System.out.println("ERROR");
System.out.println(result.getAllErrors().toString());
}
return "admin/home";
}
MODEL CLASS CODE
package com.gatepass.web.model;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.Size;
import org.springframework.lang.NonNull;
public class SchoolModel {
#NotEmpty(message = "User's name cannot be empty.")
#NotBlank()
#NonNull()
#Size(min=2, max=3)
private Long id;
#NotEmpty(message = "User's name cannot be empty.")
#Size(min=2, max=2)
private String name;
#NotEmpty(message = "User's name cannot be empty.")
#Size(min=2, max=2)
private String email;
#NotEmpty(message = "User's name cannot be empty.")
#Size(min=2, max=30)
private String mobileNumber;
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 getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getMobileNumber() {
return mobileNumber;
}
public void setMobileNumber(String mobileNumber) {
this.mobileNumber = mobileNumber;
}
#Override
public String toString() {
return "SchoolModel [id=" + id + ", name=" + name + ", email=" + email + ", mobileNumber=" + mobileNumber + "]";
}
}
HTML CODE
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<link th:href="#{/css/style.css}" rel="stylesheet" />
<title>Insert title here</title>
</head>
<body>
<h1>HOME PAGE VIEW FOR ADMIN</h1>
<form th:action="#{/logout}" method="post">
<input type="submit" value="logout">
<input
type="hidden"
th:name="${_csrf.parameterName}"
th:value="${_csrf.token}" />
</form>
<br></br>
<form th:action="#{/admin/saveschool}" th:object="${schoolModel}" method="post">
<input type="text" th:field="*{id}">
<input type="text" th:field="*{name}">
<input type="text" th:field="*{email}">
<input type="text" th:field="*{mobileNumber}">
<br></br>
<input type="submit" value="submit"/>
</form>
</body>
</html>
I am inserting a null value but the validation does not working I don't understand what is the issue I tried #validate also but it not working.
I am new to spring boot please help me out with this problem.
I am trying to add validation rules in the spring boot application I have created a form that contains the school object and this school object is mapped with modelAttribute.
so when I am submitting the post request it should validate the rules which I added in SchoolModel class but it's not working school model have the data but it not validate the data and the binding result have a false result in hase error
new updated code after comments..........
XML FILE
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.2</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.gatepass.web</groupId>
<artifactId>gatepass</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>GatePassSystem</name>
<description>A project where student will register and they will get their gate pass for outside visiting</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>javax.validation</groupId>
<artifactId>validation-api</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
Model CLASS
package com.gatepass.web.model;
import javax.validation.Valid;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.Size;
#Valid
public class SchoolModel {
private Long id;
#Valid
#NotEmpty(message = "User's name cannot be empty.")
#Size(min=2, max=2)
private String name;
#Valid
#NotEmpty(message = "User's name cannot be empty.")
#Size(min=2, max=2)
private String email;
#Valid
#NotEmpty(message = "User's name cannot be empty.")
#Size(min=2, max=30)
private String mobileNumber;
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 getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getMobileNumber() {
return mobileNumber;
}
public void setMobileNumber(String mobileNumber) {
this.mobileNumber = mobileNumber;
}
#Override
public String toString() {
return "SchoolModel [id=" + id + ", name=" + name + ", email=" + email + ", mobileNumber=" + mobileNumber + "]";
}
}
CONTROLLER CLASS
package com.gatepass.web.controller;
import javax.validation.Valid;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PostMapping;
import com.gatepass.web.model.SchoolModel;
import com.gatepass.web.repo.RoleJpa;
#Validated
#Controller
public class WelcomeController {
#Autowired
RoleJpa roleJpa;
#GetMapping("/user/home")
public String ushomePage() {
System.out.println(SecurityContextHolder.getContext().getAuthentication().toString()+"---USER HOME");
//Optional<Role> r = roleJpa.findById(1L);
return "user/home";
}
#GetMapping("/admin/home")
public String adhomePage(#ModelAttribute("schoolModel") SchoolModel school, Model model) {
return "admin/home";
}
#PostMapping("/admin/saveschool")
public String saveSchool(#Valid #ModelAttribute("schoolModel") SchoolModel schoolModel, BindingResult result) {
System.out.println(schoolModel.toString()+">>>>>>>>>>>>>>>>>>>>");
System.out.println(result.hasErrors()+"RESULT HASE ERROR");
System.out.println(result.getAllErrors().toString());
if (result.hasErrors()) {
System.out.println("ERROR");
System.out.println(result.getAllErrors().toString());
}
return "admin/home";
}
#GetMapping("/manager/home")
public String mghomePage() {
System.out.println(SecurityContextHolder.getContext().getAuthentication().toString()+"---MANAGER HOME");
return "manager/home";
}
}
I Just tried with a small demo project and it's working fine for me.
Controller.
import javax.validation.Valid;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;
import com.demo.test.dto.DemoDto;
#RestController
#Validated
public class DemoController {
#PostMapping("/demo")
String getValidationResponse(#Valid #RequestBody DemoDto demoDto) {
return "all Valid";
}
}
Model class
import javax.validation.Valid;
import javax.validation.constraints.NotNull;
#Valid
public class DemoDto {
#Valid
#NotNull
private String name;
#Valid
#NotNull
private int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
POM.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.2</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<groupId>com.demo.test</groupId>
<artifactId>demovalidator</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>demovalidator</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>11</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
postman request-response.
Valid request
#NotEmpty and #NotBlank() can only work on properties of string type.
#Size is same.
so..
#NonNull(message = "User's name cannot be empty.")
#Min(2)
#Max(3)
private Long id;
Spring example:https://spring.io/guides/gs/validating-form-input/
but i got this error,
2021-02-05 12:19:08.944 WARN 8168 --- [nio-8080-exec-3] .w.s.m.s.DefaultHandlerExceptionResolver : Resolved [org.springframework.web.bind.MissingServletRequestParameterException: Required String parameter 'name' is not present]
dependencies are,
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.4.2</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.example.sample</groupId>
<artifactId>springboot-test</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>springboot-test</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
** Repository is,**
package com.example.sample.springboottest.Model;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
#Entity
public class User {
#Id
#GeneratedValue(strategy= GenerationType.AUTO)
private Integer id;
private String name;
private String email;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}
** Controllers are,**
package com.example.sample.springboottest.Controller;
import com.example.sample.springboottest.Model.User;
import com.example.sample.springboottest.Repository.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;
#Controller
#RequestMapping(path = "/demo")
public class MainController {
#Autowired
private UserRepository userRepository;
#PostMapping(path = "/add")
public #ResponseBody String addNewUser(#RequestParam String name, #RequestParam String email){
User n =new User();
n.setName(name);
n.setEmail(email);
userRepository.save(n);
return "Saved";
}
#GetMapping(path = "/all")
public #ResponseBody Iterable<User> getAllUser(){
return userRepository.findAll();
}
}
** Properties are,**
spring.jpa.hibernate.ddl-auto=update
spring.datasource.url=jdbc:mysql://${MYSQL_HOST:localhost}:3306/db_example
spring.datasource.username=root
spring.datasource.password=root
spring.jpa.open-in-view=true
spring.jpa.show-sql=true
Please help me to fix this,
Since you are using #ReuestParam you can't pass JSON like what you did.
In order to pass JSON format change #RequestParam to #RequestBody as below:
#PostMapping(path = "/add")
public #ResponseBody String addNewUser(#RequestBody User user){
// User n =new User();
//
// n.setName(name);
// n.setEmail(email);
// userRepository.save(n);
userRepository.save(user);
return "Saved";
}
And postman result would be as below:
But if you need to use #RequestParam then pass query string as below:
localhost:8811/demo/add?name=upul&email=upul#gmail.com
It seems that you have mixed up #RequestParam with #RequestBody
You seem to want to POST a JSON object to your controller, in which case your method signature should be
public #ResponseBody String addNewUser(#RequestBody User user){
Required String parameter 'name' is not present
Method parameters annotated with #RequestParam are required by default. It looks like while you are calling the API, you are not passing the name query param.
Edit: In this case, we could be passing the user in the request body.
I am very new in Java Spring and have a problem where I can not figure out what am I missing.
For the shake of brevity I will make it short:
I have a controller class with two methods for #GetMapping (get info from a patient in database) and #PostMapping (upload a photo from that patient).
In both methods, at some point I am calling through "findById" to database and populating a "Patient" model class object.
All the attributes of this class are retrieved successfully from Database but there is an attribute of this class (getPhoto()) that gets a null value only in the #PostMapping method.
What am I missing? The code is just the same in both methods.
Thanks very much in advance!!
Controller:
#CrossOrigin(origins="http://localhost:4200", maxAge = 3600)
#RestController
#RequestMapping({"/patients"})
public class PatientController {
#Autowired
IPatientService patientService;
#GetMapping("/{id}")
public ResponseEntity<?> listPatientId(#PathVariable("id") Integer id){
Optional<Patient> patient=null;
Map<String, Object> response=new HashMap<>();
try{
patient=patientService.findById(id);
}catch(DataAccessException e){
response.put("error", e.getMessage().concat(": "+e.getMostSpecificCause().toString()));
new ResponseEntity<Map<String, Object>>(response, HttpStatus.INTERNAL_SERVER_ERROR);
}
System.out.println("Patient with id: "+id+" / "+patient.get().getId()+" which photo is: "+patient.get().getPhoto());
/*Some other code*/
}
#PostMapping("/upload")
public ResponseEntity<?> upload(#RequestParam("archive")MultipartFile archive, #RequestParam("id") Integer id){
Optional<Paciente> paciente = Optional.empty();
Map<String, Object> respuesta= new HashMap<>();
try{
patient=patientService.findById(id);
}catch(DataAccessException e){
response.put("error", e.getMessage().concat(": "+e.getMostSpecificCause().toString()));
new ResponseEntity<Map<String, Object>>(response, HttpStatus.INTERNAL_SERVER_ERROR);
}
System.out.println("Patient with id: "+id+" / "+patient.get().getId()+" which photo is: "+patient.get().getPhoto());
/*Some other code*/
}
}
Patient class:
#Entity
#Table(name = "patients")
public class Patient {
#Id
#Column
#GeneratedValue(strategy=GenerationType.IDENTITY)
private Integer id;
#Column
private String photo;
(Getters and setters)
}
Repository:
#Repository
public interface PatientRepository extends JpaRepository<Patient, Integer> {
Iterable<Patient> findByNameContainingOrSurnameContaining(String name, String surname);
}
Service (Interface and Implemantation):
public interface IPatientService {
public List<Patient> findAll();
public Optional<Patient> findById(Integer id);
public Iterable<Patient> findByNameContainingOrSurnameContaining(String term);
}
#Service
public class PatientServiceImpl implements IPatientService {
#Autowired
private PatientRepository patientDao;
#Override
#Transactional(readOnly = true)
public List<Patient> findAll() {
return patientDao.findAll();
}
#Override
public Optional<Patient> findById(Integer id) {
return patienteDao.findById(id);
}
public Iterable<Patient> findByNameContainingOrSurnameContaining(String term){
return patientDao.findByNameContainingOrSurnameContaining(term, term);
}
#Override
public Patient save(Patient patient){
return patientDao.save(patient);
}
#Override
public void deleteById(Integer id) {
patientDao.deleteById(id);
}
}
As stated before, "patient.get().getPhoto()" returns in #GetMapping the actual value stored in the database. But in the method annotated with #PostMapping returns null for that value (Although other attributes seem to work just fine).
This was the backend, but in the frontend I am using Angular, where I call this method in component (I am showing just the parts involved in the uploading photo):
patient: Patient;
constructor(private route: ActivatedRoute, private router: Router, private service: ServiceServicee) {
this.paient = new Patient();
}
uploadPhoto() {
this.service.uploadPhoto(this.selectedPhoto,
this.patient.id).subscribe(patient => {
this.patient = patient;
});
}
Service:
constructor(private http:HttpClient, private router:Router) {
this.urlPatients='http://localhost:8080/patients';
}
uploadPhoto(file: File, id):Observable<Patient>{
let formData= new FormData();
formData.append("archive", file);
formData.append("id", id);
return this.http.post(`${this.urlPatients}/upload`, formData).pipe(
map((response:any)=> response.patient as Patient),
catchError(e=>{
console.error(e.error.mensaje);
return throwError(e);
})
);
}
UPDATE:
Using Postman and making a POST to http://localhost:8080/patients/upload and sending in the body a jpg file (form-data - "archive") and a id number("id"), I got a success with the inserts and the method it didn't worked previously in the backend (patient.get().getPhoto()) worked perfectly this time. With the same code, so I assume that it is as #BiteBat said and it is a problem of the Frontend and how it is calling the Backend.
I simulated the same environment that you created and it works for me as you expect, I leave the code for you to review what your problem. I would think you are incorrectly calling the POST method. Now, I would recommend that you do not save the images in a relational database, because there are alternatives with better performance, such as Google Storage / Local storage or any file storage service.
Structure:
EntryPoint:
package question;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
#SpringBootApplication
#EnableJpaRepositories
public class JulianPelayoApplication {
public static void main(String[] args) {
SpringApplication.run(JulianPelayoApplication.class, args);
}
}
Controller:
package question.controller;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.DataAccessException;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import question.repository.Patient;
import question.repository.PatientsRepository;
#CrossOrigin(origins="http://localhost:4200", maxAge = 3600)
#RestController
#RequestMapping("/patients")
public class PatientController {
private PatientsRepository patientsRepository;
#Autowired
public PatientController(PatientsRepository patientsRepository) {
this.patientsRepository = patientsRepository;
}
#GetMapping("/{id}")
public ResponseEntity<?> listPatientId(#PathVariable("id") Integer id){
Optional<Patient> patient=null;
Map<String, Object> response=new HashMap<>();
try{
patient = patientsRepository.findById(id);
}catch(DataAccessException e){
response.put("error", e.getMessage().concat(": "+e.getMostSpecificCause().toString()));
new ResponseEntity<Map<String, Object>>(response, HttpStatus.INTERNAL_SERVER_ERROR);
}
System.out.println("Patient with id: "+id+" / "+patient.get().getId()+" which photo is: "+patient.get().getPhoto());
return ResponseEntity.ok(patient);
}
#PostMapping(value="/upload")
public ResponseEntity<?> upload(#RequestParam("archive") MultipartFile archive, #RequestParam("id") Integer id){
Optional<Patient> patient = Optional.empty();
Map<String, Object> response = new HashMap<>();
try{
patient = patientsRepository.findById(id);
}catch(DataAccessException e){
response.put("error", e.getMessage().concat(": "+e.getMostSpecificCause().toString()));
new ResponseEntity<Map<String, Object>>(response, HttpStatus.INTERNAL_SERVER_ERROR);
}
System.out.println("Patient with id: "+id+" / "+patient.get().getId()+" which photo is: "+patient.get().getPhoto());
return ResponseEntity.ok(patient);
}
}
Repository:
package question.repository;
import org.springframework.data.repository.CrudRepository;
import org.springframework.stereotype.Repository;
#Repository
public interface PatientsRepository extends CrudRepository<Patient, Integer>{
}
Patient:
#Entity
#Table(name = "patients", schema = "business")
#Getter #Setter
public class Patient {
#Id
#Column
#GeneratedValue(strategy=GenerationType.IDENTITY)
private Integer id;
#Column
private String photo;
}
Spring.properties:
spring.datasource.url=jdbc:postgresql://localhost/test
spring.datasource.username=test
spring.datasource.password=test
spring.datasource.driver-class-name=org.postgresql.Driver
spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.PostgreSQLDialect
Pom:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.3.1.RELEASE</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<groupId>question</groupId>
<artifactId>JulianPelayo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>JulianPelayo</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
<exclusions>
<exclusion>
<groupId>org.junit.vintage</groupId>
<artifactId>junit-vintage-engine</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
Response:
Get
Post