ORM(Object-Relational Mapping)
κ°μ²΄ μ§ν₯ νλ‘κ·Έλλ° μΈμ΄μμ κ΄κ³ν λ°μ΄ν°λ² μ΄μ€(RDB)λ₯Ό μ¬μ©ν λ κ°μ²΄(Object)μ λ°μ΄ν°λ² μ΄μ€μ κ΄κ³(Relation)λ₯Ό λ§€ννλ κΈ°μ
β’
Persistence Framework
β¦
ORM
β¦
SQL Mapper
β’
ORM vs SQL Mapper
Persistence Framework
β’
ORM
β’
SQL Mapper
Persistence Framework
λ°μ΄ν°λ₯Ό μꡬμ μΌλ‘ μ μ₯νκ³ κ΄λ¦¬νλ νλ μμν¬λ‘, ORM(JPA, Hibernate)κ³Ό SQL Mapper(MyBatis) λ±μ΄ ν¬ν¨λλ©°, SQL μμ± λ°©μκ³Ό κ°μ²΄ λ§€ν λ°©μμ λ°λΌ ꡬλΆλ©λλ€.
ORM (Object-Relational Mapping)
ORMμ΄λ?
κ°μ²΄μ λ°μ΄ν°λ² μ΄μ€μ ν
μ΄λΈμ μλμΌλ‘ λ§€ννλ κΈ°μ μ
λλ€. κ°λ°μκ° SQLμ μ§μ μμ±νμ§ μκ³ , κ°μ²΄λ₯Ό μ‘°μνλ©΄ ORMμ΄ μλμΌλ‘ SQLμ μμ±νμ¬ λ°μ΄ν°λ² μ΄μ€μ ν΅μ ν©λλ€.
ORM νΉμ§ (ν)
κ΅¬λΆ | μ€λͺ
|
κ°μ²΄(Entity)μ ν
μ΄λΈ(Table)μ μλ λ§€ν | κ°μ²΄μ ν
μ΄λΈμ 1:1 λλ N:1 λ±μ κ΄κ³λ‘ λ§€ν |
SQLμ μ§μ μμ±ν νμ μμ | κ°μ²΄μ CRUD(Create, Read, Update, Delete) μμ
μ΄
λ©μλ νΈμΆλ§μΌλ‘ κ°λ₯ |
νΈλμμ
κ΄λ¦¬ μλν | ORMμ΄ νΈλμμ
μ μλμΌλ‘ κ΄λ¦¬ |
μ§μ° λ‘λ©(Lazy Loading),
μ¦μ λ‘λ©(Eager Loading) | μ°κ΄λ λ°μ΄ν°λ₯Ό μΈμ λΆλ¬μ¬μ§ μ€μ κ°λ₯ |
ORMμ μ₯λ¨μ (ν)
μ₯μ | μ€λͺ
|
μμ°μ± μ¦κ° | SQLμ μ§μ μμ±νμ§ μμλ κ°μ²΄ μ‘°μλ§μΌλ‘ λ°μ΄ν° μ²λ¦¬κ° κ°λ₯ |
μ μ§λ³΄μ μ©μ΄ | λΉμ¦λμ€ λ‘μ§κ³Ό SQLμ΄ λΆλ¦¬λμ΄ μ½λ κ°λ
μ±μ΄ λμ |
λ°μ΄ν°λ² μ΄μ€ λ
λ¦½μ± | ORM νλ μμν¬κ° SQLμ μμ±νλ―λ‘ DBMS λ³κ²½μ΄ μ©μ΄ |
κ°μ²΄μ§ν₯μ μΈ κ°λ° κ°λ₯ | μν°ν° ν΄λμ€λ₯Ό νμ©νμ¬ κ°μ²΄ μ§ν₯μ μΈ μ€κ³ κ°λ₯ |
λ¨μ | μ€λͺ
|
μ±λ₯ μ΅μ ν μ΄λ €μ | μλ μμ±λ SQLμ΄ λΉν¨μ¨μ μΌ μ μμ |
볡μ‘ν 쿼리 μμ± μ΄λ €μ | λ€μ€ JOINμ΄λ νΉμ DBMS κΈ°λ₯μ νμ©νλ €λ©΄ Native Query νμ |
νμ΅ κ³‘μ μ΄ λμ | JPA/Hibernateμ κ°λ
(μ§μ° λ‘λ©, μμμ± μ»¨ν
μ€νΈ λ±)μ μ΄ν΄ν΄μΌ ν¨ |
λνμ μΈ ORM κΈ°μ (ν)
κΈ°μ | μ€λͺ
|
JPA (Java Persistence API) | μλ° ORM κΈ°μ νμ€ μΈν°νμ΄μ€ |
Hibernate | JPAμ λνμ μΈ κ΅¬ν체 |
EclipseLink, OpenJPA | JPAμ λ€λ₯Έ ꡬν체 |
ORM μμ (JPA & Hibernate)
@Entity
@Table(name = "users")
public class User {
@Id @GeneratedValue
private Long id;
private String name;
private String email;
}
Java
볡μ¬
// λ°μ΄ν° μ μ₯ (SQL μ§μ μμ± μμ΄ ORMμ΄ μ²λ¦¬)
User user = new User();
user.setName("John Doe");
user.setEmail("john@example.com");
entityManager.persist(user); // INSERT SQL μλ μ€ν
Java
볡μ¬
SQL Mapper
SQL Mapperλ?
SQL Mapperλ κ°λ°μκ° μ§μ SQLμ μμ±νκ³ , μ€ν κ²°κ³Όλ₯Ό κ°μ²΄μ λ§€ννλ λ°©μμ
λλ€. SQL μμ±μ μμ λκ° λμ 볡μ‘ν 쿼리λ μ½κ² μμ±ν μ μμ§λ§, SQLμ μ§μ κ΄λ¦¬ν΄μΌ ν©λλ€.
SQL Mapper νΉμ§ (ν)
κ΅¬λΆ | μ€λͺ
|
SQLμ μ§μ μμ±ν΄μΌ ν¨ | ORMμ²λΌ μλ μμ±λμ§ μμΌλ©°, SQLμ κ°λ°μκ° λͺ
μμ μΌλ‘ μμ±ν΄μΌ ν¨ |
SQL μ€ν κ²°κ³Όλ₯Ό κ°μ²΄μ λ§€ν | SQLμ μ€ννκ³ , κ²°κ³Όλ₯Ό μλμΌλ‘ κ°μ²΄μ ν λΉ |
DBMS μ’
μμ | DBμ λ§μΆ° SQLμ μ΅μ νν μ μμ§λ§, νΉμ DBMSμ μ’
μλ κ°λ₯μ±μ΄ λμ |
SQL Mapperμ μ₯λ¨μ (ν)
μ₯μ | μ€λͺ
|
SQLμ μ§μ 컨νΈλ‘€ κ°λ₯ | ORMλ³΄λ€ SQL μ΅μ νκ° μ¬μ |
볡μ‘ν 쿼리 μμ± μ©μ΄ | JOIN, μλΈμΏΌλ¦¬, κ·Έλ£Ήν λ±μ΄ μμ λ‘μ |
λ°°μ°κΈ° μ¬μ | SQLμ μκ³ μλ€λ©΄ λ³λ€λ₯Έ μΆκ° νμ΅ μμ΄ μ¬μ© κ°λ₯ |
λ¨μ | μ€λͺ
|
λΉμ¦λμ€ λ‘μ§κ³Ό SQLμ΄ νΌμ¬λ κ°λ₯μ± | μ μ§λ³΄μκ° μ΄λ €μΈ μ μμ |
DBMS μ’
μμ± | DB λ³κ²½ μ SQLμ μμ ν΄μΌ ν κ°λ₯μ±μ΄ λμ |
νΈλμμ
κ΄λ¦¬ λ³λ νμ | ORMμ²λΌ μλ νΈλμμ
κ΄λ¦¬ κΈ°λ₯ μμ |
λνμ μΈ SQL Mapper κΈ°μ (ν)
κΈ°μ | μ€λͺ
|
MyBatis | Java κΈ°λ° λνμ μΈ SQL Mapper νλ μμν¬ |
iBatis | MyBatisμ μ΄μ λ²μ |
SQL Mapper μμ (MyBatis)
β XML κΈ°λ° SQL μ μ
<mapper namespace="UserMapper">
<select id="getUserById" parameterType="int" resultType="User">
SELECT * FROM users WHERE id = #{id}
</select>
</mapper>
XML
볡μ¬
β‘ Java μ½λμμ SQL μ€ν
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
User user = userMapper.getUserById(1);
Java
볡μ¬
ORM vs SQL Mapper, μ΄λ€ κ±Έ μ νν΄μΌ ν κΉ?
ORMμ΄ μ ν©ν κ²½μ°
β’
κ°μ²΄ μ§ν₯μ μΈ κ°λ°μ΄ νμν λ
β’
λΉμ¦λμ€ λ‘μ§κ³Ό λ°μ΄ν°λ² μ΄μ€ λ‘μ§μ λΆλ¦¬νκ³ μΆμ λ
β’
λ°μ΄ν°λ² μ΄μ€ λ³κ²½ κ°λ₯μ±μ΄ λμ λ (ORMμ DB λ
립μ±μ΄ λμ)
β’
μλνλ νΈλμμ
κ΄λ¦¬κ° νμν λ
SQL Mapperκ° μ ν©ν κ²½μ°
β’
볡μ‘ν SQL 쿼리λ₯Ό μμ£Ό μμ±ν΄μΌ ν λ
β’
SQL μ΅μ νκ° μ€μν νλ‘μ νΈ
β’
λμ©λ λ°μ΄ν° μ²λ¦¬(ORMλ³΄λ€ SQL νλμ΄ μ©μ΄)
β’
DBMSμ λ§μΆ° μ±λ₯μ μ΅μ νν΄μΌ ν λ
κ²°λ‘ : ORMκ³Ό SQL Mapperλ λͺ©μ μ λ°λΌ μ ννμ!
ORMκ³Ό SQL Mapperλ κ°μ μ₯λ¨μ μ΄ μμΌλ©°, νλ‘μ νΈ μ±κ²©μ λ°λΌ μ μ ν λ°©μμ μ νν΄μΌ ν©λλ€.
β’
ORMμ κ°μ²΄ μ€μ¬μ μΈ κ°λ°κ³Ό μ μ§λ³΄μκ° μ½μ΅λλ€.
β’
SQL Mapperλ SQL μ΅μ νμ 볡μ‘ν 쿼리 μμ±μ΄ μ 리ν©λλ€.
β’
λ κ°μ§λ₯Ό λ³ννμ¬ μ¬μ©ν μλ μμ (μ: κΈ°λ³Έμ μΈ CRUDλ ORM, 볡μ‘ν 쿼리λ SQL Mapper νμ©)
ORM vs SQL Mapper
κ΅¬λΆ | ORM (Object-Relational Mapping) | SQL Mapper |
κ°λ
| κ°μ²΄μ κ΄κ³ν λ°μ΄ν°λ² μ΄μ€λ₯Ό μλμΌλ‘
λ§€ννμ¬ SQL μμ΄ λ°μ΄ν° μ‘°μ κ°λ₯ | SQLμ μ§μ μμ±νκ³ κ²°κ³Όλ₯Ό κ°μ²΄μ λ§€ν |
SQL μμ± | μλμΌλ‘ μμ± (JPQL, Criteria API λ± μ¬μ©) | μ§μ SQL μμ± (κ°λ°μκ° μ»¨νΈλ‘€) |
μ μ°μ± | κ°μ²΄ μ€μ¬μ μΈ λ°μ΄ν° μ‘°μ (DBMS λ
립μ ) | SQL μ€μ¬μ μΈ λ°μ΄ν° μ‘°μ (DBMS μ’
μμ ) |
νμ΅ λμ΄λ | μλμ μΌλ‘ λμ (μ§μ° λ‘λ©, μ°κ΄ κ΄κ³ μ€μ λ±) | λΉκ΅μ μ¬μ (SQLμ μ΄λ―Έ μκ³ μλ€λ©΄) |
νΌν¬λ¨Όμ€ μ΅μ ν | SQL νλμ΄ μ΄λ ΅κ³ , μλ μμ±λ μΏΌλ¦¬κ° λΉν¨μ¨μ μΌ μ μμ | SQLμ μ§μ μμ±νλ―λ‘ μ±λ₯ μ΅μ ν μ©μ΄ |
볡μ‘ν 쿼리 | 볡μ‘ν JOIN, μλΈμΏΌλ¦¬ λ±μ΄ μ΄λ €μΈ μ μμ (Native Query νμ) | 볡μ‘ν 쿼리 μμ±μ΄ μμ λ‘μ |
νΈλμμ
κ΄λ¦¬ | μλμΌλ‘ κ΄λ¦¬ (Spring, Hibernate μ§μ) | μ§μ κ΄λ¦¬ νμ |
μΊμ± μ§μ | 1μ°¨ μΊμ, 2μ°¨ μΊμ μ§μ (JPA/Hibernate) | μΊμ κΈ°λ₯ μμ (λ³λ ꡬν νμ) |
λν κΈ°μ | JPA, Hibernate, EclipseLink, OpenJPA | MyBatis, iBatis |
νλμ 보λ μ°¨μ΄μ
β’
ORM: SQLμ μ§μ λ€λ£¨μ§ μκ³ κ°μ²΄ μ€μ¬μΌλ‘ λ°μ΄ν° μ‘°μ β μλν, μ μ§λ³΄μ νΈλ¦¬
β’
SQL Mapper: SQLμ μ§μ μμ±νμ¬ DBλ₯Ό μ‘°μ β μ μ°μ±, μ±λ₯ νλ μ©μ΄
β’
ORMμ΄ μ ν©ν κ²½μ°: λ°μ΄ν° λͺ¨λΈμ΄ κ°μ²΄ μ§ν₯μ μΌλ‘ μ€κ³λμ΄ μκ³ , SQLμ μ΅μννλ©° μ μ§λ³΄μλ₯Ό μ½κ² νκ³ μΆμ λ
β’
SQL Mapperκ° μ ν©ν κ²½μ°: 볡μ‘ν μΏΌλ¦¬κ° λ§κ±°λ, μ±λ₯ νλμ΄ μ€μνλ©° SQLμ μ§μ 컨νΈλ‘€ν΄μΌ ν λ




