2021. 9. 29. 01:34ใProgramming Project ์์ ์ค/๋ด์ฉ ์ ๋ฆฌ
์๋ ํ์ธ์? ์ฃผ๋ํ๋์ด์์!
์ค๋๋ถํฐ ์ฃผ๋ํ๋์ด ๊ฐ์กฑ๋ค์ ์ํ ์น ์๋น์ค๋ฅผ ํผ์ ๋ง๋ค์ด ๋ณด๋ ค ํ๋ ๊ฒ์ด์์.
์ฃผ๋ํ๋์ ์ง์ Synology NAS๋ฅผ ํตํด ์ ์ ๊ฐ์กฑ๋ค์ ์ํด ํธ๋ฆฌํ ๊ธฐ๋ฅ๋ค์ ๋ง์ด ์๋น์ค ์ค์ธ๋ฐ, ๊ฐ์กฑ๋ค์ด ์๋ฌด๋ ์ฌ์ฉ์ ํ์ง ๋ชปํ๋ ๊ฒ์ด์์๐ฅ
๊ทธ๋์ ์น ์๋น์ค๋ฅผ ๋ง๋ค์ด์ ๋ฉ๋ด์ผ์ ๋ณผ ์ ์๋ ์๋น์ค๋ฅผ ๋ง๋ค์ด ๋ณผ ๊ฒ์ด์์!
์ฃผ๋ํ๋์ด ์์ฑํ Source Code๋ ์ฌ๊ธฐ Git Hub์์ ํ์ธํ์ค ์ ์์ต๋๋ค!
๐ Member์ ๊ฒ์ํ ๊ทธ๋ฆฌ๊ณ ๋๊ธ
๋จผ์ ์ฃผ๋ํ๋์ Maria DB๋ฅผ Sysnology NAS์ Docker๋ก ๋ง๋ค์ด ๋ ผ ๊ฒ์ด์์.
๊ทธ๋์ mariadb์ driver๋ฅผ ์ค์ ํ๊ณ , ๊ณ์ ์ ์ค์ ํด ์ค ๊ฒ์ด์์.
๐ Hibernate ์์ฑ ์๊ฐ
- hibernate.show_sql : ์คํํ๋ SQL๋ฌธ์ Console์ ์ถ๋ ฅ
- hibernate.format_sql : SQL์ ๋ณด๊ธฐ ์ข๊ฒ ์ ๋ฆฌํด์ ์ถ๋ ฅ
- spring.jpa.hibernate.use-new-id-generator-mappings : JPA์ ๋ง์ถ ์๋ก์ด ID ์์ฑ ๋ฐฉ๋ฒ ์ฌ์ฉ. Hibernate Legacy๋ฅผ ์ด์ํ๋ ๊ฒ์ด ์๋๋ผ๋ฉด ํญ์ true๋ก ์ค์
- spring.jpa.hibernate.ddl-auto : Applicatioon์ด ์์๋ ๋ ํ
์ด๋ธ๊ณผ ๊ธฐํ DDL์ ์๋์ผ๋ก ์์ฑ.
- create : ๊ธฐ์กด DDL์ ์ ๊ฑฐํ๊ณ , ์๋ก ์์ฑ
- create-drop : create์ ๊ฐ์ผ๋, Application์ด ์ข ๋ฃ๋ ๋, ์์ฑํ DDL ์ ๊ฑฐ
- update : ํ์ฌ DB DDL๊ณผ ๋น๊ตํ์ฌ ๋ณ๊ฒฝ์ฌํญ๋ง ์์
- validate : ํ์ฌ ์ํฐํฐ ๋งคํ ์ ๋ณด์ DB ์คํค๋ง๊ฐ ๊ฐ์์ง ๋น๊ตํ๋ค. ๋ง์ฝ ๋ค๋ฅด๋ฉด ๊ฒฝ๊ณ ๋ฅผ ๋จ๊ธฐ๊ณ , Application์ ์คํํ์ง ์๋๋ค. ์ด ์ค์ ์ DDL ๋ฏธ ๋ณ๊ฒฝ.
โ ์ฃผ์ : spring.jpa.hibernate.use-new-id-generator-mappings ์ฃผ์์ฌํญ
์ด ์ต์ ์ ์ค์ ํ์ง ์์ผ๋ฉด ํ์ด๋ฒ๋ค์ดํธ๋ ๊ณผ๊ฑฐ ๋ฒ์ ์์ ์ฌ์ฉํ๋ ํค ์์ฑ ์ ๋ต์ ์ฌ์ฉํ๊ฒ ๋๋ค.
ํ์ด๋ฒ ๋ค์ดํธ ๊ณต์ ๋ฌธ์๋ true๋ก ์ค์ ํด์ JPA ํ์ค์ ๋ง์ถ ์๋ก์ด ํค ์์ฑ ์ ๋ต์ ๊ถ์ฅํ๋ค.
ํ์ด๋ฒ๋ค์ดํธ๋ ๊ณผ๊ฑฐ ๋ฒ์ ๊ณผ ํธํ์ ์ํด ์ ๊ท ๊ฐ๋ฐ์์๊ฒ ์ด ์ต์ ์ ์ค์ ํ๋๋ก ํ๋ค.
๐ก ์ฐธ๊ณ :
JPA์ ๋์ ํ๊ฒฝ์ ์์ ์๋ฐ์ธ J2SE์ JSEE ํ์ค ์ปจํ ์ด๋ ์์์ ๋์ํ๋ ๊ฒ์ผ๋ก ๋๋ ์ ์๋ค.
์คํ๋ง ํ๋ ์์ํฌ๋ LocalContainerEntityManagerFactoryBean์ ์ฌ์ฉํ์ฌ J2SE ํ๊ฒฝ์ JPA๋ฅผ ๋ง์น ํ์ค ์ปจํ ์ด๋ ์์์ ๋์ํ๋ ๊ฒ์ฒ๋ผ ์๋ฎฌ๋ ์ด์ ํ๋ค.
๐ Member Entity
๋จผ์ ์ฃผ๋ํ๋์ ํด๋น ์๋น์ค๋ฅผ ์ํด DB ์ค๊ณ๋ฅผ ์ด๋ป๊ฒ ํ ์ง ๊ณ ๋ฏผํ ๊ฒ์ด์์.
์ฌ๋ฌ ๊ณ ๋ฏผ์ ๋์ ์์ ๊ฐ์ด DB๋ฅผ ์์ฑ ํด ๋ณด๊ธฐ๋ก ํ๋ต๋๋ค!
๐ Entity Class ์์ฑ
@Entity
Entity Class๋ Spring Data JPA์์๋ @Entity๋ฅผ ์ถ๊ฐํด์ผ๋ง ํ๋ ๊ฒ์ด์์. ์ด ์น๊ตฌ๋ JPA๊ฐ ๊ด๋ฆฌ๋ฅผ ํ๋ ๊ฒ์ด์์.
@Entity๋ ํด๋น ํด๋์ค๊ฐ ์ํฐํฐ๋ฅผ ์ํ ํด๋์ค์ด๋ฉฐ, ํด๋น ํด๋์ค์ ์ธ์คํด์ค๋ค์ด JPA๋ก ๊ด๋ฆฌ๋๋ ์ํฐํฐ ๊ฐ์ฒด๋ฅผ ์๋ฏธํ๋ ๊ฒ์ด๋๋๋ค!
- ๊ธฐ๋ณธ ์์ฑ์๋ ํ์ (๋งค๊ฐ ๋ณ์๊ฐ ์๋ public ๋๋ protected ์์ฑ์)
- final ํด๋์ค, enum, interface, inner ํด๋์ค์๋ ์ฌ์ฉ ๋ถ๊ฐ.
- ์ ์ฅํ ํ๋์ final์ ์ฌ์ฉ ๋ถ๊ฐ
@NoArgsConstructor
๊ธฐ๋ณธ ์์ฑ์๋ฅผ ๋ง๋ค์ด ์ฃผ๋ Annotation
@AllArgsConstructor
๋ฉค๋ฒ ๋ณ์๋ฅผ ๋งค๊ฐ ๋ณ์๋ก ๊ฐ๋ ์์ฑ์๋ฅผ ๋ง๋ค์ด ์ฃผ๋ Annotation
@Getter
๋ฉค๋ฒ ๋ณ์์ ๋ํ Getter Method๋ฅผ ๋ง๋ค์ด์ฃผ๋ Annotation
@ToString
- toString()์ Override(์ฌ ์ ์)ํ์ฌ ๊ฐ๊ฐ์ ๋ฉค๋ฒ ๋ณ์๋ค์ (Non Static Filed)๋ฅผ ์ถ๋ ฅ
- ๋ฉค๋ฒ ๋ณ์ ์ด๋ฆ์ ์ถ๋ ฅ๋์ง ์๊ฒ ํ๊ธฐ ์ํ ๋ฐฉ๋ฒ
@ToString(includeFieldNames = false) - ํน์ ๋ฉค๋ฒ ๋ณ์๊ฐ toString()์ ํฌํจ๋์ง ์๊ฒ ํ๋ ค๋ฉด
@ToString(exclude={'Field ์ด๋ฆ1',' Field ์ด๋ฆ2'}) - ๋ช
์์ ์ผ๋ก ํน์ ํ๋๋ฅผ ํฌํจํ๊ฒ ํ๋ ค๋ฉด
@ToString(callSuper=true) - ๋ถ๋ชจ ํด๋์ค์ toString()์ ํธ์ถํ๊ฒ ํ๋ ค๋ฉด
@ToString(callSuper=true) - ๊ธฐ๋ณธ์ ์ผ๋ก getter๊ฐ ์์ผ๋ฉด ํด๋น Method ํธ์ถ์ด ๋๋, ์ด๋ฅผ ์ฌ์ฉํ์ง ์๊ณ , ํ๋๋ฅผ ์ง์ ํธ์ถํ๋ ค๋ฉด
@ToString(doNotUseGetter=true)
@Id
DB์์ PK (Primary Key)๋ฅผ ์ง์ ํ๋ Annotaion์ธ ๊ฒ์ด์์.
@GeneratedValue
์์์ ์ฌ์ฉํ strategy=GenerationType.IDENTITY๋ IDENTITY ์ ๋ต์ด๋ผ๊ณ ํ๋๋ฐ, MariaDB์ ๊ฐ์ DBMS์์ ์ฌ์ฉํ๋ AUTO_INCREMENT๋ฅผ ์ฌ์ฉํ๋๋ก ๋ง๋๋ ๊ฒ์ด์์. ๊ฐ๋ฐ์๊ฐ ์ํฐํฐ์ ์ง์ ์๋ณ์๋ฅผ ํ ๋นํ๋ฉด @Id๋ง ์์ผ๋ฉด ๋์ง๋ง, ์๋ณ์๊ฐ ์์ฑ๋๋ ๊ฒฝ์ฐ๋ค๋ @GeneratedValue๋ฅผ ํตํด ์๋ณ์ ์์ฑ ์ ๋ต์ ๊ตฌ์ฑํด์ผ ํ๋ ๊ฒ์ด์์.
IDENTITY ์ ๋ต์ ์ฌ์ฉํ๋ ค๋ฉด @GeneratedValue์ strategy ์์ฑ๊ฐ์ GenerationType.IDENTITY๋ก ์ง์ ํ๋ฉด ๋๋ ๊ฒ์ด์์. ์ด๋ ๊ฒ ํ๋ฉด JPA๋ ๊ธฐ๋ณธ ํค ๊ฐ์ ์ป์ด์ค๊ธฐ ์ํด DB๋ฅผ ์ถ๊ฐ๋ก ์กฐํํด์ผ ํ๋ ๊ฒ์ด์์.
- ์๋ ์์ฑ : ๋๋ฆฌ ํค ์ฌ์ฉ ๋ฐฉ์
- IDENTITY : ๊ธฐ๋ณธ Key ์์ฑ์ DB์ ์์
- SEQUENCE : DB ์ํ์ค๋ฅผ ์ฌ์ฉํด์ ๊ธฐ๋ณธ ํค ํ ๋น
- TABLE : Key ์์ฑ Table ์ฌ์ฉ
- ์ง์ ํ ๋น : ๊ธฐ๋ณธ ํค๋ฅผ Application์ ์ง์ ํ ๋น
@Enumerated(EnumType.STRING)
๋จผ์ @Enumerated๋ JAVA์ enum Type์ Mappingํ ๋ ์ฌ์ฉํ๋ ๊ฒ์ด์์.
์ ์ฑ | ๊ธฐ ๋ฅ | ๊ธฐ ๋ณธ ๊ฐ |
value | โ EnumType.ORDINAL : enum ์์๋ฅผ DB์ ์ ์ฅ โ EnumType.STRING : enum ์ด๋ฆ์ DB์ ์ ์ฅ |
EnumType.ORDINAL |
enum Class๋ ๋ค์๊ณผ ๊ฐ์ด ์ฌ์ฉํ๋ ๊ฒ์ด์์.
enum RoleType {
ADMIN, USER
}
์๋๋ enum ์ด๋ฆ์ผ๋ก Mappingํ๋ ๊ฒ์ด์์.
@Enumerated(EnumType.STRING)
private RoleType roleType;
enum์ ๋ค์๊ณผ ๊ฐ์ด ์ฌ์ฉํ๋ ๊ฒ์ด์์.
// DB์ ๋ฌธ์ ADMIN์ผ๋ก ์ ์ฅ
number.setRoleType(RoleType.ADMIN);
@Enumerated๋ฅผ ์ฌ์ฉํ๋ฉด ํธ๋ฆฌํ๊ฒ enum Tyupe์ DB์ ์ ์ฅํ ์ ์๋ ๊ฒ์ด์์.
EnumType.ORDINAL์ enum์ ์ ์๋ ์์๋๋ก ADMIN์ 0, USER๋ 1 ๊ฐ์ด DB์ ์ ์ฅ ๋๋ ๊ฒ์ด์์.
- ์ฅ์ : DB์ ์ ์ฅ๋๋ Data ํฌ๊ธฐ๊ฐ ์๋ค.
- ๋จ์ : ์ด๋ฏธ ์ ์ฅ๋ enum์ ์์๋ฅผ ๋ณ๊ฒฝํ ์ ์๋ค.
EnumType.STRING์ enum ์ด๋ฆ ๊ทธ๋๋ก ADMIN์ 'ADMIN', USER๋ 'USER'๋ผ๋ ๋ฌธ์๋ก DB์ ์ ์ฅ๋๋ ๊ฒ์ด์์.
- ์ฅ์ : ์ ์ฅ๋ enum์ ์์๊ฐ ๋ฐ๋๊ฑฐ๋, enum์ด ์ถ๊ฐ ๋์ด๋ ์์ ํ๋ค.
- ๋จ์ : DB์ ์ ์ฅ๋๋ Data ํฌ๊ธฐ๊ฐ ORDINAL์ ๋นํด์ ํฌ๋ค.
๐ก ์ฐธ๊ณ :
๊ธฐ๋ณธ๊ฐ์ธ ORDINAL์ ์ฃผ์ํด์ ์ฌ์ฉ ํ ๊ฒ!
ADMIN(0๋ฒ), USER(1๋ฒ) ์ฌ์ด์ enum์ด ํ๋ ์ถ๊ฐ๋์ด ADMIN(0๋ฒ), NEW(1๋ฒ), USER(2๋ฒ)์ผ๋ก ์ค์ ๋๋ฉด ์ด์ ๋ถํฐ USER๋ 2๋ก ์ ์ฅ๋๋, ๊ธฐ์กด DB์ ์ ์ฅ๋ ๊ฐ์ ์ฌ์ ํ 1๋ก ๋จ์ ์๋ค. ๋ฐ๋ผ์ ์ด๋ฐ ๋ฌธ์ ๊ฐ ๋ฐ์ํ์ง ์๋ EnumType.STRING์ ๊ถ์ฅํ๋ค.
์ฃผ๋ํ๋์ ์์ Annotation๋ค์ ์ฌ์ฉํด์ Member๋ผ๋ Entity๋ฅผ ๊ตฌ์ฑํ๊ณ , ํ์ ๋ฑ๊ธ๊ณผ ๊ฐ์ธ์ ๋ณด ์์ง ๋์์์ ๋ํ ๋ด์ฉ๋ค์ ๋ฐ์ ์ ์๊ฒ ์ฒ๋ฆฌํ ๊ฒ์ด์์.
ํ์ ๊ฐ์ ์์ ํ์ ๊ณ ์ ๋ฒํธ(id), ํ์ Email ์ฃผ์(email), ํ์ ๋น๋ฐ๋ฒํธ(password), ํ์ ์ด๋ฆ(name), ํ์ ๋ณ๋ช (nick_name), ํ์ ์ ํ๋ฒํธ(phone), ํ์ ๋ฑ๊ธ(grade), ๊ฐ์ธ์ ๋ณด ์์ง ๋์์(agree)๋ฅผ ๋ฐ์ ๊ฒ์ด์์.
๐ MemberGrade
ํ์ ๋ฑ๊ธ์ ์์ ๊ฐ์ด ADMIN, FAMILY, GUEST๋ก ๋๋์๊ณ , DB์ ๋ค์ด๊ฐ ๋๋ ์ง์ ํ ๋ฌธ์์ด์ด ๋ค์ด๊ฐ ์ ์๋๋ก ์ฒ๋ฆฌํ ๊ฒ์ด์์.
๐ private_information_essential_agree
์์ ๊ฐ์ธ์ ๋ณด ์์ง ๋์๋ ๋๊ฐ์ด ์ฒ๋ฆฌํ ๊ฒ์ด์์!
๐ SystemUseManual Entity
@Column
๋ฉค๋ฒ ๋ณ์(ํ๋)๋ฅผ ์ปฌ๋ผ์ ๋งคํํ๋ ๊ฒ์ด์์. ์ฃผ๋ํ๋์ name ์์ฑ์ ์ฌ์ฉํด์ SystemUseManul ์ํฐํฐ์ regdate ํ๋๋ฅผ SystemUseManul ํ ์ด๋ธ์ regdate ์ปฌ๋ผ์ ๋งคํํ ๊ฒ์ด๊ณ , mode ํ๋๋ฅผ moddate ์ปฌ๋ผ์ ๋งคํํ ๊ฒ์ด์์.
์ ๊ธฐ ์์ฑ์ updatable = false๋ ํด๋น ๊ฒ์๊ธ์ด ์์ ์ด ๋ ๋, ์์ฑ์ผ์ ๋ณ๊ฒฝ์ด ๋๋ฉด ์๋๋ ๊ฒ์ด์์.
๊ทธ๋ ๊ธฐ ๋๋ฌธ์ ํด๋น ์์ฑ์ผ๋ก ๋ณ๊ฒฝ๋์ง ๋ชปํ๋๋ก ์ค์ ํ๋ ๊ฒ์ด๋๋๋ค.
LocalDateTime ๊ฐ์ฒด๋ฅผ ์ฌ์ฉํ๋ฉด ์์คํ ์ ๋ ์ง์ ์๊ฐ์ ์ฌ์ฉํ ์ ์๋ ๊ฒ์ด์์!
์ ์ฑ | ๊ธฐ ๋ฅ | ๊ธฐ ๋ณธ ๊ฐ |
name | ํ๋์ ๋งคํํ ํ ์ด๋ธ ์ปฌ๋ผ ์ด๋ฆ ์ ์ | ๊ฐ์ฒด์ ํ๋ ์ด๋ฆ |
@LastModifiedDate
์กฐํํ Entity์ ๊ฐ์ ๋ณ๊ฒฝํ ๋, ๋ ์ง์ ์๊ฐ์ด ์๋์ผ๋ก ๋ณ๊ฒฝ๋์ด ์ ์ฅ๋๋ ๊ฒ์ด์์.
@ManyToOne
Member Entity์์ 1:N ๊ด๊ณ๋ฅผ ์ํด ์ฌ์ฉํ ๊ฒ์ด์์.
ํ ๋ช ์ ํ์์ ์ฌ๋ฌ๊ฐ์ ๊ฒ์๊ธ์ ๋จ๊ธธ ์ ์๊ณ , ์ด๊ฒ์ 1:N์ ๊ด๊ณ์ธ ๊ฒ์ด์์.
๊ทผ๋ฐ ์? @OneToMany๊ฐ ์๋๊ณ , @ManyToOne์ผ๊น์?
๊ทธ๊ฒ์ ๋ฐ๋ก ํด๋น Entity ๊ธฐ์ค์ผ๋ก ๋ฐ๋ผ๋ณด๊ณ ์ค์ ํด์ผ ํ๊ธฐ ๋๋ฌธ์ด์์. ์ฆ, SystemUseManul Entity ๊ธฐ์ค์ผ๋ก Member Entity์์ ๊ด๊ณ๋ฅผ ๋ํ๋ด๊ธฐ ์ํจ์ด์์.
์ด๋ ๊ฒ ํด์ค์ผ ๊ฒ์๊ธ์ ์์ฑํ ์์ฑ์ ์ ๋ณด ๋ฑ์ ๊ฐ์ ธ์ฌ ์ ์๋ ๊ฒ์ด์์!
๊ฒ์ํ์์๋ ๊ฒ์๊ธ ๊ณ ์ ๋ฒํธ(id), ๊ฒ์๊ธ ์ ๋ชฉ(title), ๊ฒ์๊ธ ๋ด์ฉ(contents)์ ์์ฑ์ผ(reg_date), ์์ ์ผ(mod_date) ๋ง์ง๋ง์ผ๋ก ์์ฑ์ ๋๋ค์์ด ๋์ค๋๋ก ํ ๊ฒ ์ด๋๋๋ค!
๐ SystemUseManualComment Entity
๐ SystemUseManualHashTag
๐ SystemUseManualImage
์ด๋ ๊ฒ Entity๋ค์ ๊ตฌ์ฑํ ๊ฒ์ด์์!
์ฃผ๋ํ๋์ ๊ธ์ด ๋ง์์ ๋์ จ๋์? ๊ตฌ๋ ๊ณผ ๊ณต๊ฐ! ๊ทธ๋ฆฌ๊ณ , ๋๊ธ ๊ทธ๋ฆฌ๊ณ ๋ฐฉ๋ช ๋ก์ ์ฃผ๋ํ๋์๊ฒ ๋ง์ ํ์ด ๋ฉ๋๋ค.