1. Clone 개요


  머큐리얼의 Clone은 저장소를 복사하는 것을 의미하며, 단순히 저장소의 "현재 상태"를 복사하는 것이 아니라, 저장소의 모든 변경 이력 등을 함께 복사하는 것을 의미한다. 머큐리얼은 모든 사용자가 자신의 저장소를 이용하여 이력을 확인할 수 있고, 유연하게 변경 사항을 Push, Pull 할 수 있다. 따라서, Clone은 여러가지 형태로 활용이 가능하다. 

  • 프로젝트를 Checkout하기 위해 Clone을 수행할 수 있다.
  • 프로그램에 실험적인 코드를 적용하기 위해 Clone을 한 후, 변경 사항을 적용하거나, 해당 코드를 버릴 수 있다. 이러한 작업을 위해 SVN은 흔히 branch를 사용하며, 머큐리얼 역시 branch 기능을 지원하긴 하지만, 머큐리얼의 Clone을 통한 branch는 훨씬 유연한 branch 기능으로 활용될 수 있다. 

2. Clone 절차

  Eclipse에서 MercurialEclipse를 통한 Clone은 다음과 같은 과정을 통해 수행한다. 
  • Clone을 수행할 원본 프로젝트를 가지고 있는 외부 저장소의 웹 서비스가 실행되어 있어야 하며, 해당 서비스 주소를 알고 있어야 한다. 
  • 이클립스에서 New > Project > Clone Exists Mercurial Repository 를 선택한다. 


  • 표시되는 창에서 URL에 외부 저장소의 주소를 입력한다. Next버튼을 클릭한다. 


  • Revision 선택 창에서는 Revision을 선택할 수 있는 여러 옵션을 제공한다. Revisions 탭을 선택하면 여러 Revision 중 하나를 Clone할 수 있다. 원하는 Revision을 선택하고 Finish를 누른다. 




1. Push, Pull 개요


  머큐리얼의 Push, Pull은 타 저장소로 변경 사항(changeset)을 전송하는 과정을 의미한다. Push와 Pull을 설명하기 이전에, 머큐리얼의 Revision과 Changeset의 개념에 대해 간단히 정리할 필요가 있다. 

  • Revision은 특정 시점에 저장소의 상태를 표시하는 번호이다. 이 번호는 순차적으로 올라가게 된다. 
  • changeset은 저장소의 변경 사항을 저장하는 단위이며, 하나의 changeset을 commit하거나 다른 저장소로부터 pull/update하게 되면, changeset을 받아오게 되며, Revision 번호는 하나 증가한다.
  • Revision 번호를 changeset과 동일한 것으로 보는 경향이 있는데 이는 잘못된 것이다. 이는 머큐리얼이 각자의 저장소를 가지고 각자의 변경 이력을 관리할 수 있는 저장소를 제공하는 특성(즉, DVCS의 특성)에 기인한다. 
  즉, Push나 Pull을 통해 changeset을 교환하는 순서에 따라 머큐리얼의 changeset 번호는 순차적이지 않을 수 있으므로, Revert 등의 기능을 통해 특정 Revision으로 돌아갈 때 유의해야 한다. 또한, 이러한 단점을 보완하기 위해, 특정 Revision을 Tagging 하는 기능이 있고, 이를 자주 작성하는 것을 권장한다. 
  더 자세한 설명은 Joel의 Mercurial 소개 사이트(http://hginit.com/)를 살펴보기 바란다. 


  앞에서 언급했듯이, 머큐리얼의 Push, Pull은 "변경사항(changeset)을 전송" 하는 형태이므로, 상당히 유연하게 동작한다. 예를 들면 

  • 중앙 저장소와 변경 사항을 Push/Pull 할 수 있다. 
  • 특정 사용자에게만 변경 사항을 Push/Pull하여 적용하도록 할 수 있다. 예를 들자면, QA에게 변경한 코드를 전송한 후, 테스트가 끝나면 중앙 저장소에 Push 하는 형태로 활용할 수 있다. 
  • 자기 자신이 Clone 한 저장소에 변경사항을 Push/Pull 할 수 있다. 


2. 외부 저장소로 변경사항 Push

  변경사항을 commit했다면, Revision 번호가 변경되었을 것이고, 이를 외부 저장소에 Push해야 한다. MercurialEclipse에서 Push 과정은 다음과 같은 과정을 통해 수행한다.
  • 먼저 Push를 받을 원격 저장소의 Mercurial Web Server가 동작하고 있어야 하며, 해당 웹 서비스의 주소를 알고 있어야 한다. 
  • 변경사항이 있는 프로젝트를 우클릭하고, Team > Push를 수행하면 다음과 같은 창이 표시된다. URL을 입력한 후, Next를 눌러 Push할 changeset을 확인한 후, Finish를 눌러 Push를 완료한다.


  • Push한 changeset을 원격 저장소의 웹서비스를 통해 확인한다. 



3. 외부 저장소로부터 Pull


  Pull은 Push와는 대비되는 개념으로, 외부 저장소로부터 현재 변경된 changeset을 받아오는 과정을 의미한다. 

  MercurialEclipse에서 Pull은 다음과 같은 과정을 통해 수행된다. 

  • 먼저 Pull를 받을 원격 저장소의 Mercurial Web Server가 동작하고 있어야 하며, 해당 웹 서비스의 주소를 알고 있어야 한다. 
  • 변경사항이 있는 프로젝트를 우클릭하고, Team > Pull를 수행하면 다음과 같은 창이 표시된다. URL을 입력한 후, Next를 눌러 Pull할 changeset을 확인한 후, Finish를 눌러 Push를 완료한다.



  • ※ 머큐리얼은 일반적으로 Pull을 수행하면, Update를 통해 수신받은 changeset을 현재 프로젝트에 반영하는 과정이 한 단계 포함하나, MercurialEclipse의 실행 옵션 중 Pull Option에 "update after pull"이 체크되어 있어, Pull을 수행한 직후에 update를 수행해주도록 되어있다. 다른 머큐리얼 환경 (특히 command로 Mercurial 수행시) 유의하도록 하자. 




Eclipse를 통해 생성한 프로젝트를 머큐리얼을 통해 공유하는 방법을 알아본다.



1. 공유할 프로젝트 생성


Eclipse를 이용하여 공유할 프로젝트를 생성한다.
이 과정은 일반적인 이클립스 프로젝트 생성 과정과 동일하므로, 별도로 언급하지 않는다.


Maven 프로젝트로 생성한 프로젝트에 간단한 예제 파일을 넣어 프로젝트를 생성한다.



2. Mercurial Repository에 프로젝트 공유

  프로젝트를 공유하기 위해 다음과 같은 과정을 수행한다. 
  • 프로젝트를 선택한 후, 우클릭하여 Team > Share Project를 선택
  • 표시된 창에서 Mercurial을 선택한 후, 다음 창에서 Finish를 눌러 프로젝트를 머큐리얼로 공유
  • 첫 공유 이후 commit을 수행하여 현재 프로젝트의 첫 commit을 수행


  하지만 이 과정까지 수행한 것은 현재 자신의 머큐리얼 저장소를 생성한 것에 불과하며, 이렇게 될 경우, commit과 update가 가능하긴 하지만, 외부 저장소에 소스가 공유되지는 않는다. 실제 외부 저장소에 commit을 수행하려면, push를 통해 외부 저장소에 현재 프로젝트 이력을 전송하는 과정을 거쳐야 한다. 


3. 프로젝트를 중앙 Repository에서 Cloning


  2번까지의 과정을 통해 프로젝트를 머큐리얼을 통해 관리하는 것이 가능하다. 하지만, 중앙 저장소에 프로젝트를 공유하는 과정이 남아있다. 

  프로젝트 생성을 이클립스를 통해 수행했으므로, 이 프로젝트를 공유하기 위해서는 중앙 저장소에서 이 저장소를 Cloning 하는 과정을 수행해야 한다. 아래의 과정을 통해 Cloning을 수행한다.

  1. MercurialEclipse를 이용하여 Mercurial Web Server를 실행한다. 이 과정은 이클립스에서 프로젝트를 우클릭한 후, Team > Serve 를 통해 가능하다. 


  2. localhost:8000을 브라우져로 확인해본다. 정상적으로 실행되었다면, 생성하고 Commit한 프로젝트에 대한 정보가 페이지로 보이게 된다. 

  3. 머큐리얼 중앙 저장소의 Workbench를 실행하고, File > Clone Repository 를 수행한다. Source에는 Mercurial Web Server를 동작시킨 PC의 웹 주소(http://ip:port)를 입력하고, Destination은 Cloning한 저장소의 로컬 저장 위치를 입력한다. (빨간 상자 부분에 IP와 port를 입력하면 된다.)



  4. Workbench에서 Cloning 한 저장소의 정보를 확인한다. 



모든 작업이 끝났다면, 중앙 저장소에 web config 파일에 해당 정보를 업데이트 한 후, 머큐리얼 웹 서버를 재시작함으로써, 이후에 중앙 저장소에서 서비스가 가능하도록 한다. 




  머큐리얼을 Eclipse에서 직접 사용하기 위해서는 MercurialEclipse 플러그인을 설치해야 한다. 이 포스팅에서는 MercurialEclipse 플러그인을 설치하는 방법을 알아본다. 


  MercurialEclipse 플러그인 홈페이지는 다음 주소(http://javaforge.com/project/HGE)에서 확인할 수 있다. 



이 홈페이지에서 Download Now 버튼을 찾아 이동한 페이지에서 Eclipse Plugin 주소(http://cbes.javaforge.com/update)를 확인할 수 있다.




해당 주소를 입력하여 MercurialEclipse를 선택하고, 설치를 진행한다.

(주: codeBeamer를 함께 설치했으며, Eclipse는 전자정부표준프레임워크 2.5를 사용했으나, 설치시 Plugin-dependency 관련 에러가 발생했다. 이는 codeBeamer 관련 에러인 듯 하며, Mercurial 사용에는 전혀 문제가 없다.)





설치가 종료되고 이클립스를 재시작하면, Eclipse에서 새로운 프로젝트 설치시, 다음과 같이 Mercurial Project를 선택할 수 있다.






1. Mercurial 설치 개요


  머큐리얼은 대표적인 DVCS(Distributed Version Control System) 중 하나다. 머큐리얼에 대한 설명은 내 블로그에 이미 정리된 포스트(http://silencer.tistory.com/57)가 있으므로, 생략한다. 

  현재까지 내가 머큐리얼을 사용하면서 직접적으로 느낀 장점과 단점은 아래와 같다. 

  • 장점
    • 빠른 커밋
      • 로컬 저장소에 이력을 저장하므로, 커밋이 빠르다. 로컬 저장소에 커밋이 빠르다는 점은, 그만큼 '커밋을 하는데 부담이 적다'라는 장점을 가질 수 있고, 이는 사용자가 변경사항에 대해 더 자주 커밋을 할 수 있도록 해준다. 
      • 단, 이 커밋은 중앙 저장소로의 커밋과는 다르다. 머큐리얼은 중앙 저장소로의 동기화를 위해 pull, push 라는 명령을 지원한다. (pull = svn의 update, push = svn의 commit과 같은 개념을 보면 됨)
    • 충돌이 비교적 적음
    • 설치/사용의 간편성
      • 서버/클라이언트 등을 설정해야 하는 SVN과 달리 머큐리얼은 자체가 서버/클라이언트 역할을 모두 할 수 있으므로 설치가 간편하다. 
      • 또한, TortoiesHg 라는 강력한 UI 툴을 지원하므로, 중앙저장소, 개발 환경에 관계 없이 머큐리얼과 TortoiesHg 패키지만 설치하면 되고, (물론, 이클립스 사용 시에는 머큐리얼 플러그인을 사용하는 게 좋다.) ToroiesHg를 통해 모든 명령어를 명령창 없이 GUI만으로 사용할 수 있다. 
    • 분기(branch)와 병합(merge)이 유연함
      • branch 명령을 지원하긴 하지만, 단순히 clone이라는 명령을 통해 프로젝트를 복사하는 것만으로 분기가 가능
      • clone 명령을 통해 분기한 프로젝트의 변경 사항을 기존 저장소로 push 함으로써 변경 사항을 merge 할 수 있음
  • 단점 
    • 중앙 저장소 동기화 빈도가 낮아짐
      • 시스템의 문제라기보단, 프로그램 사용상의 문제에 가깝다고 봐야 할 것 같음
      • 특히, SVN에 익숙한 사용자의 경우, SVN의 commit과 머큐리얼의 commit을 동일하게 여기는 경향이 생기는 듯함
      • 하지만, 중앙 저장소와 동기화하지 않는 DVCS는, 개발 툴이 지원하는 History 기능이나 마찬가지라는 생각이 듬
      • 또한, 동기화 빈도가 낮아질수록 충돌이 발생할 가능성은 점점 높아짐
      • 정기적인 push, pull 주기를 정하는 등의 별도 정책을 정하여, 중앙 저장소와 정기적으로 동기화를 수행할 수 있도록 하는 것이 좋을 것 같음

2. Mercurial 설치

  Mercurial 설치는 패키지를 다운 받아 Install 하고, 별도의 설정 없이 기본 값을 선택하면서 설치하면 된다. 자세한 설치 과정은 이 블로그의 포스팅(http://silencer.tistory.com/58)을 참고한다. 


3. Mercurial 설정


  머큐리얼 Workbench를 실행하면, 현재 생성된 Repository를 확인할 수 있으며, 여기서 여러가지 설정을 수행할 수 있다. 여기서는 설정에 대해 자세한 설명은 생략하고, 기본적인 설정만 진행한 후, 변경할 때마다 내용을 추가하기로 한다. 


  • Workbench에서 File > Settings를 선택하면 TortoiesHg Settings 창이 표시된다.
    • Commit
      • Username을 설정한다. Username은 이 PC에서 commit을 수행할 시에 사용자 이름을 나타낸다. 
    • Web Server
      • 웹서버 실행 시 홈페이지에 표시할 이름, 설명, 포트 등을 설정해준다. 또한, Allow  Push, Deny Push 등을 설정해주어야 하는데, 이는 중앙 서버에 Push 할 수 있는 사용자 이름을 의미한다. 

4. Repository 생성

  머큐리얼의 웹서버는 최소한 하나의 저장소가 존재할 때 실행이 가능하다. 실행을 위해 먼저 서버측에 테스트용 Repository를 생성한다.



  1. File > New Repository를 선택하면 위와 같은 창이 표시된다. 
  2. 알맞은 저장소 디렉토리를 설정한다. (주: 웹서버 상의 주소가 매핑될 때, Space나 한글을 구분하지 못하는 경우가 많으므로, Repository 주소는 항상 공백이나 한글이 없도록 하는 것을 추천한다.) 
  3. Create 버튼을 눌러 Repository가 생성된 것을 확인한다. 
  생성한 Repository를 아래와 같이 Workbench에서 확인할 수 있으며, Repository의 이름을 변경할 수 있다. 알맞은 이름으로 변경한다. 




5. 웹서버 실행


  머큐리얼의 Web Server를 띄운다는 의미는 단순히 이력을 확인할 수 있는 웹 페이지를 올리는 작업을 말하는 것은 아니다. 머큐리얼은 push를 받기 위해서는 Web Server가 동작해야 하며, 해당 포트를 통해 push 정보를 수신받게 된다. 



  1. 메뉴의 Repository > Start Web Server를 실행한다. 위와 같은 창이 표시된다.
  2. 포트를 설정하고, Start 버튼을 누른다. 

  아래쪽에 표시된 Config File에 주목해보자. Web Server 실행시, 기본적으로 Workbench에서 선택한 Repository를 실행하도록 되어있으나, 만약 다수의 Repository를 웹서버에 띄우고자 한다면, 미리 Config File에 다수의 Repository를 지정해두는 것이 좋다. 


[paths] 하위에 [프로젝트이름]=[Repository경로] 형식으로 지정하고, 이를 파일로 저장하고 매 실행시 이 파일을 로드하면, 다수의 Web페이지를 띄울 수 있다. 


※ 이 설정 파일의 물리 경로에 공란이 포함되어 (e.g. "Program Files") 인식이 되지 않는 경우를 겪은 적이 있다. 반드시 경로에 공란이 포함되지 않도록 주의할 것



6. 웹 서버 실행 자동화


  위와 같이 설정을 하더라도, 웹서버는 사용자가 WebServer를 실행시켜주기까지 동작하지 않는다. 그렇다고, 매 번 Web Server를 서버 부팅시마다 실행해주는 것은 너무 비효율적인 일이다. 간단한 방법을 통해 웹서버가 부팅시마다 켜질 수 있도록 해보자. 


  머큐리얼은 기본적으로 TUI 형식의 명령어를 지원한다. 머큐리얼과 관련된 명령을 수행하기 위해서는 hg(주: Mercurial=수은 -> 수은의 원소기호 hg)를 타이핑하고, 뒤에 수행할 작업을 인자로 전달해야 한다. 머큐리얼이 지원하는 작업 종류는 다음의 명령을 통해 확인할 수 있다. 


> hg help


  이 명령어 중, hg serve 라는 명령이 존재한다. serve 명령은 웹 서버를 실행해주는 명령이며, 이 때 필요한 옵션은 아래와 같은 명령으로 확인할 수 있다. 


> hg help serve

아래 이미지는 hg help serve 명령을 수행한 결과이다. 


  이 중, -d, -p, --web-conf 옵션 등에 주목할 필요가 있다. 대부분은 위에서 Web Server 관련 머큐리얼 설정에서 알아본 내용이므로, 별도의 부연 설명은 생락한다. 최종적으로 실행할 명령어는 아래와 같다. 


> hg serve -d -p [웹 포트번호] --web-conf [웹 설정 파일 경로]


  이 명령을 수행하면, 웹서버가 백그라운드 프로세스로 수행되게 된다. 프로세스의 이름은 hg.exe이므로, 종료를 원할 땐 참고하기 바란다. 


  이 명령을 배치파일로 만들어 시작 프로그램에 등록하거나, 배치 파일을 서비스 형태로 등록하면, 매 실행시마다 WebServer를 실행할 필요 없이 자동으로 머큐리얼 웹서비스가 실행된다. 아마도 시작 프로그램으로 실행시에는 사용자 로그인이 필요하거나, 별도의 조작이 필요하므로, 가장 이상적인 건 배치파일을 서비스로 등록하는 방법일 것이다. 배치 파일을 서비스로 등록하는 방법은 다음 포스팅과 외부 링크를 참고한다.


(다행히도, Windows 7에서도 호환성 문제 없이 잘 동작한다. 설치 과정에서 호환성 관련 경고를 한번 무시하는 것 빼고는 아래 절차와 동일하다.)


http://silencer.tistory.com/30


  1. 2013.04.24 17:15

    비밀댓글입니다


요즘 회사에서 몇 년전 포스팅했던 TOW(Trac On Windows)를 사용하고 있다. 
현재는 거의 혼자 일하기 때문에, 이슈 트랙킹은 거의 사용하지 않고 있으며
SVN은 소스 형상 관리 면에서는 이전보다 상당히 편리해졌다는 생각이 든다. 

SVN과 같은 기존 버전 관리 시스템은 중앙 서버에 소스 수정 이력이 저장되는 구조를 가진다. 
이러한 특징은 많은 한계점을 보여주는데, 내가 사용하면서 느꼈던 예를 들다면 다음과 같다. 

1) 항상 서버와 연결이 되어야 작업이 가능 
본인의 회사는 방화벽때문에 외부 접속이 불가능하다. 따라서 집에서는 작업이 불가능하다. 
마찬가지로, 외부로 출장을 나가더라도, 버전 컨트롤 시스템에 접속해서 작업은 불가능하다. 

2) 네트워크의 상황이 성능에 많은 영향을 미치고, 전체적으로 성능이 느림
중앙 서버와의 연결 속도가 성능에 많은 영향을 미친다. 
개발을 위해 이클립스를 사용하고 있는데, 가끔 네트웍 상황이 썩 좋지 않을 때 매우 버벅대는 경우가 생긴다. 

이러한 단점을 극복하기 위해 개발된 분산 버전 관리 시스템(Distributed Version Control System)은 수정 이력을 저장하는 중앙 서버가 별도로 존재하지 않으며, 각각의 개발자(클라이언트)마다 수정 이력을 저장한다. 

이러한 점 때문에 분산 버전 관리 시스템은 최근(? 최근이라 하기는 좀 시간이 지난 듯 하지만) 주목받고 있다. 

나도 위에서 말한 문제에 대한 대안으로 사용할 수 있을만한 분산 버전 관리 시스템을 찾고 있었으며, 
그 와중에 Mercurial 이라는 프로그램을 만날 수 있게 되었다.
(사실 직접 찾은건 아니고 선배의 추천으로... ㅎㅎ 그게 벌써 1년이 되어가는 듯 하다.) 

위에서도 말했지만 Mercurial은 분산 버전 관리 시스템이므로, 분산 버전 관리 시스템이 가지는 많은 장점을 가진다. 
공식 홈페이지(http://mercurial.selenic.com/)에서 말하는 Mercurial의 특징을 요약하면 다음과 같다. 

1) 분산 아키텍쳐 (Distributed architecture)
전통적인 버전 컨트롤 시스템(e.g. Subversion)은 전형적인 서버-클라이언트 아키텍쳐의 형태로써, 중앙 서버에 수정 내용이 저장된다.
반면에 Mercurial은 수정 내용이 분산되어 있으며 각각의 개발자가 전체 개발 히스토리의 로컬 복사본을 가진다. 

Mercurial은 위와 같은 방법으로 네트워크 연결이나 중앙 서버에 독립적으로 동작한다. 
Commit, Branch, Merge 작업이 빠르고 비용이 저렴하다.  

2) 빠른 속도 (Fast) 
3) 플랫폼 독립성 (Platform independent)

Mercurial은 플렛폼에 독립성을 고려하여 작성되었다.
Mercurial은 Python으로 작성되었으며, 성능적인 이유에 의해 아주 작은 부분만 C로 작성되어 있다.

4) 확장성 (Extensible)
5) 사용하기 쉬움 (Easy to use) - (과연?)
6) Open Source (GPL2)


해외에서도 많은 문서를 찾을 수 있지만, 위키피디아에서 Mercurial을 검색하다보니 
국내에도 튜토리얼이 있어, 이를 이용하면 빠른 학습이 가능할 것으로 보인다.

Mercurial 튜토리얼 한국어 버전 : http://mercurial.selenic.com/wiki/KoreanTutorial

앞으로 이 카테고리에 Mercurial 사용법을 정리해보겠다. 

+ Recent posts