연재를 시작하기 전에 양해 부탁드리는 것이 하나 있습니다.
제가 올해 .NET 5년차 개발자로서 유수의 유명하신 개발자 분들의 아티클 같은 퀄리티를 내기에 부족함이 많습니다.
게다가 혼자 독학으로 배운 것이라 간혹 실무에 맞지 않는 경우도 있을 것입니다.
간혹 개념의 혼동이나 잘못된 설명이 있다면 과감하게 댓글 남겨주세요.
저는 "모르거나 잘못 알고 살아가는 것이 무섭지만, 누군가 제가 알고 있는 잘못된 정보와
제가 전혀 모르고 지낸 관련 정보를 깨우쳐 주는 분들은 항상 고맙게 생각합니다" ^^;;
하이버네이트(Hibernate)는 "ORM 프레임워크" 입니다.
"ORM? 그게 뭔데? 뭐 또 어려운거 튀어나와서 가뜩이나 힘겨운 개발자를 더 힘들게 하는 거야?!"
네, 맞습니다. 아직 경험하지 않은 분들에게 새로운 기술은 항상 버겹고 힘들죠.
저 또한 해보지 않은 기술을 해야하는 상황이 오면 일단 스트레스부터 생깁니다. 지금까지 배운 것도 많은데
왜 또 배워야 하는거야!!!
그래도 이 바닥에 들어오면서 다들 이런 상황에 대한 각오는 했을 겁니다.
떠나지 않는 이상 평생을 공부해야하는 직업
저는 이 부분을 나름대로 달리 생각하기로 했습니다. 어떠한 기술이 나오고 그 기술이 일련의 흐름(업무든 삶이든)을
좌우하거나 좌우할 수 있는 영향력이 있다고 판단 된다면
"내가 좀 더 편해질 수 있는 약간의 노력",
"특정상황(야근같은)에 노가다로 소비되는 아까운 시간을 없애버릴 수 있는 도구",
마지막으로
"남들과 다른 나를 볼 수 있는 자기 개발"
로 생각하는 겁니다.
항상 느끼는 것이지만 새로운 기술과 방법론은 과거의 반복되어진 문제에 대한 해결책인 경우가 많습니다.
그렇다는 것은 이제 반복되는 작업의 고통으로 벗어나 좀 더 생각할 수 있는 시간과 업무의 퀄리티에 집중 할
수 있는 기회가 주어진 것이라고 볼 수 있습니다.
여기를 찾아오시는 분들도 이렇게 생각하면서 마음이나마 평안을 찾았으면 합니다. (ㅋㅋ)
다시 본론으로 돌아가서 ORM 이 뭐의 약자인가 하면 "Object - Relational - Mapping" 의 약자입니다.
즉, 객체 관계 매핑이라는 개념으로 객체간의 관계를 맺는 뜻인데... 이게 뭔소리여... 라고 한다면
Database 의 관계 구조 (부모/자식처럼) 를 우리가 사용하는 프로그래밍 언어는 java, .net 등으로
풀어내는 기술을 뜻합니다.
예를 들어 DB의 부모 테이블명이 Parent 이고 자식 테이블이 Child 라면 이 둘의 테이블 관계는 1:N 이라고
보고 Child 테이블에는 부모 테이블인 Parent의 식별키가 참조 외래키로 적용되어 있을 것입니다.
이것을 프로그래밍으로 풀어낸다면 아래와 같습니다. (예제는 C#.NET 으로 하겠습니다)
public class Parent { public int ParentNo { get; set; } // 식별키 public int ParentName { get; set; } } public class Child { public int ChildNo { get; set; } // 식별키 public string ChildName { get; set; } public Parent MyParent { get; set; } }
Child 클래스의 멤버 속성 중 제일 하단에 MyParent 이라는 속성이 보일 것입니다.
이것이 Parent 클래스와 맺는 관계인 것입니다. MyParent 속성이 DB 관점에서는 부모 테이블에 대한 참조 외래키인
것이죠.
이렇게 데이터를 가져온다면 우리가 사용하는 IDE인 Visual studio 등에서 인텔리센스 기능으로 쉽게 부모 클래스에
접근(access)이 가능합니다. (* OOP 객체에서의 부모/자식 관계는 오해의 소지가 있을 수 있지만, 쉽게 설명하고자 DB 의
부모/자식 관계를 OOP에서도 같은 의미로 사용하도록 하겠습니다.)
그런데!
Child 기준에서는 Parent 에 접근이 편리한데 Parent 입장에서는 전혀 Child 에 접근할 방법이 없군요. 실제로 DB의
관계도 이와 같습니다. 부모 테이블은 자식 테이블의 어떠한 관계정보를 가지고 있지 않죠.
하지만, ORM은 이런 경우 DB 구조와는 다르게 접근이 용이하도록 설정할 수 있습니다.
아래와 같이 말이죠.
이것이 Parent 클래스와 맺는 관계인 것입니다. MyParent 속성이 DB 관점에서는 부모 테이블에 대한 참조 외래키인
것이죠.
이렇게 데이터를 가져온다면 우리가 사용하는 IDE인 Visual studio 등에서 인텔리센스 기능으로 쉽게 부모 클래스에
접근(access)이 가능합니다. (* OOP 객체에서의 부모/자식 관계는 오해의 소지가 있을 수 있지만, 쉽게 설명하고자 DB 의
부모/자식 관계를 OOP에서도 같은 의미로 사용하도록 하겠습니다.)
그런데!
Child 기준에서는 Parent 에 접근이 편리한데 Parent 입장에서는 전혀 Child 에 접근할 방법이 없군요. 실제로 DB의
관계도 이와 같습니다. 부모 테이블은 자식 테이블의 어떠한 관계정보를 가지고 있지 않죠.
하지만, ORM은 이런 경우 DB 구조와는 다르게 접근이 용이하도록 설정할 수 있습니다.
아래와 같이 말이죠.
public class Parent { public int ParentNo { get; set; } //식별키 public int ParentName { get; set; } public IList<Child> MyChilds { get; set; } } public class Child { public int ChildNo { get; set; } //식별키 public string ChildName { get; set; } public Parent MyParent { get; set; } }
Parent 클래스의 IList<> 타입의 속성이 보이시나요?! ILIst 인터페이스의 제네릭 타입으로 Child 클래스에 대한 컬렉션을
정의하고 있습니다. 이렇게 하면 Parent 입장에서 Child에 대한 접근이 가능해지는 것입니다.
이를 "객체망을 순회 한다고 합니다.
그런데 왜
처럼 단일 참조가 아니고
처럼 컬렉션이냐 하면, 본문 위를 살펴보시면 부모와 자식 관계를 1:N으로 정의했다는 내용을 찾으실 수 있을 것입니다.
1:N, 즉 "부모는 여러 자식을 가질 수 있지만, 자식은 오로지 한명의 부모만 존재한다".
그래서 컬렉션 타입인 것입니다.
이런식으로 풀어내면 DB의 모든 관계를 object 로 풀어낼 수 있습니다.
하지만 이렇게 정의했다고 DB와 매핑될 수 있는 것은 아닙니다. DB 입장에서는 자료형도 있고, 자료의 길이, 조회에
대한 규칙등이 객체 구조와 판이하게 다릅니다. 예를 들어 자료형만 보더라도 MS-SQL 기준에서
문자열 타입은 char, varchar, nvarchar 등이 있지만, 객체 관점에서는 이 모두가 String 일 뿐이죠.
(DB의 char와 OOP의 char는 다릅니다)
그리고 조회(탐색) 방법도 OOP와 DB는 구조적으로 다르기 때문에 쉽게 매핑될 수 없습니다.
이를 매핑하기 위해 직접 구현한다면 정말 많은 시간과 비용이 발생할 것입니다. 그런데 개념을 놓고 보면
어플리케이션 개발자 입장에서는 정말 편리합니다.
DB 쿼리에 신경 쓸 필요없이 객체 망을 통해 접근한다는 개념은 우리 어플리케이션 개발자가 친숙한 OOP
개발방식으로 비즈니스에 집중할 수 있는 시간을 만들어주고, 맨 위에서 언급한 반복되는 작업의 스트레스
로부터 벗어날 수 있습니다.
그래서 나온 프레임워크가 ORM 프레임워크입니다.
그리고 이렇게 OOP - DB 간의 쉽게 맺을 수 없는 구조적 문제 (임피던스 불일치)를 해결해주는 도구로는
iBatis, (N)Hibernate, Code First 등이 있으며 그 중 가장 많은 기능과 진정한 ORM로 불리우고 많이 사용되고 있는
하이버네이트를 연재하게 되었습니다.
정의하고 있습니다. 이렇게 하면 Parent 입장에서 Child에 대한 접근이 가능해지는 것입니다.
이를 "객체망을 순회 한다고 합니다.
그런데 왜
public Child MyChild { get; set; }
처럼 단일 참조가 아니고
public IList<Child> MyChilds { get; set; }
처럼 컬렉션이냐 하면, 본문 위를 살펴보시면 부모와 자식 관계를 1:N으로 정의했다는 내용을 찾으실 수 있을 것입니다.
1:N, 즉 "부모는 여러 자식을 가질 수 있지만, 자식은 오로지 한명의 부모만 존재한다".
그래서 컬렉션 타입인 것입니다.
이런식으로 풀어내면 DB의 모든 관계를 object 로 풀어낼 수 있습니다.
하지만 이렇게 정의했다고 DB와 매핑될 수 있는 것은 아닙니다. DB 입장에서는 자료형도 있고, 자료의 길이, 조회에
대한 규칙등이 객체 구조와 판이하게 다릅니다. 예를 들어 자료형만 보더라도 MS-SQL 기준에서
문자열 타입은 char, varchar, nvarchar 등이 있지만, 객체 관점에서는 이 모두가 String 일 뿐이죠.
(DB의 char와 OOP의 char는 다릅니다)
그리고 조회(탐색) 방법도 OOP와 DB는 구조적으로 다르기 때문에 쉽게 매핑될 수 없습니다.
이를 매핑하기 위해 직접 구현한다면 정말 많은 시간과 비용이 발생할 것입니다. 그런데 개념을 놓고 보면
어플리케이션 개발자 입장에서는 정말 편리합니다.
DB 쿼리에 신경 쓸 필요없이 객체 망을 통해 접근한다는 개념은 우리 어플리케이션 개발자가 친숙한 OOP
개발방식으로 비즈니스에 집중할 수 있는 시간을 만들어주고, 맨 위에서 언급한 반복되는 작업의 스트레스
로부터 벗어날 수 있습니다.
그래서 나온 프레임워크가 ORM 프레임워크입니다.
그리고 이렇게 OOP - DB 간의 쉽게 맺을 수 없는 구조적 문제 (임피던스 불일치)를 해결해주는 도구로는
iBatis, (N)Hibernate, Code First 등이 있으며 그 중 가장 많은 기능과 진정한 ORM로 불리우고 많이 사용되고 있는
하이버네이트를 연재하게 되었습니다.
'연재 > NHibernate' 카테고리의 다른 글
[챕터5] 도메인 모델간의 연관(association)관계 설정 - 1 대 N (3) | 2011.08.20 |
---|---|
[챕터4] XML 매핑 클래스에 대한 테이블 스키마를 실제 DB에 생성해보자. (2) | 2011.08.07 |
[챕터3] 도메인 모델 작성 및 간단한 하이버네이트 XML 매핑 (0) | 2011.08.07 |
[챕터2] 프로젝트 시작하기 (0) | 2011.07.31 |
[챕터1] NHibernate 2 (0) | 2011.07.31 |