@postya

Как сохранить текст из полей в базу данных с Thymeleaf и Spring Boot?

Делаю простое веб приложение на SpringBoot. Фронт енд на Thymeleaf. Имеется страница с полями и кнопкой, при нажатии на кнопку текст из полей должен сохраниться в базу данных(использую PostgreSQL)

На данный момент при запуске приложения сразу в стэктрейсе появляются ошибки:

5cc0970b86ae1998163215.jpeg
===================================================
5cc0971154fbe637099072.jpeg
=====================================================

5cc097174387a480852658.jpeg

Как правильно сохранять информацию из текстовых полей в базу данных?

сможете показать хотя бы один пример сохранения из одного текстового поля в БДпо нажатию кнопки?

Структура моего проекта:

5cc097a634afa196282771.jpeg

Класс Сar:

import javax.persistence.*;

@Entity
public class Car {

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

  @Column(name = "vehicle_id")
  private int vehicleID;

  private String color;

  private int year;

  private int seatCapacity;

  private String make;

  private int mileage;

  private double rate;

  public Car() {
  }

  public Car(int vehicleID, String color, int year, int seatCapacity, String make, int mileage, double rate) {
    this.vehicleID = vehicleID;
    this.color = color;
    this.year = year;
    this.seatCapacity = seatCapacity;
    this.make = make;
    this.mileage = mileage;
    this.rate = rate;
  }

  public Long getId() {
    return id;
  }

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

  public int getVehicleID() {
    return vehicleID;
  }

  public void setVehicleID(int vehicleID) {
    this.vehicleID = vehicleID;
  }

  public String getColor() {
    return color;
  }

  public void setColor(String color) {
    this.color = color;
  }

  public int getYear() {
    return year;
  }

  public void setYear(int year) {
    this.year = year;
  }

  public int getSeatCapacity() {
    return seatCapacity;
  }

  public void setSeatCapacity(int seatCapacity) {
    this.seatCapacity = seatCapacity;
  }

  public String getMake() {
    return make;
  }

  public void setMake(String make) {
    this.make = make;
  }

  public int getMileage() {
    return mileage;
  }

  public void setMileage(int mileage) {
    this.mileage = mileage;
  }

  public double getRate() {
    return rate;
  }

  public void setRate(double rate) {
    this.rate = rate;
  }
}


Интерфейс СarRepository:
import com.kentforth.car.entity.Car;
import org.springframework.data.repository.CrudRepository;
import org.springframework.stereotype.Repository;

@Repository
public interface CarRepository extends CrudRepository<Car, Long> {
}


Интерфейс СarService:

import com.kentforth.car.entity.Car;

public interface CarService {

  Iterable<Car> getAllCars();

  Car createCar(Car car);
}


Класс CarServiceImpl:

import com.kentforth.car.entity.Car;
import com.kentforth.car.repository.CarRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

@Service
public class CarServiceImpl implements CarService {

  @Autowired
  private CarRepository carRepository;

  @Override
  public Iterable<Car> getAllCars() {
    return carRepository.findAll();
  }

  @Override
  public Car createCar(Car car) {
    return carRepository.save(car);
  }
}


Класс MainController:

import com.kentforth.car.entity.Car;
import com.kentforth.car.service.CarService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PostMapping;

@Controller
public class MainController {

  @Autowired
  private CarService carService;

  @GetMapping("/")
  public String showPage(Model model) {
    return "main";
  }

  @GetMapping("/cars")
  public String getAllCars(@ModelAttribute Car car, Model model) {
    carService.getAllCars();
    model.addAttribute("cars", carService.getAllCars());
    return "cars";
  }

  @PostMapping("/cars")
  public String addCar(@ModelAttribute("car") Car car) {
    carService.createCar(car);
//    model.addAttribute("car", car);
    return "main";
  }
}


html файл :

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org" lang="en">
    <head>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
        <title>Car Edit</title>
        <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous">
    </head>
    <body>

        <form class="container mt-md-5 needs-validation"
              data-toggle="validator" novalidate action="#" th:action="@{/cars}" th:object="${car}" method="post">
            <div class="form-row">
                <div class="form-group col-md-6">
                    <label for="vehicleID">VehicleID</label>
                    <input type="number" class="form-control" id="vehicleID" required th:field="*{vehicleID}">
                    <div class="invalid-feedback">
                        Please provide Vehicle ID.
                    </div>
                </div>

                <div class="form-group col-md-6">
                    <label for="color">Color</label>
                    <input type="text" class="form-control" id="color" required th:field="*{color}">
                    <div class="invalid-feedback">
                        Please provide a valid color.
                    </div>
                </div>

                <div class="form-group col-md-6">
                    <label for="year">Year</label>
                    <input type="number" class="form-control" id="year" required th:field="*{year}">
                    <div class="invalid-feedback">
                        Please type year.
                    </div>
                </div>

                <div class="form-group col-md-6">
                    <label for="seat-capacity">Seat Capacity</label>
                    <input type="number" class="form-control" id="seat-capacity" required th:field="*{seatCapacity}">
                    <div class="invalid-feedback">
                        Please provide number of seats.
                    </div>
                </div>

                <div class="form-group col-md-6">
                    <label>Make</label>
                    <select class="custom-select mr-sm-2" required th:field="*{make}">
                        <option value="">Choose...</option>
                        <option value="1">Dodge</option>
                        <option value="2">BMW</option>
                        <option value="3">Honda</option>
                        <option value="4">Tesla</option>
                    </select>
                    <div class="invalid-feedback">Please select make</div>
                </div>

                <div class="form-group col-md-6">
                    <label for="mileage">Current Mileage</label>
                    <input type="number" class="form-control" id="mileage" required th:field="*{mileage}">
                    <div class="invalid-feedback">
                        Please provide a valid mileage.
                    </div>
                </div>

                <div class="form-group col-md-2">
                    <label for="rate">Rate</label>
                    <input type="number" class="form-control" id="rate" required th:field="*{rate}">
                    <div class="invalid-feedback">
                        Please provide rate.
                    </div>
                </div>

            </div>
            <button type="submit" class="btn btn-primary mt-2 col-md-1">Add</button>
            <button type="submit" class="btn btn-success mt-2 ml-3 col-md-2">Show Cars</button>
        </form>


        <script src="https://code.jquery.com/jquery-3.3.1.slim.min.js" integrity="sha384-q8i/X+965DzO0rT7abK41JStQIAqVgRVzpbzo5smXKp4YfRvH+8abtTE1Pi6jizo" crossorigin="anonymous"></script>
        <script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js" integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1" crossorigin="anonymous"></script>
        <script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"></script>
         
    <script src="/validate.js"></script>
    </body>
</html>
  • Вопрос задан
  • 1887 просмотров
Решения вопроса 1
azerphoenix
@azerphoenix Куратор тега Java
Java Software Engineer
Здравствуйте!
У вас выбрасывает исключение связанное с шаблонизатором thymeleaf
+ вы не указали атрибут name для инпутов
А теперь, простой пример
@Entity
Car {
	
	@Id
	@GeneratedValue(strategy = GenerationType.AUTO)
  	private Long id;

  	private String carModel;

  	private String carName;

	public Car() {}
	//getters & setters & no args constructor
}


<form method="post" th:action="@{/cars/add}">
	
	<input type="text" name="carModel">
	<input type="text" name="carName">
	<input type="submit" value="Добавить машину">

</form>

@Autowired
private CarRepository carRepository

@PostMapping("/cars/add")
public String addNewCar(
 @ModelAttribute("carModel") String carModel,
 @ModelAttribute("carName") String carName,
 Car car
) {
 // тут конечно можно в carService создать метод и передать ему эти аргументы
	car.setCarModel(carModel);
	car.setCarName(carName);
	carRepository.save(car);

	return "main"; 
}


Видео - https://www.youtube.com/watch?v=jH17YkBTpI4&list=P...
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы