티스토리 뷰

반응형

2회에 이어 이제 본격적으로 시작을 해보자. 테이블 명세서는 1회에 있는 내용을 사용해서 만들 것이니 참고를 하면 돼고, 이번에는 Code First란 무엇인지 먼저 좀 알아보고, Code First를 이용해서 클래스를 만들고 데이터베이스를 만드는 과정을 하나 하나 보도록 하겠다.

1. 목표

1회에 보면 귀차니즘으로 인해 Model First로 작업을 하겠다고 했었는데..어쩔 수 없이 Code First로 작업을 해야한다. 이건 사연이 좀 있는데 엠에스에서 얼마전 EF(Entity Framework) 4.2를 정식 버전 배포를 했었는데.. 지금 사용하고 있는 EF버전은 4.1이다. 그러다 보니 Package형태로 배포가 된것인 듯하고, 또한 오직 Code First만을 지원한다....(이걸 알기 위해 몇시간 삽질을 했다는..)

음..아마도 다음에 EF4.5정도가 나오면 아마 두개가 합해져서 나오지 않을까 생각하며, 이 강좌(게시판 만들기)에서는 몇가지만 가지고 가면 될 것이다.

1-1. Code First 사용 방법

1-2. SQL Server Compact 4.0 - Streamlined Database의 개념 및 사용법

1-3. WCF RIA Service Support EF4.1 사용 방법

2. 강좌 관련 사이트 정리

ado.net team blog
http://blogs.msdn.com/b/adonet/

WCF RIA Services Support for EF 4.1 (and EF Code-First)
http://varunpuranik.wordpress.com/

RIA Services EF Code First Support
http://jeffhandley.com/

자세한 환경설정은 강좌 2번을 참고하고, 그렇게 해두 앙대면, 리플로 알려 주면 해결 방법을 찾아보겠다.

3. 만들기 시작
일단 BOARD_MAN이란 이름의 테이블 한개만 가지고 어떻게 만드는 것인지에 대한 내용을 정리하도록 하겠다.

3-1. 폴더 추가

SL5_BOARD.Web

DomainService, Model 2개의 폴더 추가

3-2. BOARD_MAIN 작업

먼저 Model폴더에 클래스 추가 -> 이름 : BOARD_MAIN.cs

//Key를 잡기 위해서 추가함
using System.ComponentModel.DataAnnotations; 

namespace SL5_BOARD.Web.Model
{
    public class BOARD_MAIN
    {
        [Key]
        public int BOARD_MAIN_IDX { get; set; }
        public string BOARD_NAME { get; set; }
        public string BOARD_TYPE { get; set; }
        public bool MEMBER_CHECK { get; set; }
        public string BOARD_DESC { get; set; }
        public string BOARD_STATE { get; set; }
        public DateTime REG_DT { get; set; }
        public int REG_IDX { get; set; }
        public DateTime? UPT_DT { get; set; }          //Null허용 DateTime은 반드시 필요, String은 그냥 둬두댐
        public int? UPT_IDX { get; set; }                  //Null허용
    }
}

음..정확하게 할려면 문자열의 길이도 정하고 해야겠지만 생략한다. 이렇게 하면 하나의 레코드를 정의 한 것이다. 음..어려운 것 없다는..ㅋㅋ

주의 할 점은 클래스에 반드시 하나이상의 Key필드가 존재 해야 한다는 것인데, 예를 들어 처음 필드명이 ID로 끝나는 단어를 가지고 있다면 그 필드는 자동을 Key로 인식이 되고, ID가 아니면 명시적으로 [Key]를 붙여 주어야 한다.

모든 필드에 값을 넣을 수 없을 때 Null허용 필드를 만들기 위해서는 타입뒤에 ?를 붙여서 Null허용을 표시한다. (DateTime필드는 꼭 붙여주어야 한다.)

3-3. Database 작업

using System.Web;
using System.Data.Entity;

namespace SL5_BOARD.Web.Model
{
    //맨뒤에 DbContext가 바로 이 클래스를 Db로 인식시키는 넘이다.
    public class SL5_BOARD_DBCONTEXT : DbContext
    {
        //생성자에서.. : base("SL5_BOARD") 라는 부분이 생략되면 로컬에 있는 sqlexpress DB를 사용하는 걸로 간주한다.
        //여기서는 Web.config에 있는 SL5_BOARD라는 ConnectionString을 사용하도록 지정되어 있다.
        public SL5_BOARD_DBCONTEXT()
            : base("SL5_BOARD")
        {
            //기존 Code First에 없던 내용으로 WCF RIA Service에서만 추가된 내용으로 디자인 타임에서
            //Database 생성을 하지 않도록 하기 위한 내용이다.
            if (HttpContext.Current == null)
            {
                //원래 여기도 맨뒤에 길게 꼬리가 붙어있는데 WCF RIA Service에서는 null로 처리를 한다.
                Database.SetInitializer<SL5_BOARD_DBCONTEXT>(null);
            }
        }
        //Table 객체
        public DbSet<BOARD_MAIN> BOARD_MAINS { get; set; }
    }
}


먼저 Model폴더에 클래스 추가 -> 이름 : SL5_BOARD_DBCONTEXT.cs음..그럼 일단 데이터베이스 만들고, 테이블 만드는 것 까지는 했다. 위해서 이야기를 했지만 Code First는 기본으로는 로컬 컴퓨터에 sqlexpress를 기본 DB로 생각하고 있지만.. 강좌에서는 Compact DB를 사용하기로 했기 때문에 Web.config를 설정해야한다. (이것도 30분정도 삽질해서 찾아낸 내용이라는..;; 뭐든지 쉬운것은 하나도 없다. )

3-4. Web.config

<connectionStrings>
  <add name="SL5_BOARD"
       providerName="System.Data.SqlServerCe.4.0"
       connectionString="Data Source=|DataDirectory|\SL5_BOARD.sdf"/>   
</connectionStrings>

딱 위의 문장이다..하지만, 그냥 아..그렇구나하고 넘어가면 에러 하나가 무지하게 괴롭힐 것이다. 왜일까? 우리는 DB를 웹서버 바로 아래 놓을 것이기 때문에 상대 경로를 적어 주어야 한다. 요기서 상대경로 지정 방법을 알고 있다면 패스하고 다음으로 넘어가도 좋다.

3-5. ASP.NET Folder추가
SL5_BOARD.Web -> 오른쪽 마우스 클릭 -> Add -> Add ASP.NET Folder -> App_Data
이렇게 지정한다. 그럼 SL5_BOARD.Web 프로젝트에 App_Data라는 폴더가 추가되고, 그 폴더를 지칭하는 문자열이 |DataDirectory| 이다 왼쪽 오른쪽에 |문자가 존재한다.

3-6. Database File 추가
않한다. 패스~ 그냥 폴더만 만들어 놓는다;;

3-7. Domain Service추가
DomainService 폴더에 SL5_BOARDDomainService.cs라는 클래스 추가

//추가
using System.ServiceModel.DomainServices.Hosting;
using System.ServiceModel.DomainServices.EntityFramework;
using SL5_BOARD.Web.Model;
using System.Data.Entity.Infrastructure;
using System.Data;

namespace SL5_BOARD.Web.DomainService
{
    //이번에 새로 나온 내용~
    [EnableClientAccess]
    //                                                        이넘두 새로 나온 내용
    public class SL5_BOARDDomainService : DbDomainService<SL5_BOARD_DBCONTEXT>
    {
        //기본 조회
        public IQueryable<BOARD_MAIN> GetBoardMain()
        {
            return this.DbContext.BOARD_MAINS;
        }
        //Insert 작업 처리부
        public void InsertBoardMain(BOARD_MAIN entity)
        {
            DbEntityEntry<BOARD_MAIN> entityEntry = this.DbContext.Entry(entity);
            if ((entityEntry.State != EntityState.Detached))
            {
                entityEntry.State = EntityState.Added;
            }
            else
            {
                this.DbContext.BOARD_MAINS.Add(entity);
            }
        }
        //Update 작업 처리부
        public void UpdateBoardMain(BOARD_MAIN entity)
        {
            this.DbContext.BOARD_MAINS.AttachAsModified(entity, this.ChangeSet.GetOriginal(entity), this.DbContext);
        }
        //Delete 작업 처리부
        public void DeleteBoardMain(BOARD_MAIN entity)
        {
            DbEntityEntry<BOARD_MAIN> entityEntry = this.DbContext.Entry(entity);
            if ((entityEntry.State != EntityState.Deleted))
            {
                entityEntry.State = EntityState.Deleted;
            }
            else
            {
                this.DbContext.BOARD_MAINS.Attach(entity);
                this.DbContext.BOARD_MAINS.Remove(entity);
            }
        }
    }
}

Select하는 부분은 WCF RIA Serivce 4.0과 흡사 하지만, Insert, Update, Delete부분은 큰 차이가 있는데, 그것은 4.0에서는 레코드를 Object로 처리를 하고, 5.0은 엔티티로 처리를 한다는 것이다. 에..그게 정확하게 무슨 의미냐구 반문을 해도 딱히 한 단어로 설명을 하기는 어렵고.. 디버그나 앞으로 작업을 하면서 어떤 것인지 직접 느껴야 할 것이다. 자세한 설명은 다음으로..일단 미룬다..

3-8. 빌드를 하고 실행해보자
빈화면이 이쁘게 잘뜨고 에러도 없으면 일단 성공이다. 에러가 Workspace를 불러 올수 없다는 그런 오류가 뜨면, 어딘가가 틀렸을 것이니 다시 차근 차근 검사를 하기 바란다. 그럼 이제 실버라이트로 넘어가 보자

3-9. SL5_BOARD 프로젝트 -> MainPage.xaml
화면 왼쪽 사이드 메뉴 중에 Data Sources라는 텝이 보일 것이다. (SL4 WCF RIA 프로그램 강좌 참고) 눌러 보면 SL5_BOARDDomainContext라는 내용이 보이면서 BOARD_MAIN이란 항목이 표시 된다.(처음에 뜰때 시간이 걸리니 약간 인내하자)
BOARD_MAIN을 드래그해서 MainPage.xaml 하면에 드롭하면 자동으로 코드가 생성된다. 그리고 실행해보자. 한번에 여기까지 성공을 하면 당신은 천재 일지도 모른다..(여기까지 작업하는데 3시간 정도 걸렸었다;;)

비록 보이는건(그리드 헤더는 보인다) 없지만, 오류없이 화면만 잘 떠도 성공적인 것이다. 그런데, 궁금하지 않나? 과연 데이터베이스는? 테이블은? 데이터는? 아까 우린 데이터베이스를 만든적도 없고, 그냥 연결문자열만 작성하고 넘어왔었다. 그런데 어떻게 화면에 내용이 나올까??

WCF RIA Service support EF4.1 Code First 에서는 SL5_BOARD_DBCONTEXT 넘이 인스턴스 될때 모든 작업을 백그라운드로 처리를 한다. 데이터 베이스를 만들고, 테이블을 만들고, 머 또 다른 할일있으면 하는.. 그럼 이제 아까 SL5_BOARD.Web 프로젝트에 만들어 놓은 App_Data폴더를 열어보자..(탐색기로 찾아가자) 아마 깜짝 놀랄지도..

VS2010 화면 왼쪽 사이드 메뉴 중에 Server Explorer 텝을 클릭 -> Data Connections에서 오른쪽 마우스 클릭 -> Add Connection 을 선택해서 새로 생긴 파일을 선택해서 내용을 확인해보자. 테이블도 이쁘게 만들어져 있을 것이다.


3-10. 추가 작업(CRUD)
SL5_BOARD 프로젝트 -> Add Reference -> System.Windows.Data 추가

3-11. MainPage.xaml 화면 개선 작업

화면에 버튼을 3개를 추가하고 더블 클릭해서 이벤트를 연결해 준다.

3-12. MainPage.xaml.cs

using SL5_BOARD.Web.Model;

//3개의 버튼의 클릭 이벤트를 모두 여기로
private void button1_Click(object sender, RoutedEventArgs e)
{
    Button btn = sender as Button;
    switch (btn.Content.ToString())
    {
        case "Insert":
            //DTO객체를 만들고
            BOARD_MAIN bm = new BOARD_MAIN();

            //날짜를 입력(날짜를 앙넣어주면 0001/01/01로 초기값이 들어가는데 오류남)
            bm.REG_DT = DateTime.Now;
            bm.REG_IDX = -1;

            //일단 새로 만든걸 추가하고
            bOARD_MAINDomainDataSource.DataView.Add(bm);

            //바로 서브밋 - 서브밋을 하자마자 ID가 부여되어서 바로 보임
            bOARD_MAINDomainDataSource.DomainContext.SubmitChanges();
            break;
        case "Update":
            //서브밋
            bOARD_MAINDomainDataSource.DomainContext.SubmitChanges();
            break;
        case "Delete":
            //선택된 아이템이 있을 경우
            if (bOARD_MAINDomainDataSource.DataView.CurrentItem != null)
            {
                //선택된 아이템 삭제
                bOARD_MAINDomainDataSource.DataView.Remove(bOARD_MAINDomainDataSource.DataView.CurrentItem);
                //서브밋
                bOARD_MAINDomainDataSource.DomainContext.SubmitChanges();
            }
            break;
    }
}


3-13. 일단 여기까지만 하도록 하자..화면을 실행해서 Insert버튼도 눌러보고, Update버튼도 눌러보고..

DB에 저장대고 삭제되는 과정들을 쭈욱 한번씩 보기 바란다. 그리고, 소스는 당분간 리플로 요청한 분들에 한해서만 보내 주는 방향으로 하겠다. 같이 해야 가치가 있다는.. 굿굿한 신념으로..함께 차근 차근 만들면서 진행해야 실력이 는다.

에러도 먼저 맞은 넘이 낳고, 일찍 에러나는 코딩이 오래간다!

그럼


 

 

반응형
댓글