如何解决使用外键保存对象不会在数据库中返回 ID
我有一个电影院预订系统,用户可以在其中添加电影,然后他们可以为每部电影添加日期。它工作正常,但是当用户添加日期时,没有错误,但它以movie_id = null 保存到数据库中。
我该如何解决?
电影.java
@Data
@Entity
public class Movie {
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Id
@Column(name = "id")
private Long id;
@Column(unique = true)
private String title;
private String category;
@Column( columnDeFinition = "TEXT")
private String description;
private Integer lenght;
private Integer minAge;
@Column(columnDeFinition = "TEXT")
private String imageUrl;
@OnetoMany(mappedBy = "movie",orphanRemoval = true)
private List<Repertoire> repertoires;
public Movie() {
}
}
Repertoire.java
@Data
@Entity
public class Repertoire {
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Id
@Column(name = "id")
private Long id;
@DateTimeFormat(pattern = "yyyy-MM-dd'T'HH:mm")
private LocalDateTime date;
@ManyToOne(cascade = CascadeType.ALL)
@JoinColumn(name = "movie_id")
private Movie movie;
}
电影控制器.java
@Controller
@RequestMapping("/movies")
public class MovieController {
private MovieRepo movieRepo;
private RepertoireRepo repertoireRepo;
@Autowired
public MovieController(MovieRepo movieRepo,RepertoireRepo repertoireRepo) {
this.movieRepo = movieRepo;
this.repertoireRepo = repertoireRepo;
}
@GetMapping("showForm")
public String showStudentForm(Movie movie) {
return "add-movie";
}
@GetMapping("list")
public String getMovies(Model model) {
model.addAttribute("movies",movieRepo.findAll());
return "movieIndex";
}
@PostMapping("add")
public String movies(@Validated Movie movie,BindingResult result,Model model) {
if(result.hasErrors()) {
return "add-movie";
}
movieRepo.save(movie);
return "redirect:/movies/list";
}
@GetMapping("edit/{id}")
public String showUpdateForm(@PathVariable ("id") long id,Model model) {
Movie movie = movieRepo.findById(id)
.orElseThrow(() -> new IllegalArgumentException("Nieprawidłowe ID: " + id));
model.addAttribute("movie",movie);
return "update-movie";
}
@PostMapping("update/{id}")
public String updateMovie(@PathVariable("id") long id,@Validated Movie movie,Model model) {
if(result.hasErrors()) {
movie.setId(id);
return "update-movie";
}
movieRepo.save(movie);
model.addAttribute("movies",movieRepo.findAll());
return "movieIndex";
}
@GetMapping("delete/{id}")
public String deleteMovie(@PathVariable ("id") long id,Model model) {
List<Repertoire> repertoires = repertoireRepo.findByMovieId(id);
repertoires.forEach(r -> repertoireRepo.deleteById(r.getId()));
Movie movie = movieRepo.findById(id)
.orElseThrow(() -> new IllegalArgumentException("Nieprawidłowe ID : " + id));
movieRepo.delete(movie);
model.addAttribute("movies",movieRepo.findAll());
return "movieIndex";
}
// HERE'S WHERE I ADD THE TIME:
@GetMapping("/admin/{movieName}/newRepertoire")
public String showRepertoireForm(Model model,@PathVariable ("movieName") String movieName) {
Movie movieRepertoire = movieRepo.findByTitle(movieName);
model.addAttribute("movieRepertoire",movieRepertoire);
model.addAttribute("repertoire",new Repertoire());
return "repertoire";
}
@PostMapping("/admin/newRepertoire")
@Transactional
public String addRepertoire(@modelattribute ("repertoire") Repertoire repertoire,@modelattribute("movieRepertoire") Movie movie,BindingResult result) {
// if(result.hasErrors()) {
// return "repertoire";
// }
repertoire.setMovie(movieRepo.findByTitle(movie.getTitle()));
repertoireRepo.save(repertoire);
return "redirect:/movies/list";
}
}
RepertoireRepo.java
@Repository
public interface RepertoireRepo extends JpaRepository<Repertoire,Long> {
List<Repertoire> findByMovieId(Long movieId);
}
MovieRepo.java
@Repository
public interface MovieRepo extends JpaRepository<Movie,Long> {
Movie findByTitle(String title);
}
repertoire.html
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org"
xmlns:sec="http://www.thymeleaf.org/extras/spring-security">
<head>
<Meta charset="UTF-8">
<Meta http-equiv="x-ua-compatible" content="ie=edge">
<title>c</title>
</head>
<body>
<div class="container my-5">
<div class="card">
<div class="card-body">
<div class="col-md-10">
<h1 th:text="${movieRepertoire.title}"> MovieName</h1>
<form action="#" th:action="@{/movies/admin/newRepertoire}" th:object="${repertoire}" method="post">
<div class="row">
<div class="form-group col-md-8">
<label for="date" class="col-form-label">Date</label>
<input type="datetime-local" th:field="*{date}" class="form-control" id="date" value="2021-01-20T13:01">
<span th:if="${#fields.hasErrors('date')}" th:errors="*{date}" class="text-danger"></span>
</div>
<div class="col-md-6">
<input type="submit" class="btn btn-primary" value="Add">
</div>
<div class="form-group col-md-8"></div>
</div>
<!-- <input type = "hidden" th:value="${movieRepertoire}">-->
</form>
</div>
</div>
</div>
</div>
</body>
</html>
电影结构:
id | category | description | imageurl| lenght| minage| title
-------------------------
36 | Action | Simple desc. | photo.jpg | 137 | 7 | Iron Man |
曲目结构:
id | date | movie_id
-------------------------
37 | 2021-01-01 14:00:00 | null |
解决方法
关系的双方都必须更新,您应该从父级级联保存。您的代码:
repertoire.setMovie(movieRepo.findByTitle(movie.getTitle()));
repertoireRepo.save(repertoire);
应该变成:
Movie movie = movieRepo.findByTitle(movie.getTitle());
movie.getRepertoires().add(repertoire);
repertoire.setMovie(movie);
session.saveOrUpdate(movie);
实际上,您应该向 Movie 添加一个辅助方法,该方法执行两个操作以确保关系的双方始终同步:
public void addRepertoire(Repertoire repertoire) {
repertoires.add(repertoire);
repertoire.setMovie(this);
}
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。