wecode [TIL]

[TIL] Git & GitHub ( 1탄 )

프린벼르 2022. 2. 26. 17:39

GIt 1탄 표지

오늘은 그동안 나를 무던히도 괴롭혀온 git에 대해서 포스팅해보고자 한다. git은 정말 어렵고 또 어렵다. 처음 git에 대해 배운 날에는 혼이 빠지는 느낌을 받았다. 도대체 이 어려운 git을 왜 써야 하는 것이며, 이 어려운 git을 어떻게해야 좀 더 쉽게 이해할 수 있는지에 대해서 자세히 포스팅하려 한다.


1. Git 이 뭔가요 ? Git 은 왜 필요한가요 ?

Git이란 소스코드를 효과적으로 관리하기 위해 개발된 '분산형 버전 관리 시스템'이다.
( 💁🏻‍♀️ 버전프로그램 변경사항을 의미한다. )

🙋🏻‍♀️ 그렇다면 버전은 왜 굳이 관리해야하는 걸까? 최종 코드만 계속 갱신하면 되는게 아닐까?
매번 코드 수정 때마다 변경 사항을 업로드하는게 더 귀찮지 않을까?

( 💁🏻‍♀️ Git에서는 소스 코드가 변경된 이력을 쉽게 확인할 수 있다. 또한, 특정 시점에 저장된 버전과 비교할 수 있고
특정 시점으로 되돌아갈 수도 있다. 게다가, 내가 올리려는 파일이 다른 팀원과 편집한 내용과 conflict(충돌)한다면
서버에 업로드 할 때 경고 메시지가 발생한다. 그렇기에 실수로 누군가의 작성 문서를 덮어버리는 일은 생기기 힘들다. )

개발을 하다보면, 협업이 필수과정이다. Git은 문제점들(코드를 공유받지 못해 다음 단계로 진행할 수가 없는 경우, 팀원들 간의 코드 충돌 경우, 여러 번의 수정 과정을 거치면서 내가 짠 코드가 무엇인지 헷갈리게 되는 경우 등)을 방지하기 위해 버전 관리를 통해 작업 일지 기록이나 협업, 백업 등을 가능하게 한다.

위 모든 이유들로 인해 Git은 필수적으로 모든 개발자들에게 필요한 필수템이라고 할 수 있다.

2. Git 에 관한 자세한 개념 소개 

1) Repository (저장소)

Repository( 레포지토리 )는 말 그대로 파일 등이 저장되는 저장소로, 프로젝트 폴더를 의미한다. 저장소의 종류는 다음과 같다.

  • Remote Repository (원격 저장소)원격 서버저장된 저장소로, 여러 사람함께 공유한다.
  • Local Repository (개인 저장소): 우리가 직접 관리하는 저장소로, 내 PC저장되어 있다.

Git 저장소 도식화

보통 레포지토리는 로컬에서 만들어서 원격에 업로드하거나, 원격에서 생성된 레포지토리를 로컬로 다운받는 방법으로 생성한다.


2) Commit

Commit( 커밋 )프로젝트변경 이력을 말한다. 복잡하게 생각될 수 있는데, 간단하게 로컬에서 작업 시 다음과 같이 나타낼 수 있다.

commit 개념 도식화


3) Branch

이전까진 모두 개인이 로컬에서 개발하는 상황에서 사용하는 git의 명령어다. Branch( 브랜치 )여러 명이 같은 코드를 공유하며 협업하는 상황에서 사용하는 git의 명령어다. 앞서 설명했듯, 개발자들은 여러 번 commit을 하여 코드를 업로드한다. 이때 누가 어떤 commit을 추가했는지 구분이 가능해야 한다. 바로 이런 상황에서 사용되는 것이 branch다. branch각 개발자들이 개발을 진행하고 있는 환경 또는 흐름을 말한다. 그래서 새로운 브랜치가 생성되더라도 기존의 메인 브랜치는 그대로 남아있다. 이게 무슨 의미인지 그림을 통해 설명하려 한다.

Git Branch 도식화

물론 다음과 같이 한 사용자가 자신의 기능의 세부 브랜치를 또 다시 나눌 수도 있다. ( 브랜치 생성 가능 갯수에는 제한 없다. )

▶ 주로 쓰이는 브랜치 종류 (" Git flow - 저장소 고수준 관리위한 브랜칭 기법 ")

☑️ Master 브랜치 - (메인 배포판) 실제로 클라이언트에서 이용하는 최종 형태메인 브랜치이다.
☑️ Develop 브랜치 - (메인 개발) 현재 개발이 진행 중인 메인 브랜치이다. Master 브랜치와 마찬가지로
추가적으로 생성 또는 삭제되지 않는 브랜치이다.
☑️ Feature 브랜치 - (추가 기능 개발) 새로운 기능을 추가하기 위해 사용되는 브랜치로, 특정 기능의 개발이 필요할 때
Develop 브랜치에서 파생되며, 기능 개발이 완료되면 Develop 브랜치로 병합된다. (가장 많이 생성되었다 삭제되는 브랜치 )

4) Checkout

현재 위치한 commit ( 커밋 )에서 다른 commit ( 커밋 )으로 이동하는 것Checkout ( 체크 아웃 )이라 한다. 체크 아웃을 통해 현재 커밋에서 같은 브랜치 내 다른 커밋으로 이동하거나, 다른 브랜치 내 커밋으로 이동할 수 있다. 결론적으로 체크아웃으로 인해 이전 시점의 버전으로 되돌아갈 수도 있고, 다른 사람의 브랜치로 전환해 다른 개발자들의 코드 진행 상황을 확인해 볼 수도 있다.


5) Merge

Merge는 나뉘어진 브랜치를 다시 하나의 브랜치로 합치는 것을 말한다. 가장 오류가 많이 발생하는 과정이니 주의해야 한다.
Merge 진행 시 현재 브랜치를 브랜치가 합쳐지는 기존 메인 브랜치로 전환한 후 수정된 브랜치를 Merge해야 오류가 발생하지 않는다.
여러 개의 브랜치들을 한꺼번에 Merge할 때도 마찬가지로, 차례대로 기존 브랜치 상태에서 Merge를 진행해야한다.

Merge에는 종류가 2가지가 있다. 하나는 fast-forward이고, 나머지 하나는 non fast-forward이다.
먼저 fast-forward기본 merge 방식으로, 서로 다른 두 브랜치를 충돌 없이 자동 merge 시키는 병합이다.

하지만 그 과정에서 때때로 일부 문법으로 인해 충돌 (Conflict)이 발생하면 병합에 실패하는 경우가 발생한다.
이때 해당 충돌 기록을 살피며 일일히 해당 코드를 수정한 뒤 Merge를 이어서 진행하면 성공적으로 브랜치가 병합된다.
이 Merge 방식이 non fast-forward이다. 또한 이 과정에서 코드의 수정이 이루어졌으니 마찬가지로 새로운 커밋이 생성된다.

merge 작업 도식화


6) Clone

Clone ( 클론 )은 원격 저장소로부터 특정 프로젝트통째로 내 로컬 저장소에 다운받는 것을 말한다.

7) Push

Push ( 푸쉬 )는 현재 내 로컬에서 작업한 변경 사항들을 원격 저장소에 반영하는 것을 말한다.
작업이 완료될 때마다 원격 저장소에 푸쉬해야 다른 사람들이 내 코드를 확인할 수 있다.

8) Pull

Pull ( 풀 )은 원격 저장소에서 변경된 사항들을 내 로컬 저장소에 반영하는 것을 말한다. Push의 정반대 개념으로, 다른 사람이 Push를 해서 원격 저장소에 코드를 업데이트하면 우리는 해당 코드를 Pull하여 로컬의 코드를 업데이트한다. ( 이때 기존의 코드와 내 코드가 다른 경우 Merge를 진행해 코드를 합치게 된다. )

※ Clone과 개념이 헷갈릴 수도 있는데, Clone은 프로젝트를 처음 불러올 때 프로젝트 전체를 다운받는 것이지만, Pull은 해당 프로젝트에서 변경된 사항들만 다운받는 것을 말한다.