크게 두 가지로 나눌 수 있습니다. 프록시를 사용하는 방법과 그렇치 않은 방법. 좀 더 세밀하게 나누면, 여러 방법이 있지만 구현되어 있는 특징을 기준으로 나누면 AOP를 사용한 방법과 그렇치 않은 방법으로 나눌 수 있고 그 두 방법의 대표자로 각각 @Transactional과 PlatformTransactionManager을 꼽을 수 있습니다.

PlatformTransactionManager
1. 트랜잭션 범위를 세밀하게 조정할 수 있다.
2. 코드가 지져분해진다. 템플릿을 이용하면 어느 정도는 청소할 수 있지만 한계는 있다.
3. 메소드 접근 지시자를 신경쓰지 않아도 된다.
4. 롤백 시킬 예외를 명시적으로 catch 블럭에서 잡아줘야 한다.

@Transactional을 사용할 때 주의
1. 코드가 깔끔해진다.
2. public 메소드만 트랜잭션 처리가 된다는 것을 알아둬야 한다.
3. 세밀하게 적용하려면 해당 부분을 별도의 public 메소드로 빼내야 한다.
4. RuntimeException은 기본으로 롤백해버리고 Catched Exception중에서도 롤백하고 싶은게 있으면 별도의 설정을 필요로 한다.

여기에 하나더, @Transactional을 사용할 때 만약 인터페이스가 아니라 클래스의 프록시 객체를 사용할 때, CGLib을 사용하게 되는데, CGLib 좀 별로임. 성능도 떨어지고 리플랙션 할 떄 문제도 있는 것 같고.. 따라서 프록시 사용할 때는 무조건 인터페이스 기반으로 만들어서 JDK의 프록시 사용하도록 할 것.