2025-02-16
Board entity를 만들고 실행하던 중 이런 에러가 나타났다.
Hibernate:
alter table board
drop
foreign key FKfyf1fchnby6hndhlfaidier1r
2025-02-16T19:44:54.506+09:00 WARN 27568 --- [newsFeed] [ main] o.h.t.s.i.ExceptionHandlerLoggedImpl : GenerationTarget encountered exception accepting command : Error executing DDL "
alter table board
drop
foreign key FKfyf1fchnby6hndhlfaidier1r" via JDBC [Table 'newsfeed.board' doesn't exist]
org.hibernate.tool.schema.spi.CommandAcceptanceException: Error executing DDL "
alter table board
drop
foreign key FKfyf1fchnby6hndhlfaidier1r" via JDBC [Table 'newsfeed.board' doesn't exist]
하고 블라블라 ~~~~~~~~~ 하다가
Caused by: java.sql.SQLSyntaxErrorException: Table 'newsfeed.board' doesn't exist
여기서 핵심은 GenerationTarget encountered exception accepting command : Error executing DDL 이라는 문구인데
GenerationTarget에서 예외 수락 명령이 발생했습니다: DDL 실행 중 오류 발생
파파고한테 번역기를 돌리니 이렇다고 한다.
주로 jpa를 사용할때 나타나는 오류이며 DDL 명령어 실행 중에 발생한다고 한다
그럼 Board 라고 이름을 지은 entity에 문제가 생긴 것 같으니 찾아본다.
package com.example.newsfeed.board.entity;
import com.example.newsfeed.common.entity.BaseEntity;
import com.example.newsfeed.user.entity.User;
import jakarta.persistence.*;
import lombok.Getter;
import lombok.Setter;
@Entity
public class Board extends BaseEntity {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(nullable = false)
private String title;
@Column(nullable = false)
private String contents;
@ManyToOne
@JoinColumn(name = "user_id")
@Getter
private User user;
@Setter
@Getter
private Long like;
}
문법적으로는 오류가 없다.
하지만 '좋아요'라는 의미에서 지은 like 라는 필드가 생각해보니 jpa가 쿼리문을 작성해 줄때 SQL 예약어와 같아서 오류가 나는 것 같으니 이를 바꿔야할듯하다.
like 필드를 likes로 바꾸니 해결됐다. 다음부터는 entity 클래스의 필드명을 지을 때 SQL 예약어와 같은지 생각하고 지어야겠다.
2025-02-19
회원 탈퇴 기능을 만들고 나니 그 회원이 아무 게시물이나 댓글, 좋아요 등 행동이 없으면 탈퇴가 잘 되지만 뭐라도 하나 하면 회원탈퇴가 안된다.
2025-02-19T13:05:41.877+09:00 ERROR 17856 --- [newsFeed] [nio-8080-exec-4] o.h.engine.jdbc.spi.SqlExceptionHelper : Cannot delete or update a parent row: a foreign key constraint fails (`newsfeed`.`friend`, CONSTRAINT `FK3uu8s7yyof1qmenthngm24hry` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`))
2025-02-19T13:05:41.920+09:00 ERROR 17856 --- [newsFeed] [nio-8080-exec-4] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed: org.springframework.dao.DataIntegrityViolationException: could not execute statement [Cannot delete or update a parent row: a foreign key constraint fails (`newsfeed`.`friend`, CONSTRAINT `FK3uu8s7yyof1qmenthngm24hry` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`))] [/* delete for com.example.newsfeed.user.entity.User */delete from user where id=?]; SQL [/* delete for com.example.newsfeed.user.entity.User */delete from user where id=?]; constraint [null]] with root cause
Cannot delete or update a parent row: a foreign key constraint fails (`newsfeed`.`friend`, CONSTRAINT `FK3uu8s7yyof1qmenthngm24hry` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`))
부모 행을 삭제하거나 업데이트할 수 없습니다: 외래키 제약 조건이 실패합니다 ('newsfeed' gilsfriend', 제약 조건 'FK3uu8s7yof1qmenthm24hry' 외래 키 ('user_id') 참조 '사용자' ('id')
자식 테이블 입장에선 부모 테이블의 열과 일치하는 데이터를 가져와야 하는데 이 무결성이 깨지기 때문에 삭제를 못하는 것 같다.
그럼 JPA로 부모테이블에서 자식테이블로 oneToMany를 사용하여 양방향 매핑이 되게 한뒤 oneToMany에 cascade.remove나 all을 적어주면 될 것 같다.
package com.example.newsfeed.user.entity;
import com.example.newsfeed.comment.entity.Comment;
import com.example.newsfeed.common.entity.BaseEntity;
import com.example.newsfeed.friend.entity.Friend;
import com.example.newsfeed.friend.entity.FriendsRequest;
import com.example.newsfeed.like.entity.Likes;
import com.example.newsfeed.post.entity.Post;
import jakarta.persistence.*;
import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;
@Getter
@Setter
@Entity
@NoArgsConstructor
public class User extends BaseEntity {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(nullable = false)
private String name;
@Column(nullable = false, unique = true)
private String email;
@Column(nullable = false)
private String password;
@OneToMany(mappedBy = "user", cascade = CascadeType.ALL)
private List<Post> posts;
@OneToMany(mappedBy = "user", cascade = CascadeType.ALL)
private List<Likes> likes;
@OneToMany(mappedBy = "requester", cascade = CascadeType.ALL)
private List<FriendsRequest> sentFriendsRequests;
@OneToMany(mappedBy = "receiver", cascade = CascadeType.ALL)
private List<FriendsRequest> receiveFriendsRequests;
@OneToMany(mappedBy = "receiver", cascade = CascadeType.REMOVE)
private List<Friend> receiveFriends;
@OneToMany(mappedBy = "requester", cascade = CascadeType.REMOVE)
private List<Friend> requesterFriends;
public User(String email, String password, String name) {
this.email = email;
this.password = password;
this.name = name;
}
private User(Long id) {
this.id = id;
}
public static User fromUserId(Long id) {
return new User(id);
}
}
이렇게 했더니 회원 탈퇴 시 회원의 행적이 다 삭제되며 탈퇴가 제대로 되는 모습이다.
만약 회원 탈퇴를 해도 행적은 남게 하려면 어떻게 해야할지 생각해봐야겠다.
'spring' 카테고리의 다른 글
| 관계형DB일때 N:M 연관관계 @ManyToMany (0) | 2025.02.24 |
|---|---|
| @Mock (0) | 2025.02.24 |
| HttpServletResponse 메서드 (0) | 2025.02.12 |
| Bcrypt (0) | 2025.02.10 |
| scheduleJPA 트러블슈팅 (1) | 2025.02.07 |