개발/Spring

[Spring] JPA Auditing

뽀글뽀글 개발자 2023. 12. 30. 15:37

JPA Auditing이란?

생성자, 수정자, 생성 시간, 수정 시간과 같은 메타 데이터를 자동으로 관리할 수 있는 JPA 라이브러리이다.

 

 

Auditing 적용방법

@EnableJpaAuditing

JPA Auditing 기능을 활성화하는 애노테이션으로 꼭 활성화를 시켜주어야 Auditing이 정상적으로 동작한다.

* Config class에서 @EnableJpaAuditing을 넣어주어도 무방하다.

@EnableJpaAuditing
@SpringBootApplication
public class Application {

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }

}

 

@EntityListners

Auditing을 적용할 엔티티 클래스에 리스너를 넣어줌으로써 해당 엔티티의 영속, 수정 이벤트를 감지하여 Auditing을 적용시킬 수 있다.

 

@CreatedBy, @LastModifiedBy, @CreatedDate, @LastModifiedDate

각 애노테이션을 붙어 해당 컬럼에 생성자, 수정자, 생성 시간, 수정 시간을 적용시킬 수 있다.

@Getter
@ToString
@EntityListeners(AuditingEntityListener.class)
@MappedSuperclass
public abstract class AuditingFields {

    @DateTimeFormat(iso = DateTimeFormat.ISO.DATE_TIME)
    @CreatedDate
    @Column(nullable = false, updatable = false)
    private LocalDateTime createdAt; // 생성일시

    @CreatedBy
    @Column(nullable = false, updatable = false, length = 100)
    private String createdBy; // 생성자

    @DateTimeFormat(iso = DateTimeFormat.ISO.DATE_TIME)
    @LastModifiedDate
    @Column(nullable = false)
    private LocalDateTime modifiedAt; // 수정일시

    @LastModifiedBy
    @Column(nullable = false, length = 100)
    private String modifiedBy; // 수정자

}

 

 

AuditorAware

AuditorAware 설정을 통해 @CreatedBy, @LastModifiedBy에 의해 작성되는 유저의 이름 또는 아이디 등을 지정해줄 수 있다.

/*
	AuditorAware의 제네릭 타입은 @CreatedBy에 들어가는 값의 타입으로
    유저의 이름이라면 String, 아이디라면 Long을 넣어주면 된다.
    
    아래 코드는 Security의 인증 정보를 받아와서 유저이름을 넣어주는 코드이다.
*/
@EnableJpaAuditing
@Configuration
public class JpaConfig {

    @Bean
    public AuditorAware<String> auditorAware() {
        return () -> Optional.ofNullable(SecurityContextHolder.getContext())
                .map(SecurityContext::getAuthentication)
                .filter(Authentication::isAuthenticated)
                .map(Authentication::getPrincipal)
                .map(BoardPrincipal.class::cast)
                .map(BoardPrincipal::getUsername);
    }

}