TIL

Git / GitHub 톺아보기 (1)

1. Git 시작하기 ✍️ 1-1. 깃으로 할 수 있는 것 ✅ 1-2. 리눅스 명령어 ✅ 2. 깃으로 버전 관리하기 ✍️ 2-1. 깃 저장소 만들기 ✅ 2-2. 버전 만들기 ✅ 2-3. 커밋 내용 확인 ✅ 2-4. 파일 상태 확인 ✅ 2-5. 작업 되돌리

2025년 7월 3일12min read

0. Overview ✍️

Do it! 5일 만에 끝내는 깃&깃허브 입문을 읽고 네 편에 걸쳐 Git / GitHub에 관해 정리하고자 합니다. 이미 자주 사용하고 있지만, 이해하지 못한 채로 습득된 내용도 많겠죠. 이번 시리즈를 통해 Git / GitHub의 전반에 관해 명확히 이해해 보겠습니다.

1. Git 시작하기 ✍️

리누스 토르발스(Linus Torvalds)는 리눅스(Linux) OS의 창시자로 유명한데요, Git의 창시자이기도 합니다.

리누스 토르발스는 Git을 세상에 처음 소개할 때, '깃은 지옥에서 온 관리자'라고 했습니다. '관리되지 못한 수천만 줄의 소스 코드'는 지옥에 비견할 수 있는 작업 환경이었을 것입니다.

1-1. 깃으로 할 수 있는 것 ✅

1-1-1. 버전 관리 🚀

개발은 사실 버전 관리와의 싸움이기도 합니다. 만약 1000개가 넘는 문서를 수정할 때마다 위와 같은 방식으로 저장한다면 어떨까요? 저는 일단 상상하기조차 싫습니다.

문서를 수정할 때마다 '언제' 수정했는지, '어떤 것'을 변경했는지 등을 구체적으로 기록하는 것을 '버전 관리'라고 하고, 이러한 버전 관리를 담당하는 시스템이 바로 Git입니다.

1-1-2. 백업 🚀

우리가 사용하는 컴퓨터에는 '확실한 것'과 '불확실한 것'이 있습니다.

'확실한 것'은 '내 컴퓨터는 언젠가 고장난다'는 것이고, '불확실한 것'은 '내 컴퓨터가 언제 고장 날지 모른다'는 것입니다. 따라서 현재 컴퓨터에 있는 자료를 다른 컴퓨터에 복제하는, 백업 과정이 필수적으로 요구됩니다.

백업 공간을 제공하는 여러 온라인 저장소가 있는데요, 이러한 서비스 가운데 가장 많이 쓰이는 것이 GitHub입니다. 예전에 '정육각' 클론 코딩을 하고 Bitbucket이라는 원격 저장소에 코드를 백업하는 과정에서, 코드가 몽땅 날아간 사건이 생각나네요.

1-1-3. 협업 🚀

Git / GitHub의 최대 장점은 협업에 있습니다.

프랑스에 있는 A가 코딩을 한 뒤 원격 저장소에 올리면, 시애틀에 있는 B가 파일을 내려받아 추가 작업을 진행한 뒤, 그 결과물을 다시 원격 저장소에 올릴 수 있습니다.

누가 어느 부분을 어떻게 수정했는지 기록으로 다 남기 때문에, 나중에 오류가 발생했을 때 식별하기도 쉽습니다.

⚠️ 버전 관리를 이해하지 못하면, 백업을 이해할 수 없고, 백업을 이해하지 못하면 협업을 이해할 수 없습니다.

1-2. 리눅스 명령어 ✅

$는 리눅스 명령어임을 나타냅니다. 실제 터미널에 입력할 때에는 $를 제외하고 입력하면 됩니다.

1-2-1. 현재 디렉터리 살펴보기 🚀

code
$ pwd

pwd를 입력하면 현재 위치의 경로가 나타납니다.

code
/Users/wonminkwan

code
$ ls

ls를 입력하면 현재 디렉터리에 어떤 파일이나 디렉터리가 있는지 나타납니다.

code
111						mern_project
Applications			modify
Desktop					modules
Documents				my-app
Downloads				my-vite
IdeaProjects			myenv
Library					node_modules
MERN_Notes_App			package-lock.json
Movies					package.json
Music					phonebook
Music-App-React			project_fitness_app
Pictures				project_music_player
Postman					python
Postman Agent			react-firebase-auth
Public					redux-111
PyStat					redux-app
REACT					redux-practice
backend					redux-starter-kit

code
$ ls -l

ls 명령 뒤에 -l 옵션을 붙이면 파일이나 디렉터리의 상세 정보까지 표시할 수 있습니다.

code
total 2112
drwxr-xr-x   10 wonminkwan  staff     320  3 20  2023 111
drwx------@   4 wonminkwan  staff     128 11  3  2022 Applications
drwx------@  18 wonminkwan  staff     576  7  3 19:25 Desktop
drwx------+   7 wonminkwan  staff     224  2 19 20:29 Documents
drwx------+ 480 wonminkwan  staff   15360  7  3 19:25 Downloads
drwxr-xr-x    3 wonminkwan  staff      96 10 13  2022 IdeaProjects
drwx------@ 105 wonminkwan  staff    3360  1 21 21:12 Library
drwxr-xr-x    7 wonminkwan  staff     224  6 30  2024 MERN_Notes_App
drwx------    4 wonminkwan  staff     128 10 13  2022 Movies

1-2-2. 터미널 창 지우기 🚀

code
$ clear

clear를 입력하면 터미널 화면을 깨끗하게 비울 수 있습니다.

1-2-3. 터미널 창에서 디렉터리 이동하기 🚀

code
$ cd ..

상위 디렉터리로 이동하게 됩니다. /Users/wonminkwan 경로에서 위 명령어를 입력하면, /Users로 이동합니다.


code
$ cd wonminkwan

하위 디렉터리로 이동할 때에는 이동할 하위 디렉터리의 이름(wonminkwan)을 입력합니다.

1-2-4. 터미널 창에서 디렉터리 만들기 및 삭제하기 🚀

code
$ cd Documents
$ mkdir test

Documents 경로로 이동하여 test라는 이름의 하위 디렉터리를 만드는 명령어입니다.


code
$ rm -r test

test 디렉터리를 삭제하고 싶다면 rm 명령어를 사용하면 됩니다. 다만, 삭제할 디렉터리의 상위 디렉터리에서 rm 명령어를 수행해야 합니다.

즉, test를 지우고 싶다면 Documents 경로에서 rm 명령을 입력해야 합니다. -r 옵션을 통해 디렉터리 안에 있는 하위 디렉터리와 파일을 함께 삭제할 수 있습니다.

1-2-5. 터미널 종료하기 🚀

code
$ exit

터미널을 종료하게 됩니다. 창의 오른쪽 위에 있는 x를 클릭하는 것과 같은 효과를 냅니다.

⚠️ 리눅스 명령어는 사용하다보면 자연스럽게 익힐 수 있습니다. 애써 먼저 암기할 필요가 없습니다.

2. 깃으로 버전 관리하기 ✍️

2-1. 깃 저장소 만들기 ✅

바탕화면에 hello-git 디렉터리를 생성하고, 해당 디렉터리에 저장소(repository)를 생성하겠습니다.

code
$ git init

디렉터리를 생성한 뒤, 위 명령어를 입력합니다.

code
(base) wonminkwan@wonmingwan-ui-MacBookAir hello-git % git init
Initialized empty Git repository in /Users/wonminkwan/Desktop/hello-git/.git/

아무것도 없는 빈 폴더에서 명령어를 입력했더니 Initialized empty Git repository~ 메세지가 나타났습니다.

hello-git이라는 폴더에서 이제 깃을 사용할 수 있게 되었다는 의미입니다.

2-2. 버전 만들기 ✅

2-2-1. 작업 영역 이해하기 🚀

우리가 앞서 만든 hello-git 디렉터리는 작업 트리라고 합니다.

스테이지는 버전으로 만들 파일이 대기하는 곳입니다. 작업 트리에서 10개 파일을 수정했는데 4개만 버전으로 만들려면, 해당하는 파일 4개만 스테이지로 넘겨주면 됩니다.

저장소는 스테이지에서 대기하고 있던 파일들을 버전으로 만들어 저장하는 곳입니다.

2-2-2. 작업 트리에서 변경 사항 만들기 🚀

hello-git 디렉터리 하위에 hello.txt 파일을 추가하고 1을 입력하겠습니다. 이후에, 아래에 있는 명령어를 입력합니다.

code
$ git status
code
Untracked files:
  (use "git add <file>..." to include in what will be committed)
        hello.txt

Git에서는 한 번도 버전 관리를 하지 않은 파일을 Untracked files라고 합니다.

2-2-3. 스테이지에 변경 사항 올리기 🚀

code
$ git add hello.txt

위 명령어를 통해 작업 트리에서 변경된 hello.txt 파일을 스테이지에 올려보겠습니다.

다시 상태를 확인해보죠.

code
$ git status
code
Changes to be committed:
  (use "git rm --cached <file>..." to unstage)
        new file:   hello.txt

Changes to be committed~으로 문구가 변경되었습니다. 스테이징 된, 커밋 대상으로 변경되었다는 의미입니다.

2-2-4. 스테이징한 파일 커밋하기 🚀

code
$ git commit -m "message1"

이제 commit을 통해 저장소로 hello.txt 파일을 보내겠습니다. 이때, 어떤 변경 사항이 있었는지 간단히 메세지를 추가하고 싶을 때에는 -m 옵션을 활용합니다.

code
$ git status
code
nothing to commit, working tree clean

버전으로 만들 파일이 없고, 작업 트리도 수정 사항 없이 깨끗하다고 나오네요.

2-2-5. 스테이징과 커밋 동시에 처리하기 🚀

code
$ git commit -am

위 명령어를 통해 스테이징과 커밋을 동시에 처리할 수도 있습니다. hello.txt 파일에 2를 작성한 후, 스테이징과 커밋을 동시에 진행해 보겠습니다.

code
$ git commit -am "message2"
code
$ git log

message2라는 메세지와 함께 최신 버전 정보가 나타납니다.

code
(base) wonminkwan@wonmingwan-ui-MacBookAir hello-git % git log 
commit 0a5d722d6c9468b4396d17dac4e8f4a786b5d4b7 (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:18:59 2025 +0900

    message2

commit 1e392c7ee12b39c5df4eee44df9d341f4ababc73
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:16:25 2025 +0900

2-3. 커밋 내용 확인 ✅

2-3-1. 커밋 기록 자세히 살펴보기 🚀

code
$ git log

git log 명령을 입력했을 때 나타난 화면을 더 자세히 살펴보겠습니다.

code
(base) wonminkwan@wonmingwan-ui-MacBookAir hello-git % git log 
commit 0a5d722d6c9468b4396d17dac4e8f4a786b5d4b7 (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:18:59 2025 +0900

    message2

commit 1e392c7ee12b39c5df4eee44df9d341f4ababc73
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:16:25 2025 +0900

    message1

커밋을 구별해 주는 해시값, 작성자, 작성 일시, 커밋 메세지가 나타납니다.

커밋 해시 오른쪽에 있는 (HEAD -> main)는, 이 버전이 가장 최신이라는 표시입니다.

2-3-2. 변경 사항 확인하기 🚀

code
$ git diff

git diff를 통해, 작업 트리와 스테이지에 있는 파일을 비교하거나, 스테이지에 있는 파일과 저장소에 있는 최신 커밋을 비교해서 수정한 파일을 커밋 하기 전에 최종적으로 검토할 수 있습니다.

hello.txt에는 현재 1과 2가 입력되어 있는데요, '2'를 지우고 'two'를 추가해 보겠습니다.

code
$ git status
code
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git restore <file>..." to discard changes in working directory)
        modified:   hello.txt

아직 스테이징 상태가 아니라고 나오네요.

방금 수정한 파일이, 저장소에 있는 최신 버전의 hello.txt 파일과 어떻게 다른지 확인해 보겠습니다.

code
$ git diff
code
diff --git a/hello.txt b/hello.txt
index 7a754f4..669742f 100644
--- a/hello.txt
+++ b/hello.txt
@@ -1,2 +1,2 @@
 1
-2
\ No newline at end of file
+two
\ No newline at end of file

'2'가 삭제되었고, 'two'가 추가되었다고 정확하게 비교해 주네요.

우선, 후속 작업을 위해 'two'를 '2'로 다시 수정한 후 저장하겠습니다.

2-4. 파일 상태 확인 ✅

2-4-1. tracked 파일 / untracked 파일 🚀

git status를 입력하면, 작업 트리의 파일이 tracked 또는 untracked 상태로 나뉘는데요, 각각이 무엇을 의미하는지 알아보겠습니다.

hello.txt에는 숫자 3을 추가하고, hello2.txt 파일은 새롭게 생성한 뒤 a, b, c, d를 입력한 후 저장하겠습니다.

code
$ git status
code
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git restore <file>..." to discard changes in working directory)
        modified:   hello.txt

Untracked files:
  (use "git add <file>..." to include in what will be committed)
        hello2.txt

no changes added to commit (use "git add" and/or "git commit -a")

hello.txt는 커밋 했던 이력이 있기에 Changes not staged for commit~ 문구가 나타납니다. hello2.txt 파일은 새롭게 생성했고 스테이징 된 적도 없기에 Untracked files라고 나타납니다.

code
$ git add .
$ git commit -m "message3"

위 명령어를 통해 모든 파일을 스테이징 한 뒤 message3라는 커밋 메세지와 함께 커밋 해 보겠습니다.

code
$ git log --stat

--stat 옵션을 붙여, 커밋과 관련된 파일까지 함께 살펴보겠습니다.

code
commit caa0c5d86c065e86d6985d55f537521b9b15004a (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:45:28 2025 +0900

    message3

 hello.txt  | 3 ++-
 hello2.txt | 4 ++++
 2 files changed, 6 insertions(+), 1 deletion(-)

commit 0a5d722d6c9468b4396d17dac4e8f4a786b5d4b7
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:18:59 2025 +0900

    message2

 hello.txt | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

commit 1e392c7ee12b39c5df4eee44df9d341f4ababc73
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:16:25 2025 +0900

    message1

 hello.txt | 1 +
 1 file changed, 1 insertion(+)

방금 커밋 한 message3는, hello.txt와 hello2.txt 모두와 관련되어 있다는 점을 확인할 수 있습니다.

2-4-2. unmodified / modifie / stage 🚀

untracked는 앞서 설명했듯, 스테이징 된 적도 없는 상태를 의미합니다.

unmodified는 마지막 커밋 이후 변경되지 않은 상태를 뜻합니다.

modified 상태는, Changes not staged for commit과 같은 의미입니다. 수정 사항은 발생했으나 스테이징 되지 않았다는 뜻이지요. git add 명령어로 스테이징을 진행하면 됩니다.

마지막으로 staged 상태에서 커밋을 진행하면, 다시 unmodified 상태가 됩니다. 마지막 커밋 이후 변경 사항이 없기 때문이죠.

2-5. 작업 되돌리기 ✅

2-5-1. 작업 트리에서 수정한 파일 되돌리기 🚀

code
$ git restore

git restore 명령을 작성하면, 가장 최신 버전 상태로 돌아가게 됩니다.

이전까지는 잘 동작하다가, 새로운 코드를 추가했는데 정상적으로 동작하지 않는다면 이전 상태로 돌아가야겠죠.

code
$ git restore hello.txt

hello.txt에 이미 작성되어 있는 '3'을 three로 변경한 후 위 명령어를 작성하면, 곧바로 3으로 다시 복구되는 것을 확인할 수 있습니다.

2-5-2. 스테이징 되돌리기 🚀

위에서는 스테이징 하지 않은 상태에서 수정을 취소하고 복구했는데요, 이번에는 스테이징 된 내용을 되돌리는 방법에 대해 알아보겠습니다.

code
$ git restore --staged

hello2.txt 파일의 a, b, c, d를 모두 대문자로 바꾼 후 스테이징까지 처리해 보겠습니다.

code
On branch main
Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        modified:   hello2.txt

상태를 확인해 보니, 스테이징이 잘 되었습니다. 그런데, git restore --staged 로 unstage 할 수 있다고 알려주기까지 하네요.

code
On branch main
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git restore <file>..." to discard changes in working directory)
        modified:   hello2.txt

no changes added to commit (use "git add" and/or "git commit -a")

스테이징을 되돌리고 상태를 추적해 봤습니다. 변경 상태가 staged 되지 않았다고 잘 나오네요.

2-5-3. 최신 커밋 되돌리기 🚀

이번에는 커밋까지 진행된 작업 내용을 되돌리겠습니다. 커밋을 취소하면 스테이징이 함께 취소됩니다.

code
$ git reset HEAD^

hello2.txt에 E를 추가한 후, 스테이징과 커밋을 동시에 진행했습니다.

code
$ git commit -am "message4"

로그는 다음과 같습니다.

code
commit 52e0c9976d6722d938818d1dae76e7f88c6ff9f9 (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:17:12 2025 +0900

    message4

commit caa0c5d86c065e86d6985d55f537521b9b15004a
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:45:28 2025 +0900

    message3

commit 0a5d722d6c9468b4396d17dac4e8f4a786b5d4b7
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:18:59 2025 +0900

    message2

commit 1e392c7ee12b39c5df4eee44df9d341f4ababc73
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:16:25 2025 +0900

    message1

git reset HEAD^ 명령어를 입력한 뒤 다시 로그를 보죠.

code
commit caa0c5d86c065e86d6985d55f537521b9b15004a (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:45:28 2025 +0900

    message3

commit 0a5d722d6c9468b4396d17dac4e8f4a786b5d4b7
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:18:59 2025 +0900

    message2

commit 1e392c7ee12b39c5df4eee44df9d341f4ababc73
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:16:25 2025 +0900

    message1

커밋 했던 내용이 잘 되돌려졌네요.

2-5-4. 특정 커밋으로 되돌리기 🚀

최신 커밋이 아니라, 특정 버전의 커밋으로 되돌아가는 방법도 있습니다.

code
$ git reset 해시

rev.txt 파일을 생성 후 다음 절차를 진행합니다.

1. a를 입력한 뒤 커밋 메세지 R1을 붙여 커밋 2. b를 입력한 뒤 커밋 메세지 R2을 붙여 커밋 3. c를 입력한 뒤 커밋 메세지 R3을 붙여 커밋 4. d를 입력한 뒤 커밋 메세지 R4을 붙여 커밋

로그를 확인하면, 다음과 같습니다.

code
commit 2e500db9ae8cca008dcfa2eaaa02992e1cd43fd6 (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:24:01 2025 +0900

    R4

commit d2d84dc6f528047ccbc4217a1ceafacdb29bb0b0
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:23:45 2025 +0900

    R3

commit 88a89c25b911b6a46e790613101044accabaf91e
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:23:24 2025 +0900

    R2

commit 28f2187242239a961208c267e3e845371d5c4656
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:23:09 2025 +0900

    R1

이제 저는 R2 해시값을 복사해, R2 커밋 단계로 복귀해 보겠습니다.

code
commit 88a89c25b911b6a46e790613101044accabaf91e (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:23:24 2025 +0900

    R2

commit 28f2187242239a961208c267e3e845371d5c4656
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:23:09 2025 +0900

    R1

commit caa0c5d86c065e86d6985d55f537521b9b15004a
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:45:28 2025 +0900

    message3

commit 0a5d722d6c9468b4396d17dac4e8f4a786b5d4b7
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:18:59 2025 +0900

    message2

commit 1e392c7ee12b39c5df4eee44df9d341f4ababc73
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 20:16:25 2025 +0900

    message1

2-5-5. 커밋 변경 이력 취소하기 🚀

커밋은 취소하더라도, 커밋 한 기록은 남겨 두어야 할 때도 있습니다.

code
$ git revert 해시

rev.txt에 영문자 'e'를 추가하고 R5라는 메세지와 함께 커밋을 진행하겠습니다.

code
commit ca203fb0520f0d42797981b47ef05b2d380232d0 (HEAD -> main)
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:29:30 2025 +0900

    R5

commit 88a89c25b911b6a46e790613101044accabaf91e
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:23:24 2025 +0900

    R2

commit 28f2187242239a961208c267e3e845371d5c4656
Author: 원민관 <mkwan5741@gmail.com>
Date:   Thu Jul 3 21:23:09 2025 +0900

    R1

여기서 revert를 통해 R5 커밋을 취소하면, R5를 revert 한 새로운 커밋이 생깁니다.

3. 핵심 요약 ✍️

⚠️ Git의 핵심은 버전 관리, 백업, 협업을 위한 시스템으로, 코드의 변경 사항을 체계적으로 추적하고 관리하는 것입니다. 작업 트리에서 파일을 수정하고, 스테이지에서 커밋 할 파일을 선별한 후, 저장소에 버전으로 기록하는 3단계 워크플로우를 통해 언제 누가 무엇을 변경했는지 명확히 기록하며, 필요시 이전 버전으로 되돌릴 수 있어 안전하고 효율적인 개발 환경을 제공합니다.

⚠️ 다음 글에서는 Git의 브랜치(Branch) 기능과 원격 저장소 연결에 대해 다룰 예정입니다. 브랜치는 독립적인 작업 공간을 만들어 메인 코드에 영향을 주지 않고 새로운 기능을 개발하거나 실험할 수 있게 해주며, 작업 완료 후 merge를 통해 통합할 수 있습니다. 또한 GitHub와 같은 원격 저장소와 연결하여 로컬에서 작업한 내용을 클라우드에 백업하고, 여러 개발자가 동시에 같은 프로젝트에서 협업할 수 있는 방법을 학습하게 됩니다.

⚠️ 이 글에서는 Git의 기본 개념과 핵심 명령어를 다뤘지만, 실제 개발 환경에서 필수적인 VSCode와 Git 연동 방법 등이 요약하는 과정에서 유실되었을 수 있습니다. 더 체계적이고 완전한 Git/GitHub 학습을 원한다면 'Do it! 5일 만에 끝내는 깃&깃허브 입문' 도서를 구매하여 더 완전한 내용을 학습하시기를 강력히 권장합니다.