선행 필요 : [Spring] JPA와 ORM
JDBC (Java Database Connectivity)
JDBC는 Persistence Framework 중 하나이며 Java 애플리케이션에서 데이터베이스에 접근하기 위한 표준 API입니다. 가장 기본적인 데이터베이스 접근 방법으로, 많은 프레임워크들이 JDBC 위에 구축되어 있습니다.
모든 주요 관계형 데이터베이스 관리 시스템은 JDBC 드라이버를 제공하며, 이를 통해 Java 애플리케이션에서 데이터베이스에 접근할 수 있습니다.
- 특징:
- 데이터베이스 독립적인 연결 인터페이스 제공
- 저수준의 데이터베이스 작업 제어 가능
- 높은 유연성
- 예시:
try (Connection conn = DriverManager.getConnection(DB_URL, USER, PASS);
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SELECT id, name, email FROM users")) {
while (rs.next()) {
int id = rs.getInt("id");
String name = rs.getString("name");
String email = rs.getString("email");
// Process the result
}
} catch (SQLException e) {
e.printStackTrace();
}
Object Mapping (SQL Mapper)
1. MyBatis
마이바티스(MyBatis)는 SQL 매퍼 프레임워크로 Java 애플리케이션에서 관계형 데이터베이스를 쉽게 사용할 수 있도록 지원하는 지속성 프레임워크입니다.
MyBatis는 SQL 쿼리, 저장 프로시저, 고유한 매핑 규칙 등을 사용할 수 있으며, 개발자가 XML이나 어노테이션을 통해 SQL을 명확하게 정의할 수 있게 해줍니다.
MyBatis를 사용하여 DBMS와 RDBMS에 커넥션하는 과정은 일반적인 JDBC를 사용하는 것과 유사하지만, MyBatis는 더 많은 추상화와 편의 기능을 제공합니다.
- 특징
- SQL 중심: JPA나 Hibernate 같은 ORM(Object Relational Mapping)과 달리, SQL을 직접 제어할 수 있어 복잡한 쿼리를 효율적으로 처리할 수 있습니다.
- XML 매핑 및 애노테이션 지원: SQL 매핑을 XML 파일이나 애노테이션을 통해 설정할 수 있습니다.
- 유연한 매핑: 복잡한 관계형 매핑을 유연하게 처리할 수 있습니다.
- SQL 재사용: SQL 쿼리를 재사용할 수 있는 기능을 제공하여 유지보수를 쉽게 합니다.
- 자동 매핑: 쿼리 결과를 Java 객체로 자동으로 매핑해 줍니다.
- Mapper 인터페이스 예시 :
@Mapper
public interface UserMapper {
@Select("SELECT * FROM users WHERE id = #{id}")
User findById(Long id);
@Insert("INSERT INTO users(name, email) VALUES(#{name}, #{email})")
@Options(useGeneratedKeys = true, keyProperty = "id")
void insert(User user);
@Update("UPDATE users SET name = #{name}, email = #{email} WHERE id = #{id}")
void update(User user);
@Delete("DELETE FROM users WHERE id = #{id}")
void delete(Long id);
}
@Mapper 어노테이션을 사용하면 MyBatis가 자동으로 구현체 생성
SQL을 직접 작성할 수 있어 최적화 및 유지보수가 쉬움
- XML 기반 Mapper 예시 :
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.example.mapper.UserMapper">
<select id="findById" parameterType="long" resultType="com.example.dto.User">
SELECT * FROM users WHERE id = #{id}
</select>
<insert id="insert" parameterType="com.example.dto.User" useGeneratedKeys="true" keyProperty="id">
INSERT INTO users (name, email) VALUES (#{name}, #{email})
</insert>
<update id="update" parameterType="com.example.dto.User">
UPDATE users SET name = #{name}, email = #{email} WHERE id = #{id}
</update>
<delete id="delete" parameterType="long">
DELETE FROM users WHERE id = #{id}
</delete>
</mapper>
SQL과 Java 코드를 분리하여 유지보수성을 높일 수 있음
복잡한 쿼리는 XML을 사용하면 가독성이 더 좋아짐
2. Apache iBATIS (MyBatis의 전신)
Apache iBATIS는 MyBatis의 전신으로, SQL 매퍼 프레임워크입니다. MyBatis는 iBATIS의 업그레이드 버전입니다.
- 특징:
- SQL 매퍼를 통해 SQL 쿼리를 명확하게 정의
- 단순하고 가벼운 프레임워크
- SQL 쿼리와 Java 객체 간의 매핑 지원
이 외에도 다양한 프레임워크와 라이브러리가 존재하며, 각각의 특성과 요구사항에 따라 적절한 것을 선택하여 사용할 수 있습니다. MyBatis는 SQL을 명확하게 제어하고자 하는 경우에 유용하며, Hibernate나 JPA는 더 높은 수준의 추상화를 제공하여 복잡한 데이터 모델을 처리하는 데 유리합니다. Spring Data JPA는 스프링 애플리케이션과의 통합이 쉽고 간편한 데이터 액세스를 제공합니다.
3. Spring JDBC
Spring JDBC는 스프링 프레임워크의 일부로, JDBC를 사용한 데이터 액세스를 단순화하고 템플릿 메서드를 제공합니다.
- 특징:
- JDBC 코드의 중복을 줄이고 간결하게 함
- 예외 처리를 단순화
- 트랜잭션 관리를 쉽게 할 수 있음
- 예시:
@Repository
public class UserRepository {
@Autowired
private JdbcTemplate jdbcTemplate;
public List<User> findAll() {
return jdbcTemplate.query("SELECT id, name, email FROM users",
(rs, rowNum) -> new User(rs.getInt("id"), rs.getString("name"), rs.getString("email")));
}
}
ORM(Object-Relational Mapping)
ORM(Object-Relational Mapping)은 객체 지향 프로그래밍 언어를 사용하여 호환되지 않는 유형의 시스템 간에 데이터를 변환하는 프로그래밍 기술입니다. 즉, 객체와 관계형 데이터베이스의 데이터를 매핑하는 것을 의미합니다.
ORM을 사용하면 SQL 쿼리 없이 데이터를 데이터베이스에 저장하고 관리할 수 있습니다.
이는 개발자가 객체 지향 프로그래밍에 더 집중할 수 있게 해주며, 데이터베이스 설계와 비즈니스 로직 사이의 간극을 줄여줍니다. 따라서 ORM은 백엔드 개발에서 중요한 역할을 합니다.
ORM의 사용은 SQL문법 대신 어플리케이션의 개발언어를 그대로 사용할 수 있게 함으로써, 개발 언어의 일관성과 가독성을 높이고, 유지 보수를 용이하게 하며, 데이터베이스와의 결합도를 낮추는 등 여러 장점을 제공합니다. 이는 개발 과정을 더욱 효율적으로 만들어 줍니다.
ORM은 다양한 프로그래밍 언어와 프레임워크에서 지원되며, Java의 Hibernate, Python의 SQLAlchemy, Ruby의 ActiveRecord 등이 대표적인 ORM 라이브러리입니다.
ORM의 주요 기능
ORM의 주요 기능으로는 객체와 테이블 간의 매핑, 데이터 쿼리 및 조작, 트랜잭션 관리 등이 있습니다. 이 기능들은 개발자가 복잡한 SQL 쿼리 없이도 데이터베이스를 효과적으로 다룰 수 있게 해줍니다.
ORM 장점
- 객체 지향적인 코드로 인해 더 직관적이고, 비즈니스 로직에 더 집중할 수 있게 도와줍니다.
ORM을 이용하면 SQL 쿼리가 아닌 직관적인 코드로 데이터를 조작할 수 있어 개발자가 객체 지향 프로그래밍하는 데 집중할 수 있도록 도와줍니다.
선언문, 할당, 종료 같은 부수적인 코드가 없거나 급격히 줄어듭니다.
각종 객체에 대한 코드를 별도록 작성하기 때문에 코드의 가독성을 올려줍니다.
SQL의 절차적이고 순차적인 접근이 아닌 객체 지향적인 접근으로 인해 생산성이 증가합니다.
- 재사용성 및 유지보수의 편리성이 증가합니다.
ORM은 독립적으로 작성되어있고, 해당 객체들을 재활용할 수 있습니다.
이로 인해 모델에서 가공된 데이터를 컨트롤러에 의해 뷰와 합쳐지는 형태로 디자인 패턴을 견고하게 다지는데 유리합니다.
매핑정보가 명확하여 ERD를 보는 것에 대한 의존도를 낮출 수 있습니다.
- DBMS에 대한 종속성이 줄어듭니다.
대부분 ORM 솔루션은 DB에 종속적이지 않습니다.
종속적이지 않다는 것은 구현 방법 뿐만 아니라 많은 솔루션에서 자료형 타입까지 유효하다는 것입니다.
개발자는 Object에 집중함으로써 극단적으로 DBMS를 교체하는 거대한 작업에도 비교적 적은 리스크와 시간이 소요됩니다.
또한 자바에서 가공할 경우 equals, hashCode의 오버라이드 같은 자바의 기능을 이용할 수 있고, 간결하고 빠른 가공이 가능해집니다.
ORM 단점
- 완벽한 ORM으로만 서비스를 구현하기가 어렵습니다.
사용하기는 편하지만 설계는 매우 신중하게 해야합니다.
프로젝트의 복잡성이 커질 경우 ORM 구현 난이도가 증가 할 수 있습니다.
잘못 구현된 경우에 속도 저하 및 심각할 경우 일관성이 무너지는 문제점이 생길수 있습니다.
- 프로시저가 많은 시스템에서는 ORM의 객체 지향적인 장점을 활용하기 어렵습니다.
이미 프로시저가 많은 시스템에서는 다시 객체로 바꿔야함, 그 과정에서 생산성 저하나 리스크가 많이 발생할 수 있습니다.
- 프로젝트의 복잡성이 높아질 경우, 난이도가 높아집니다.
- 잘못 구현하면 속도 저하 및 일관성이 무너질 수 있습니다.
1. Hibernate
Hibernate는 가장 널리 사용되는 ORM 프레임워크로, 객체 지향 프로그래밍의 데이터 모델을 관계형 데이터베이스의 데이터 모델에 매핑합니다.
- 특징:
- 객체 지향 쿼리 언어(HQL) 지원
- 자동화된 테이블 생성 및 데이터베이스 스키마 관리
- 캐싱 메커니즘을 통한 성능 최적화
- 복잡한 관계 및 상속 구조 매핑 지원
- 예시:
SessionFactory sessionFactory = new Configuration().configure().buildSessionFactory();
Session session = sessionFactory.openSession();
Transaction transaction = session.beginTransaction();
Member member = new Member();
member.setName("John Doe");
session.save(member); // INSERT 실행
transaction.commit();
session.close();
sessionFactory.close();
2. JPA (Java Persistence API)
JPA는 Java EE와 Jakarta EE 표준의 일부로, Java 객체를 관계형 데이터베이스에 매핑하기 위한 표준 명세입니다. Hibernate는 JPA의 구현체 중 하나입니다.
- 특징:
- 표준화된 API로 다양한 구현체와 호환 가능
- 애노테이션을 통한 매핑 정의
- JPQL(Java Persistence Query Language) 지원
예시:
EntityManagerFactory emf = Persistence.createEntityManagerFactory("my-persistence-unit");
EntityManager em = emf.createEntityManager();
em.getTransaction().begin();
Member member = new Member();
member.setName("John Doe");
em.persist(member); // INSERT 실행
em.getTransaction().commit();
em.close();
emf.close();
3. Spring Data JPA
Spring Data JPA는 스프링 프레임워크의 일부로, JPA 기반의 데이터 액세스를 단순화하고 추상화합니다.
- 특징:
- JPA를 사용한 데이터 액세스의 단순화
- CRUD 기능을 자동으로 생성
- 페이징 및 정렬 지원
- 커스텀 쿼리 메서드 정의 가능
- 예시:
@Entity
public class Member {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(nullable = false, length = 50)
private String name;
}
- @Entity → JPA에서 사용되는 엔티티 클래스
- @Id, @GeneratedValue(strategy = GenerationType.IDENTITY) → 기본 키 자동 증가 설정
- @Column(nullable = false, unique = true) → 필드 제약 조건 설정
public interface MemberRepository extends JpaRepository<Member, Long> {
List<Member> findByName(String name); // 자동으로 쿼리 생성
}
- JpaRepository<Member, Long> 상속 → 기본 CRUD 메서드 자동 제공
- 별도의 구현 없이 save(), findById(), findAll(), deleteById() 등 사용 가능
@Service
@RequiredArgsConstructor
public class MemberService {
private final MemberRepository memberRepository;
@Transactional
public Member saveMember(String name) {
Member member = new Member();
member.setName(name);
return memberRepository.save(member); // INSERT 실행
}
}
- @Service → 서비스 클래스 선언
- @Transactional → JPA 트랜잭션 관리
- save() → Spring Data JPA의 기본 메서드 활용하여 회원 저장
연관된 글 :
JPA, Hibernate, Spring Data JPA 차이점 정리
참고:
https://hahahoho5915.tistory.com/47
https://minsu092274.tistory.com/33
https://mysterlee.tistory.com/49
'개발 > DB' 카테고리의 다른 글
데이터베이스(DB)와 관계형데이터베이스(RDBMS) (0) | 2024.06.06 |
---|---|
DML/DDL/DCL (0) | 2024.06.06 |
[PROCEDURE] 프로시저 (0) | 2023.07.10 |
[DB] postgreSQL (0) | 2023.06.12 |
[MYSQL/SQL] HEX , UNHEX 16진수 데이터 (0) | 2023.04.29 |