As bugs are fixed and more functionalities are added to the program, the source codes change over time.

What if the bug-fix version does not work at all or crashes occasionally? You may want to go back to the previous version before the fix.

Programmer A fixed a bug #1001 and programmer B fixed a bug #2012 in the same file independently. How do you merge the two fixes?


Git Book: http://git-scm.com/book


Version control is a system that records changes to a file or set of files over time so that you can recall specific versions later. Using a VCS also generally means that if you screw things up or lose files, you can easily recover. In addition, you get all this for very little overhead.
(백업위치로 롤백하기 쉬움: 과거에는 대체로 이 용도로 Version Control System을 많이 사용했음)


Local Version Control System

Primitive VCS: copy files into another directory - problems?

A simple database that kept all the changes to files under revision control. e.g. rcs

바뀐 부분만 데이터베이스에 저장하면서 공간낭비를 줄인다.

Local Server에 각 버전별로 directory로 나누어 저장하는 방식이라 Local Computer가 crash나면 모든 정보를 손실하는 문제가 발생한다.




Central Version Control System

People needed to collaborate with developers on other systems - a single server that contains all the versioned files. e.g. CVS, Subversion, Perforce

If the server goes down, nobody can collaborate or see different versions.

If the drive in the server is corrupted, everything is lost.

Client는 Central VCS Server에 저장된 파일을 요청하여 작업하기 때문에 Server와의 Communication이 필요하다.(이전 버전에 대한 내용 확인을 위해서는 망에 연결되어야 한다는 단점이 있다.)

Checkout된 파일은 다른 Client들은 읽기만 할 수 있고 그 파일을 수정할 수 없다.

Server가 RAID 등으로 별도의 백업을 수행하지 않으면 crash났을 때 모든 정보를 잃는 문제가 발생할 수 있다.




Distributed Version Control System

Clients fully mirror the repository. Thus if any server dies, and these systems were collaborating via it, any of the client repositories can be copied back up to the server to restore it. Every checkout is really a full backup of all the data.

Server와 Client 모두 전체의 내용을 가지고 있다.

지속적으로 Communication을 하지 않기 때문에 속도는 빠르지만 다른 Client의 작업내용에 대해 Consistent하지 않는 문제가 발생한다.





Short History of Git

In 2002, the Linux kernel project began using a proprietary DVCS system called BitKeeper, but in 2005, the relationship is broke down. The Linux development community (and in particular Linus Torvalds, the creator of Linux) started developing their own tool, called Git.

  • Speed

  • Simple design

  • Strong support for non-linear development (thousands of parallel branches)

  • Fully distributed

  • Able to handle large projects like the Linux kernel efficiently (speed and data size)


Git Basics


Other systems tend to store data as changes to a base version of each file.



Git stores data as snapshots of the project over time.


  • Integrity: Everything in Git is check-summed using SHA-1 hash before it is stored and is then referred to by that checksum.

  • Nearly every operation is local.

  • Git generally only adds data.

  • Three states of the files: Committed(새로운 버전 생성), Staged(Commit 전에 Git에 백업), Merged.

  • Committed means that the data is safely stored in your local database.

  • Modified means that you have changed the file but have not committed it to your database yet.
    (수정한 파일은, Committed되어 Database에 완전히 저장된 파일과는 아직은 서로 다르다는 의미)

  • Staged means that you have marked a modified file in its current version to go into your next commit snapshot.




Git - Setting up Environment

Global environment setup
$ git config --global user.name "John Doe"
$ git config --global user.email johndoe@example.com
$ git config --global core.editor vi

Git reference page
$ git help <verb>
$ git <verb> --help
$ man git-<verb>

Initialize a Repository in an Existing Directory
$ git init

Add files to Git
$ git add *.c
$ git add README
$ git commit -m 'initial project version' // 업데이트에 대한 자세한 메시지 작성

Cloning an existing repository: 공유(다른 곳의 git을 불러오는 것)
$ git clone git://github.com/schacon/grit.git


Git - Checking the Status of Files


$ git status
# On branch master
# Untracked files:
#   (use "git add <file>..." to include in what will be committed)
#
#   README
#   nothing added to commit but untracked files present (use "git add" to track)


Git - Tracking New Files

$ git add README
$ vi benchmarks.rb // vi 에디터로 파일을 수정함
$ git status
# On branch master
# Changes to be committed:
#   (use "git reset HEAD <file>..." to unstage)
#
#   new file:   README
#
# Changed but not updated:
#   (use "git add <file>..." to update what will be committed)
#
#   modified:   benchmarks.rb
#


Git - Staging Modified Files

$ git add benchmarks.rb
$ git status
# On branch master
# Changes to be committed:
#   (use "git reset HEAD <file>..." to unstage)
#
#   new file:   README
#   modified:   benchmarks.rb
#

$ vim benchmarks.rb
$ git status
# On branch master
# Changes to be committed:
#   (use "git reset HEAD <file>..." to unstage)
#
#   new file:   README
#   modified:   benchmarks.rb
#
# Changed but not updated:
#   (use "git add <file>..." to update what will be committed)
#
#   modified:   benchmarks.rb
#

$ git add benchmarks.rb
$ git status
# On branch master
# Changes to be committed:
#   (use "git reset HEAD <file>..." to unstage)
#
#   new file:   README
#   modified:   benchmarks.rb
#


Git - Staged/Unstaged Changes

$ git diff
diff --git a/benchmarks.rb b/benchmarks.rb
index 3cb747f..da65585 100644
--- a/benchmarks.rb
+++ b/benchmarks.rb
@@ -36,6 +36,10 @@ def main
           @commit.parents[0].parents[0].parents[0]
         end

+        run_code(x, 'commits 1') do
+          git.commits.size
+        end
+
         run_code(x, 'commits 2') do
           log = git.commits('master', 15)
           log.size


Git - Moving / Removing Files

$ git rm grit.gemspec (또는 $ rm grit.gemspec)
rm 'grit.gemspec'

$ git status
# On branch master
#
# Changed but not updated:
#   (use "git add/rm <file>..." to update what will be committed)
#
#       deleted:    grit.gemspec
#

$ git mv file_from file_to


Git - Viewing Commit History

$ git log
commit ca82a6dff817ec66f44342007202690a93763949
Author: Scott Chacon <schacon@gee-mail.com>
Date:   Mon Mar 17 21:52:11 2008 -0700

    changed the version number

commit 085bb3bcb608e1e8451d4b2432f8ecbe6306e7e7
Author: Scott Chacon <schacon@gee-mail.com>
Date:   Sat Mar 15 16:40:33 2008 -0700

    removed unnecessary test code

commit a11bef06a3f659402fe7563abf99ad00de2209e6
Author: Scott Chacon <schacon@gee-mail.com>
Date:   Sat Mar 15 10:31:28 2008 -0700

    first commit


Git - Undoing Things

Changing Your Last Commit
$ git commit -m 'initial commit'
$ git add forgotten_file
$ git commit --amend

Unstaging a Staged File
$ git reset HEAD benchmarks.rb
benchmarks.rb: locally modified
$ git status
# On branch master
#   ...
# Changed but not updated:
#   (use "git add <file>..." to update what will be committed)
#   (use "git checkout -- <file>..." to discard changes in working directory)
#
#       modified:   benchmarks.rb

Unmodifying a Modified File
$ git checkout -- benchmarks.rb
$ git status
# On branch master
# Changes to be committed:
#   (use "git reset HEAD <file>..." to unstage)
#
#       modified:   README.txt
#


Git - Working with Remotes

Fetching and Pulling from Your Remotes ↔ Pushing to Your Remotes

Fetching and Pulling from Your Remotes
$ git fetch [remote-name]
$ git pull [remote-name]
# Fetches and merges to the current branch.

Pushing to Your Remotes
$ git push [remote-name] [branch-name]
$ git push origin master


Online Repository

  • GitHub(http://github.com/): 개인 git서버를 만들 수 있다.(코드의 완전공개 / 유료서비스로 비공개 가능)
  • BitBucket(http://bitbucket.org/): private한 Repository를 만들 수 있다.


Pair programming

둘이서 프로그래밍하는 것


Test-driven programming

Version Control System(VCS)에 Commit할 때 Test-driven Function이 적용되어 걸러내기도 한다.



References