3 Git의 수많은 명령어 속으로 곧바로 다이빙 하는 것 보단, 다음 간단한 예시들을 통해서
4 천천히 배우는 방법이 좋을 것 같습니다. 제가 소개하는 예시들은, 표면적으로는 간단하게 보이지만, 앞으로 여러방면으로 많은 도움이 될 것입니다.
5 저 역시도 처음 Git을 사용할 때에는 아래에 있는 예시 외에는 건들여 보지도 않았습니다.
7 === 상태 (state) 저장하는 방법===
9 파일에 무엇인가 큰 변화를 주고 싶으시다고요? 그러시기 전에, 현 디렉토리에 들어있는
14 $ git commit -m "My first backup"
16 위 명령어들을 입력 후, 만약에 편집을 하다가 잘못됬다면, 편집되기 전의 깨끗한 버전으로 되돌리면 됩니다:
20 또 어떤 작업 후 state를 저장하고 싶다면:
22 $ git commit -a -m "Another backup"
24 === 파일 더하기 (add), 지우기 (delete), 이름 바꾸기 (rename) ===
26 위의 간단한 요령들은 처음 *git add* 명령어를 실행했을 때 이미 존재하던 파일들만 저장하게 됩니다. 존재하던 파일의 편집 이외의 새로운 파일들이나 하위 디렉토리들을 추가했다면, Git에게 알려줘야 합니다:
28 $ git add readme.txt Documentation
30 그리고 만약에 원하지 않는 파일을 Git에서 없애려면 그것 역시 Git에게 알려줘야 합니다:
32 $ git rm kludge.h obsolete.c
33 $ git rm -r incriminating/evidence/
35 이렇게 함으로써 Git은 지정한 파일들을 지워주게 됩니다.
37 Git 파일이름을 바꿀때에는 원치않는 일반파일들의 이름을 지우고 새로운 이름을 새롭게 지정하는 간단한 절차와 같습니다. 좀 더 손쉬운 방법으로는 *git mv* 명령어가 있습니다. 예를 들어:
39 $ git mv bug.c feature.c
43 가끔씩은 작업을 하다가 하던 일을 멈추고 전 버전으로 돌아가고 싶다거나, 어느 시점 이후의 모든 편집을 지우고 싶을 때가 있을 것입니다. 그렇다면:
47 이 명령어는 최근의 commit들을 정리한 리스트와 그의 SHA1 hashes를 보여줍니다:
49 ----------------------------------
50 commit 766f9881690d240ba334153047649b8b8f11c664
51 Author: Bob <bob@example.com>
52 Date: Tue Mar 14 01:59:26 2000 -0800
54 Replace printf() with write().
56 commit 82f5ea346a2e651544956a8653c0f58dc151275c
57 Author: Alice <alice@example.com>
58 Date: Thu Jan 1 00:00:00 1970 +0000
61 ----------------------------------
63 Hash 앞의 알파벳 몇 개만으로도 commit을 세분화 설정하실 수 있습니다;
64 다른 방법으로는, 아래의 명령어와 같이 hash 전문을 복사/붙여넣기 하는 방법도 있지요:
66 $ git reset --hard 766f
68 위 명령어를 입력하시면 설정된 commit으로 돌아갈 수 있으며 그 후의 새로운 commit들은 영구적으로 삭제됩니다.
70 가끔씩은 또 아주 예전의 state로 잠시만 돌아가길 원하실 수 있습니다. 그럴 경우에는:
74 이 명령어는 82f5 이후의 commit들을 보존함과 동시에 과거의 시간으로 잠시 돌아가게 해줍니다. 그러나, SF영화에서 처럼, 과거에 돌아간 상태에서 편집을하고 commit을 한다면 또 다른 시간대의 현실을 만들어가게 되는 것이죠. 왜냐하면 당신의 편집이 과거의 편집과는 다르게 입력이 되었기 때문입니다.
76 이렇게 새롭게 만들어진 대체현실을 'branch (나뭇가지)'라고 부릅니다 <<branch,에 관해선 추후에 자세히 설명합니다>>. 지금 알고계셔야 할 것은
80 이 명령어는 과거에서 현재의 state로 돌아오게 해줄 것입니다. 그리고 Git이 유저에게 푸념을 놓기전에 과거에서 편집했던 사항들이 있다면
81 master branch로 돌아오기전 commit을 하거나 reset을 한번 실행하시길 바랍니다.
85 - *`git reset --hard`*: 예전에 세이브 해뒀던 게임으로 돌아가며, 돌아간 시점 이후의 세이브들을 모두 삭제합니다.
87 - *`git checkout`*: 예전에 세이브 해뒀던 게임으로 돌아가며, 돌아간 시점 이후의 게임들은 처음 세이브와 다른 길을 가게 됩니다. 추후의 모든 세이브들은 다른 branch로써 새로운 현실세계를 만들게 됩니다 <<branch,에 관해선 추후에 자세히 설명합니다>>.
89 예전의 파일/하위 디렉토리들을 되돌리고 싶을 때 다음 명령어를 이용함으로써 필요한 파일/하위 디렉토리만을 되돌릴 수 있습니다:
91 $ git checkout 82f5 some.file another.file
93 그러나 이 *checkout* 명령어가 다른 파일들을 조용히 덮어씌우기 할 수 있다는 점을 알아두세요! 이러한 사고를 방지하고 싶다면
94 checkout 명령어를 쓰기전에 commit을 이용하세요. Git을 처음 이용하는 분들은 특히 더 조심하시기 바랍니다.
95 대체적으로 파일이 삭제될까 두려우시다면 *git commit -a*를 우선해놓고 생각하세요.
97 긴 hash 전체를 복붙하기 싫으시다고요? 그렇다면:
99 $ git checkout :/"My first b"
101 이 명령어를 사용함으로써 이 commit message를 사용해서 commit했었던 state로 돌아갈 수 있습니다.
102 그리고 이 다음 명령어로 5번 스텝 전의 state로 돌아갈 수도 있습니다:
104 $ git checkout master~5
106 === 되돌리기 (Reverting) ===
108 법정에서는 어떠한 일에 관해서는 기록에서 지울 수 있습니다. 이런 식으로, Git에서는 원하는 commit을 정해서 없던 일로 할 수 있습니다.
113 이렇게 하는 것으로 특정 hash에 대한 commit을 undo 할 수 있습니다. 이렇게 되돌린 state는 새로운
114 commit으로 인식되어 *git log*에 기록됩니다.
118 어떤 프로젝트들은 http://en.wikipedia.org/wiki/Changelog[changelog]. 필요로 합니다.
119 다음 명령어를 이용해 변경기록을 만들어 봅시다.:
121 $ git log > ChangeLog
125 Git으로 관리되는 프로젝트 사본을 얻기위해서는:
127 $ git clone git://server/path/to/files
129 예를 들어, 본 웹사이트를 만들기 위해 사용한 파일들을 얻기위해서는:
131 $ git clone git://git.or.cz/gitmagic.git
133 곧 *clone* 명령어에 관해 많은 것을 소개하도록 하겠습니다.
137 *git clone* 명령어를 이용해 어떤 프로젝트의 사본을 다운로드 해뒀다면, 다음 명령어를 이용해 그 프로젝트의 최신버전으로 업데이트 할 수 있습니다:
143 당신이 다른 사람들과 공유하고 싶은 스크립트를 작성했다고 가정합니다. 당신은 그들에게 당신의 컴퓨터에서 다운로드를 받으라고 할 수있지만, 당신 친구들이 만약 당신이 해당 스크립트를 편집하는 도중에 받게된다면, 그들은 예상치 못한 트러블에 걸릴 수 있습니다. 이러한 이유 때문에 릴리스 사이클이란 것이 존재하는 것입니다. 개발자들은 개발 중인 프로젝트 디렉토리에 자주 들락날락 거릴 것이고, 그들은 그들이 한 작업이 다른 사람들 앞에 내놓을 만한 상태로 만들어지기 전까지 남들에게 보여주지 않을겁니다.
145 Git으로 릴리스 사이클을 맞추려면, 당신의 스크립트가 들어있는 디렉토리에서:
149 $ git commit -m "First release"
151 그리고 당신들 친구들에게 다음 명령어를 사용하도록 하십시오:
153 $ git clone your.computer:/path/to/script
155 그들이 이렇게하면 당신의 스크립트를 다운로드 할 수 있을 것입니다. 이 작업은 다른 유저들이 ssh 접근을 할수있다고 가정합니다. 그렇지 않다면, 소유주인 당신이 *git daemon* 명령어를 쓴 후 친구들에게 다음 명령어를 쓰라고 하십시오:
157 $ git clone git://your.computer/path/to/script
159 이렇게 하고 난 다음부터 당신의 스크립트가 준비되었을 때마다 다음 명령어를 실행하면 됩니다:
161 $ git commit -a -m "Next release"
163 당신의 친구들은 다음 명령어를 사용함으로써 가장 최근 버전으로 당신의 스크립트를 보유하고 있을 수 있게 되죠:
167 그들은 절대로 당신이 보여주고 싶지않은 버전의 스크립트를 보는 일이 없을 것입니다.
169 === 제가 도대체 뭘 한거죠? ===
171 마지막으로 한 commit으로 부터 어떤 변화가 있었는지 확인하기 위해서는:
175 어제부터 어떤 변화가 있었는지 확인하기 위해서는:
177 $ git diff "@{yesterday}"
179 어떤 특정 버전에서 부터 2번째 전 버전 사이의 변화를 확인하기 위해서는:
181 $ git diff 1b6d "master~2"
183 각각의 결과는 *git apply*와 함께 적용할 수 있는 패치가 될 것입니다.
186 $ git whatchanged --since="2 weeks ago"
188 저는 윗 방법대신 http://sourceforge.net/projects/qgit[qgit] 를 따로 다운받아서 commit 히스토리를 체크하곤 합니다. 이 프로그램은 깨끗한 그래픽 인터페이스로 구성되어 있어보기 쉽지요. 아니면, http://jonas.nitro.dk/tig/[tig], 텍스트형식 인터페이스 역시 느린 인터넷속도를 가지고 있는 분들에겐 도움이 될 것입니다. 또 다른 방법으로는 웹 서버를 설치한 후 *git instaweb*명령어를 사용하는 방법도 있겠지요.
192 우선 A, B, C, D 를 각각 연속된 한 파일에 대한 commit이라고 가정합니다. 그리고 B는 A 에서 몇 개의 파일들이 삭제된 버전으로 가정합니다. 문제는 여기서 그 삭제된 파일들을 D에 더하고 싶을 때 어떻게 하는 것 인가 입니다.
194 적어도 세가지의 방법이 있습니다. 우선 우리가 현재 D에 있다고 생각합시다:
196 1. A와 B의 차이점은 몇 개의 지워진 파일들 뿐입니다. 우리는 이 차이점을 패치로 따로 작성하여 본래의 디렉토리에 적용할 수 있습니다:
198 $ git diff B A | git apply
200 2. 우리는 A에 파일을 저장해 두었기에, 그 곳에서 다시 받아올 수 있겠지요:
202 $ git checkout A foo.c bar.h
204 3. 또는 A에서 B까지로 갈 때의 변화를 undo한다고 생각하셔도 됩니다:
208 어떤 방법이 가장 좋은 해답일까요? 답은 본인이 원하는 것이 곧 해답입니다. Git을 이용한다면 당신이 원하는 것은 쉽게 해낼 수 있고, 그 것을 해내는 방법은 한가지만 있는 것이 아닐겁니다.