Git & Github 요약 정리
git과 github의 기본 개념을 정리했다
VCS와 Git
Git은 VCS(Version Control System) 중 하나이다. Version Control System에서 Version이 의미하는 것은 개발 작업이 진행되는 폴더 및 하위 폴더와 파일들의 history를 의미한다. 따라서 VCS가 하는 역할은 개발을 진행할 때, 개발의 환경이 되는 폴더와 파일들의 변경 기록을 저장하고 관리하는 것이다. 그렇다면 VSC가 개발을 진행하는 데 있어서 필요한 이유는 무엇일까? 크게 3가지가 있다.
코드 변경 사항 내역 기록 및 관리
필요한 이전 상태로 rollback
팀단위 개발시 체계적이고 효과적인 협업
우리가 코드를 업데이트 할 때, 많은 경우 버그가 발생하고 해당 버그가 치명적이어서 이전 코드로 돌아가야 할 때가 있다. 또한 팀 단위로 협업이 진행될 때, 어떤 사람이 적용한 코드에서 문제가 발생했는지 확인해야 하는 경우도 있다. 일정 규모 이상의 프로젝트가 진행될 경우 VCS의 사용이 필수적이다.
Repository
Repository는 git이 관리하는 폴더를 의미한다. 일반 폴더는 git에게 아무 의미가 없지만 해당 폴더 내부에서 git init
을 통해 .git 폴더가 생성되어서 해당 폴더의 변경사항이 git에 의해 추적되기 시작하면 그 폴더를 repository라고 한다. git repository는 2가지로 분류된다.
local repository: local(개발자 개인의 컴퓨터)에 저장된 repository
remote repository: 중앙 서버에 저장된 repository, git을 팀 단위의 협업을 할 때 사용한다면 팀에 소속된 개발자들이 공통적으로 참조하는 repository가 있어야 할 것이다. 팀에서 공동으로(꼭 팀 단위가 아니더라도) 원격으로 관리하는 repository를 remote repository라고 한다. 일반적으로 http나 ftp로 접속가능한 서버에서 관리된다.
Staging and Commit
git init
을 통해 repository가 된 폴더(즉, repository)는 git에 의해 변경 사항이 추적되지만 자동적으로 코드 변경 사항이 저장되지는 않는다. 코드 변경 사항을 git에 저장하고 싶다면 개발자가 변경이 완료된 지점에서 git을 사용한 명령어로 변경점을 저장해야 한다. git에서는 변경 사항의 추적부터 시작하여 변경 사항이 적용되기 까지를 3가지의 상태로 나누어 관리한다. git repository 파일들은 git에 변경점이 저장되지 전에 Modified, Staged, Committed 이렇게 3가지 상태 중 하나로 존재한다.
Modified: 이전 변경점 이후에 변경된 파일들은 git에 의해 추적되어서 자동으로 modified 상태가 된다. 만약 아예 파일이 새로 생성되었다면 해당 파일은 modified가 아니라 untracked 상태가 된다.
Staged: modified 혹은 untracked 상태인 파일(혹은 폴더)들 중에
git add *
명령어를 통해 index에 등록된 상태를 말한다. git에서는 변경된 파일을 바로 변경 내용으로 저장하기 전에 index에 저장해서 추가적인 변경이 일어날 수 있는 중간 지점을 만들었다. 변경점을 저장하기 전에 누락이라 실수가 있을 수 있는데, 그 때마다 roll back을 한다면 저장소의 log도 길어지고 불편한 지점이 존재한다. 따라서 최종적으로 변경점을 저장하기 전에 변경 내용들을 점검할 수 있는 staged 상태가 있다.Committed: index에 등록된 변경 내용들은 git log에 저장되지 않는다. 아직 변경점이 저장되기 전이기 때문이다. git에서 진짜 변경점을 저장하기 위해서는 index에 등록된 변경 내용들을
git commit
명령어를 사용하여 새로운 snapshot으로 저장해줘야 한다. commit 명령어를 사용할 때,git commit -m "message"
-m 옵션을 사용하여 변경 내용에 대한 짧은 설명을 남길 수 있다. log에도 -m 옵션으로 붙여진 메세지가 기록된다.
Snapshot이 저장되는 방식
git에 저장되는 각각의 변경점을 snapshot이라고 한다. git은 VCS고 VCS에서 roll back 기능을 제공해야 한다면, 이 말은 git의 이전까지의 모든 변경점의 폴더와 파일들을 전부 저장하고 있다는 뜻이다. 그렇다면 매 snapshot마다 폴더와 파일들이 새로 저장되어야 하므로 저장공간을 많이 차지할 것이다. 다행하게도 git은 snapshot마다 폴더와 파일들을 새로 저장하는 방식으로 파일을 관리하지 않는다. git은 현재의 snapshot과 바로 이전의 snapshot과 비교하여 변경된 파일과 변경되지 않는 파일을 구분한다. 만약에 새로 변경된 파일이라면 파일을 새로 저장하지만 변경되지 않은 파일이라면 복사하지 않고 이전 snapshot의 해당 파일의 주소를 가리키게 만든다. 이런 방식으로 저장하면 변경된 파일들이 전부 저장되지만 변경되지 않은 파일들도 불필요하게 저장되는 것을 막을 수 있다.
※ 따라서 개발자가 remote repository에서 repository를 clone 혹은 pull하는 것은 해당 repository의 특정 시점의(일반적으로 가장 최신) snapshot을 받아오는 것이다.
Branch와 Merge
여태까지 git이 하는 역할과 git으로 snapshot을 저장하기 까지의 과정들, snapshot이 저장되는 방식에 대해서 설명했다. 그렇지만 아직 의문이 남는다. 개발자들이 각자 snapshot을 저장해서 개발을 한다면 어떻게 서로의 변경사항들을 조율할 수 있는것일까? 개발자들 각자의 변경사항들을 합쳐서 새로운 최신 버전의 스냅샷을 만들기 위해서는 어떤 스냅샷을 기준으로 변경 사항들을 합치는 가의 문제를 해결해야 한다. 이 문제를 해결하기 위해서 branch를 사용한다.
Branch
우리가 git init
을 통해 repository를 생성했다면 기본적으로 master branch가 만들어진다. 개발이 이루어질 때는 각 개발자들이 master branch의 snapshot을 가지고 오고 이 master branch를 기준으로 자신이 작업할 새로운 branch를 만들어 낸다. 이렇게 만들어진 branch를 feature branch라고 한다. branch를 새로 생성할 때는 git checkout -b feature_name
을 사용한다.(-b 옵션을 붙이면 생성 후에 해당 branch로 바로 이동한다.)
Merge
각 개발자는 feature branch를 기준으로 개발을 진행하고 개발이 완료되어서 최종 commit 도 완료되면 remote repository에 해당 snapshot을 저장한다. remote repository에 있는 master branch에서는 feature branch로 개발된 내용들을 합치기 위해서 merge한다. master가지를 기준으로 merge할 때는 git merge featrue_name
명령어를 사용한다.
Github
이전까지의 git의 내용을 이해했다면 Github의 역할도 쉽게 이해할 수 있다. Github은 git의 remote repository를 제공하는 웹서비스 이다. 현재 Github 단순히 중앙 저장소 역할만 하는 것이 아니라, testing, code review, documentation 생성 및 관리, 일정 관리 등의 프로젝트 개발과 운영에 필요한 다양한 기능들을 제공한다.
Github 사용하기
Github을 사용하면 remote repository를 쉽게 생성할 수 있다.
github에 로그인 한 후
new Repository 버튼을 클릭하고
Repository 이름을 설정한다.
Create Repository 버튼을 눌러서 remote repository를 생성한 뒤, 주소를 복사한다.
git init
명령어를 통해 local repository를 생성한다.새로운 파일을 repository 내에 생성한뒤
git add *
,git commit
명령어로 snapshot을 저장한다.git remote add origin '복사한 remote repository 주소'
를 사용하여 원격 저장소와 로컬 저장소를 연결한다.git push origin master
명령어를 사용하여 github remote repository master branch에 snapshot을 저장한다.