read

pro git book

git 사이트에서 Pro Git book을 제공하고 있습니다.
cherry-pick과 rebase가 궁금하여 읽기 시작했다가 거의 읽은거나 다름없어 완독해버렸습니다.
책 내용과 동일한 부분도 있고 제 나름대로 재 정리한 부분도 있습니다.
(정리하다보니 내용이 많아 좀 쳐냈습니다.)

Basics

git logo

Overview

Jessica의 Push는 성공했지만, John의 커밋은 서버에서 거절된다.
Subversion을 사용했던 사람은 이 부분을 이해하는 것이 중요하다.
같은 파일을 수정한 것도 아닌데 왜 Push가 거절되는 걸까?
Subversion에서는 서로 다른 파일을 수정하는 이런 Merge 작업은 자동으로 서버가 처리한다.
하지만, Git은 로컬에서 먼저 Merge 해야 한다.
John은 Push 하기 전에 Jessica가 수정한 커밋을 Fetch 하고 Merge 한다. p.122

HEAD는 현재 브랜치를 가리키는 포인터이며, 브랜치는 브랜치에 담긴 커밋 중 가장 마지막 커밋을 가리킨다. 지금의 HEAD가 가리키는 커밋은 바로 다음 커밋의 부모가 된다. 단순하게 생각하면 HEAD는 마지막 커밋의 스냅샷이다.

$ git show HEAD^

^ 뒤에 숫자도 사용할 수 있다. 예를 들어 d921970^2 는 “d921970의 두 번째 부모” 를 의미한다

$ git show HEAD~3

이것은 HEAD^^^ 와 같은 표현이다. 부모의 부모의 부모 즉 증조 부모쯤 되겠다. p.221

Use

Git Commit

$ git commit -am 'remove invalid default value'
=
$ git add
$ git commit -m  'remove invalid default value'

Git Merge

  • 3-way Merge

    현재 브랜치가 가리키는 커밋이 Merge 할 브랜치의 조상이 아니 Git은 ‘Fast-forward’로 Merge 하지 않는다.
    이 경우에는 Git은 각 브랜치가 가리키는 커밋 두 개와 공통 조상 하나 사용하여 3-way Merge를 한다.
    단순히 브랜치 포인터를 최신 커밋으로 옮기는 게 아니라 3-way Merge 의 결과를 별도의 커밋으로 만들고 나서 해당 브랜치가 그 커밋을 가리키도록 이동시킨다.
    그래서 이런 커밋은 부모가 여러 개고 Merge 커밋이라고 부른다. p.68

  • fast-forward

    C4 커밋이 C2 커밋에 기반한 브랜치이기 때문에 브랜치 포인터는 Merge 과정 없이 그저 최신 커밋으로 이동한다.
    이런 Merge 방식을 ‘Fast forward’라고 부른다. p.65

Merge 취소하기

예상하고 있던 일도 아니고 지금 당장 처리할 일도 아니라면 git merge –abort 명령으로 간단히 Merge 하기 전으로 되돌린다.
완전히 뒤로 되돌리지 못하는 유일한 경우는 Merge 전에 워킹 디렉토리에서 Stash 하지 않았거나 커밋하지 않은 파일이 존재하고 있었을 때뿐이다. 그 외에는 잘 돌아간다.
어떤 이유로든 Merge를 처음부터 다시 하고 싶다면 git reset –hard HEAD 명령으로 되돌릴 수 있다.
이 명령은 워킹 디렉토리를 그 시점으로 완전히 되돌려서 저장하지 않은 것은 사라진다는 점에 주의하자. p.261

$ git merge -Xignore-space-change whitespace

Merge 할 때 무수한 공백 때문에 문제가 생기면 그냥 Merge를 취소한 다음 -Xignore-all-space 나 -Xignore-space-change 옵션을 주어 다시 Merge 한다.
첫 번째 옵션은 모든 공백을 무시하고 두 번째 옵션은 뭉쳐 있는 공백을 하나로 취급한다.
팀원 중 누군가 스페이스를 탭으로 바꾸거나 탭을 스페이스로 바꾸는 짓을 했을 때 이 옵션이 그대를 구원해 준다. p.262

Merge 후의 결과를 Merge 하기 전의 브랜치와 비교하려면, 다시 말해 무엇이 합쳐졌는지 알려면 git diff –ours 명령을 실행한다.

$ git diff --theirs -b

Merge 할 파일을 가져온 쪽과 비교해서 무엇이 바뀌었는지 보려면 git diff –theirs 를 실행한다. 아래 예제에서는 공백을 빼고 비교하기 위해 -b 옵션을 같이 써주었다. p.264

$ git clean -f

수동 Merge를 위해서 만들었던 각종 파일은 이제 필요 없으니 git clean 명령을 실행해서 지워준다. p. 274

Git Delete

커밋한 파일을 제거할려면 로컬 환경에 있는 파일을 삭제한 후 커밋하면 됩니다.
이런 경우 로컬 환경에 있는 파일도 지워는 경우예요.

$ git rm A.files


커밋한 파일만 제거하고 로컬 환경에 있는 파일은 유지할려면 --cached 옵션을 이용하면 됩니다.
Untracked files 로 이동하는것을 확인할 수 있어요.

실제 사례 : Remote server 에 commit&push 한 파일을 지워야 하는 상황 발생!

$ git rm --cached box/tools.markdown

$ git status
On branch master
Your branch is up to date with 'origin/master'.

Changes to be committed:
  (use "git reset HEAD <file>..." to unstage)

	deleted:    box/tools.markdown

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

	box/tools.markdown

$ git commit -m"delete file form remote"
[master 5813a15] delete file form remote
 1 file changed, 36 deletions(-)
 delete mode 100644 box/tools.markdown

$ git push -u origin master

CONFIG

Global Config

global 설정에 .gitignore 파일을 작성해놓으면 모든 프로젝트에 적용됩니다.
(편리한 기능이죠)

$ git config --global -l
core.excludesfile=/Users/willow/.gitignore_global

 $ git help config           # config 명령 도움말

원격 저장소에 접근할때마다 사용자이름 암호를 입력하지 않도록 osxkeychain 기능을 이용할 수도 있지요.

$ git config -l

credential.helper=osxkeychain  

Local Config

프로젝트에 투입되었는데 config 의 이름, 이메일을 달리 설정해야 하는 경우가 있지요.
이런경우, 설정파일을 수정하거나 cli 명령으로 변경 가능합니다.


먼저, 기본 정보가 어떻게 되어 있는지 확인해 보아요.

$ git config --local --list  # 현재 프로젝트의 로컬 설정
$ git config --global --list # git global 설정
$ git config --list          # global, local 설정을 순차적으로 보여줍니다. 동일 항목인 경우 마지막 라인이 설정값이 됩니다.

명령어

$ git config --local --list
$ git config user.name willow  # 사용자이름
$ git config user.email willow@hahaha.com # 이메일

설정파일

프로젝트 최상위 디렉토리로 이동 후

$ vi /project/myproject1/.git/config   # local 설정

[user]
    name = willow              # 추가
    email = willow@hahaha.com  # 추가

Git Checkout

보통 checkout 은 브랜치간 이동할때 사용하지요.

checkout -f 옵션을 붙여서 강제로 브랜치를 Checkout 할 수 있지만,
서브모듈에서 저장하지 않은 내용을 되돌릴 수 없게 덮어쓰기 때문에 주의 깊게 강제 적용 옵션을 사용해야 한다. p.318

$ git checkout -f master


:herb: 쥔장의 Tip.

프로젝트 분석중에 파일이 수정되는 경우가 있지요.
(작은 공백이라던지, 실수로 누른 오타, 분석용 log 등등)

브랜치 단위로 엉망이 된경우 로컬 브랜치를 삭제하고 다시 checkout 해오세요.
파일 1~2개 인경우에는 파일 단위로 수정하는게 더 빠르지요.
파일 단위일때도 checkout 를 사용해보세요.

$ git status

Changes not staged for commit:
        modified:   ManageMapper.xml

$ git heckout ManageMapper.xml

$ git status
nothing to commit, working tree clean

Git Branching

branch

브랜치는 이슈가 생길때마다 생성하는 topic 브랜치
master, deveop과 같은 Long-Running 브랜치 가 있습니다.

branch 확인 명령어

$ git branch

간단한 정보를 보여준다.

$ git branch -vv

이 명령을 실행하면 로컬 브랜치 목록과 로컬 브랜치가 추적하고 있는 리모트 브랜치도 함께 보여준다.
게다가, 로컬 브랜치가 앞서가는지 뒤쳐지는지에 대한 내용도 보여준다.

 ~/willow/toybox (master) $ git branch -vv
  branch-test b50ce76 git branch test7
* master      f97be79 [origin/master: ahead 9] Merge branch 'branch-test'

로컬 브랜치가 커밋 9개가 앞서 있는 정보를 표시합니다. 리모트 브랜치에는 없는 커밋이 로컬에는 존재한 경우이지요.

branch 생성

$ git branch topic-branch

로컬에서 현재 브랜치에서 새로운 브랜치를 만듭니다.

$ git checkout -b featureB origin/master

브랜치를 만들면서 Checkout까지 한 번에 하려면 git checkout 명령에 -b 라는 옵션을 추가한다.

$ git checkout -b iss53
=
$ git branch iss53
$ git checkout iss53

그럼 옵션 -b 를 사용안하는 경우는 어떨까요.

$ git checkout origin/feature/topic-branch
...
Note: checking out 'origin/feature/topic-branch '.

~/Documents/source/my-project ((HEAD detached at origin/feature/topic-branch)) $

옵션 -b 가 없는 경우 HEAD 정보만 가져오게 됩니다.

branch 삭제

해당 이슈 Close 시 topic 브랜치도 함께 정리합니다.
큰 프로젝트인 경우 몇년을 방치하면 어마어마한 topic 브랜치무더기를 조우하게 됩니다.
(중요도를 몰라 삭제하기도 애매!)

(삭제하고자하는 브랜치가 아닌브랜치) $ git branch -d feature/topic-branch

* 기호가 붙어 있지 않은 브랜치는 git branch -d 명령으로 삭제해도 되는 브랜치다.
이미 다른 브랜치와 Merge 했기 때문에 삭제해도 정보를 잃지 않는다. p.72

$ git branch --merged
  branch-test
* master

branch 강제삭제

브랜치 삭제옵션에 강제 삭제가 있네요.

git branch (-d | -D) [-r] <branchname>...
       -d, --delete
           Delete a branch. The branch must be fully merged in its upstream branch, or in HEAD if no upstream was set with --track or --set-upstream.
       -D
           Shortcut for --delete --force.

코드 수정을 이것저것 다 했는데 필요없어진 경우입니다.

$ git branch -D feature/topic-branch

Git Rebase

히스토리를 한 줄로 관리하려고 Merge 보다 Rebase 나 Cherry-Pick을 더 선호하는 관리자들도 있다.
토픽 브랜치에서 작업을 마친 후 master 브랜치에 Merge 할 때 master 브랜치를 기반으로 Rebase 한다.
그러면 커밋이 다시 만들어진다.
master 대신 develop 등의 브랜치에도 가능하다. 문제가 없으면 master 브랜치를 Fast-forward시킨다.
이렇게 히스토리를 한 줄로 유지할 수 있다. p.151

저는 주로 rebase 명령 사용시 옵션 -i 를 이용합니다.

rebase -i 명령을 사용하면 여러 커밋을 하나의 커밋으로 합치거나 프로젝트의 관리자가 수정사항을 쉽게 이해하도록 커밋을 정리할 수 있다.

NAME
       git-rebase - Reapply commits on top of another base tip

SYNOPSIS
       git rebase [-i | --interactive] [options] [--exec <cmd>] [--onto <newbase>]

       -i, --interactive
           Make a list of the commits which are about to be rebased. Let the user edit that list before rebasing. This mode can also be used to split commits (see
           SPLITTING COMMITS below).
           번역 : rebase하려고하는 커밋의 목록을 만드십시오. 리베이스하기 전에 사용자가 해당 목록을 편집하도록하십시오. 이 모드를 사용하여 커밋을 분할 할 수도 있습니다

프로젝트 관리자가 사람들의 수정 사항을 Merge 하고 나서 Jessica의 브랜치를 Merge 하려고 할 때 충돌이 날 수도 있다.
그러면 Jessica가 자신의 브랜치를 origin/master 에 Rebase 해서 충돌을 해결하고 다시 Pull Request을 보낸다.

$ git checkout featureA
$ git rebase origin/master
$ git push -f myfork featureA

브랜치를 Rebase 해 버렸기 때문에 Push 할 때 -f 옵션을 주고 강제로 기존 서버에 있던 featureA 브랜치의 내용을 덮어 써야 한다. 아니면 새로운 브랜치를(예를 들어 featureAv2) 서버에 Push 해도 된다.

$ git checkout -b featureBv2 origin/master
$ git merge --squash featureB
# (change implementation)
$ git commit
$ git push myfork featureBv2

–squash 옵션은 현재 브랜치에 Merge 할 때 해당 브랜치의 커밋을 모두 커밋 하나로 합쳐서 Merge 한다.
이 때 Merge 커밋은 만들지 않는다.
다른 브랜치에서 수정한 사항을 전부 가져오는 것은 똑같다.
하지만 새로 만들어지는 커밋은 부모가 하나이고 커밋을 기록하기 전에 좀 더 수정할 기회도 있다.
다른 브랜치에서 수정한 사항을 전부 가져오면서 그전에 추가적으로 수정할 게 있으면 수정하고 Merge 할 수 있다.
게다가 새로 만들어지는 커밋은 부모가 하나다.
–no-commit 옵션을 추가하면 커밋을 합쳐 놓고 자동으로 커밋하지 않는다.

branch-test 에 master 내용을 덮어 쓴 후 충돌된 것들을 처리합니다.

  • 충돌이 없는 경우

master head 를 상속 받은 경우 (branch-test head 부모값과 일치) 입니다.
사실, sub 브랜치가 master 브랜치 상속받아 작업 후 commit 한 경우는 굳이 rebase 할 필요없이 merge(fast-forward) 하면 됩니다.

(branch-test) $ git rebase master
First, rewinding head to replay your work on top of it...
Applying: rebase test2
  • 충돌이 있는 경우

master head 부모값과 branch-test 브랜치 head 부모값이 다른 경우입니다.

    (develop) $ git checkout branch-test
(branch-test) $ git rebase master
Applying: topic branch conflict
Using index info to reconstruct a base tree...
M	practice_git/1.txt

충돌된 코드를 정리합니다.

((no branch, rebasing branch-test)) $ git add practice_git/1.txt
((no branch, rebasing branch-test)) $ git rebase --continue
Applying: topic branch conflict

rebase 명령을 실행하면 새로운 commit 을 만들어 냅니다.

  • Rebase before
(branch-test) $ git tree
*       8d56111 2019-05-08 (HEAD -> branch-test)  topic branch conflict (willow)
| *     15a926c 2019-05-08 (master)  rebase test conflict (willow)

  • Rebase after : new commit 생성
$ git tree
*       29b3723 2019-05-08 (HEAD -> branch-test)  topic branch conflict (willow)
*       15a926c 2019-05-08 (master)  rebase test conflict (willow)

rebase 다양한 명령어

git pull –rebase 로 Rebase 할 수도 있다.

git pull --rebase
=
git fetch
git rebase teamone/master

이 두 명령을 직접 순서대로 실행해도 된다.

Cherry pick

pull request 출처 : https://www.atlassian.com/ko/git/tutorials/making-a-pull-request


체리픽을 처음 경험한것은
이슈 처리 후 feature 브랜치에 커밋 해야하는데
develop(권한없는)브랜치에 커밋를 실행해버린 상황이 발생했을 때 였어요.
그 저장소 develop 브랜치는 PR(Pull Request)후 권한자만 커밋 가능했어요.
당연히 에러가 났지요. ㅎㅎ


:astonished: 이런 상태로 있던 절보고
옆자리 차장님이 feature 브랜치에 체리픽하고 커밋 후 SoCool~ 사라지시는거예요.
(멋쪙! :heart_eyes:)

$ git checkout develop          # 권한없는 브랜치
$ git commit -m "DEV-114 Ooops" # 에러남..
$ git checkout feature/DEV-114  # 권한있는 브랜치
$ git cherry-pick HEAD값

SourceTree 툴에서도 가능하답니다.

체리 픽

한 브랜치에서 다른 브랜치로 작업한 내용을 옮기는 또 다른 방식으로 Cherry-pick이란 것도 있다.
Git의 Cherry-pick은 커밋 하나만 Rebase 하는 것이다.
커밋 하나로 Patch 내용을 만들어 현재 브랜치에 적용을 하는 것이다.
토픽 브랜치에 있는 커밋 중에서 하나만 고르거나 토픽 브랜치에 커밋이 하나밖에 없을 때 Rebase 보다 유용하다. p.151

$ git cherry-pick e43a6
Finished one cherry-pick.
[master]: created a0a41a9: "More friendly message when locking the index fails."
3 files changed, 17 insertions(+), 3 deletions(-)

위 명령을 실행하면 e43a6 커밋에서 변경된 내용을 현재 브랜치에 똑같이 적용을 한다.
하지만, 변경을 적용한 시점이 다르므로 새 커밋의 SHA-1 해시값은 달라진다. p.152

Reset

커밋 히스토리를 보는 웹페이지가 깨진 문자열로 인해 페이지 오류가 발생하였습니다.
(허허~)
개발자마다 환경 셋팅이 달라 벌어진 일이였지요.
(윈도우OS에서 Visual Studio를 이용하여 커밋한 경우)

SourctTree 화면

위 경우는 원격 저장소에 커밋된 상황이지요.
reset 명령은 로컬 저장소에서 실행 하라고 권고하지만 강제 실행합니다요;;

이런경우 저장소(프로젝트)에 참여중인 개발자 모두에게 알려서 동기화 해야 합니다. :scream:

$ git reset --hard ec89d82
HEAD is now at ec89d82

SourctTree 에서도 할 수 있지요. (친절한 소트씨)

SourctTree 화면

원격 저장소의 HEAD 도 변경해야겠지요. (이런경우는 최대한 피하세요.)

$ git push -f                        
Total 0 (delta 0), reused 0 (delta 0)
To https://git.willow.pe.kr/dev/website.git
 + 0e67005...849641d develop -> develop (forced update)


reset 명령을 실행할 때 아무 옵션도 주지 않으면 기본적으로 –mixed 옵션으로 동작한다. p.250

--soft옵션은 HEAD브랜치만 이동

git reset --soft HEAD~

--mixed옵션은 HEAD브랜치 이동 + Index HEAD스냅샷 업데이트

git reset --mixed  HEAD~

--hard옵션은 HEAD브랜치 이동 + Index HEAD스냅샷 업데이트 + 워킹디렉토리 업데이트

git reset --hard HEAD~


:cactus: --hard 옵션은 되돌리는 것이 불가능합니다.
워킹 디렉토리의 파일까지 강제로 덮어쓰기 때문이지요.
꼭 필요할때만 사용하세요.

Git on the Server

Clone

로컬에 저장소를 생성하는 방법중에는
init 명령어로 로컬 저장소를 생성하고 원격 저장소를 설정하는 방법과
clone 으로 생성하는 방법이 있지요.

진행중인 오픈소스나 프로젝트 저장소를 clone 해서 로컬 저장소로 가져옵니다.

$ cd /myForest/myTree
$ git clone https://sample-project.sample.com/mytree.git

Remote repository

$ git remote -v                 # 원격 저장소 정보
$ git remote show               # 로컬브랜치의 원격 저장소 명
$ git remote show origin        # origin(원격 저장소) 정보 (브랜치별 정보 확인)  

$ git remote add myfork (url)   # 원격 저장소 fork

git fetch

git fetch [remote-name]이 명령은 로컬에는 없지만, 리모트 저장소에는 있는 데이터를 모두 가져온다.
그냥 쉽게 git pull 명령으로 리모트 저장소 브랜치에서 데이터를 가져올 뿐만 아니라 자동으로 로컬 브랜치와 Merge 시킬 수 있다.
리모트 서버로부터 저장소 정보를 동기화하려면 git fetch origin 명령을 사용한다. 명령을 실행하면 우선 “origin” 서버의 주소 정보(이 예에서는 git.ourcompany.com)를 찾아서, 현재 로컬의 저장소가 갖고 있지 않은 새로운 정보가 있으면 모두 내려받고, 받은 데이터를 로컬 저장소에 업데이트하고 나서, origin/master 포인터의 위치를 최신 커밋으로 이동시킨다.
git fetch 명령을 실행하면 서버에는 존재하지만, 로컬에는 아직 없는 데이터를 받아와서 저장한다.
이 때 워킹 디렉토리의 파일 내용은 변경되지 않고 그대로 남는다.
서버로부터 데이터를 가져와서 저장해두고 사용자가 Merge 하도록 준비만 해둔다.

$ git fetch origin

원격 master 브랜치를 fetch 합니다.

$ git fetch --all; git branch -vv

모든 브랜치를 fetch 한 후 브랜치 정보를 보여줍니다.

git full

트래킹 브랜치에서 git pull 명령을 내리면 리모트 저장소로부터 데이터를 내려받아 연결된 리모트 브랜치와 자동으로 Merge 한다.

git push

로컬에만 있는 브랜치인 경우 원격에 동일한 이름으로 생성하고 push 합니다.
기존에 존재하는 브랜인 경우 원격에 push 합니다.

git push `remote` `branch`   
git push `remote` `locally-branch:remote-branch`
$ git push origin branch-test
=
$ git push origin branch-test:branch-test
$ git push -u origin featureB:featureBee

명령에서 사용한 -u 옵션은 –set-upstream 옵션의 짧은 표현인데 브랜치를 추적하도록 설정해서 이후 Push 나 Pull 할 때 좀 더 편하게 사용할 수 있다. p.131

Git Diff

$ git diff master...contrib

앞서 살펴본 master..contrib 형식을 사용하여 확인할 수도 있다. diff 명령을 사용할 때 두 브랜치 사이에 를 쓰면, 두 브랜치의 공통 조상과 브랜치의 마지막 커밋을 비교한다. Git은 Triple-Dot 구문으로 간단하게 위와 같이 비교하는 방법을 지원한다. diff 명령을 사용할 때 두 브랜치 사이에 를 쓰면, 두 브랜치의 공통 조상과 브랜치의 마지막 커밋을 비교한다. git log 명령에 -p 옵션을 주면 각 커밋에서 실제로 무슨 내용이 변경됐는지 살펴볼 수 있다. 이 옵션은 각 commit의 뒤에 diff의 내용을 출력해 준다. p.147

$ git log contrib --not master

먼저 지금 작업하는 브랜치에서 master 브랜치에 속하지 않는 커밋만 살펴보는 것이 좋다. –not 옵션으로 히스토리에서 master 브랜치에 속한 커밋은 제외하고 살펴본다.

git diff --chec

무엇보다도 먼저 공백문자를 깨끗하게 정리하고 커밋해야 한다. Git은 공백문자를 검사해볼 수 있는 간단한 명령을 제공한다.
커밋을 하기 전에 git diff –check 명령으로 공백문자에 대한 오류를 확인할 수 있다. p.120

Git Clean

워킹 디렉토리 청소하고 싶나요?
-x -i 옵션을 사용하면 정리될 파일 목록을 확인 후 선택할수 있게 나옵니다.

$ git clean -x -i

Would remove the following item:
  framework.iml

*** Commands ***
    1: clean 2: filter by pattern  3: select by numbers  4: ask each  5: quit 6: help
What now> 5
Bye.

작업하고 있던 파일을 Stash 하지 않고 단순히 그 파일들을 치워버리고 싶을 때가 있다.
git clean 명령이 그 일을 한다.
이 명령을 사용할 때는 신중해야 한다.
이 명령을 사용하면 워킹 디렉토리 안의 추적하고 있지 않은 모든 파일이 지워지기 때문이다.
명령을 실행하고 나서 후회해도 소용없다.
지워진 파일은 돌아오지 않는다.
git stash –all 명령을이용하면 지우는 건 똑같지만, 먼저 모든 파일을 Stash 하므로 좀 더 안전하다.
-f 옵션은 강제(force)의 의미이며 “진짜로 그냥 해라”라는 뜻이다. p.223

Git Log

SourceTree같은 UI툴을 사용 안하시는 경우
아래 명령으로 간단하게 log 를 확인하실 수 있어요.

$ git log --pretty=oneline -10
$ git log --pretty=format:"%h - %an, %ar : %s"

예쁘게 :sparkles: 보고싶다면 format 옵션을 추가할 수 있지요.
너무 기니까 alias 에 넣어서 간단하게 볼까요?

$ vi ~/.gitconfig

 [alias]
     tree = log --graph --full-history --all --color --date=short --pretty=format:\"%Cred%x09%h %Creset%ad%Cblue%d %Creset %s %C(bold)(%an)%Creset\"

짜잔~~~ :star2:

~/willow/toybox (master) $ git tree
*       6728219 2019-04-09 (HEAD -> master, origin/master)Merge remote-tracking branch 'origin/master' (willow)
|\  
| *     94c2d3e 2019-04-09  Create README.md (willow)
* |     9af384f 2019-04-09  VO 2 (willow)
|/  
*       d4c0fc2 2019-04-09  VO 1(willow)
*       8114700 2019-04-09  START (willow)
*       8735c10 2019-04-04  Initial commit (willow)

옵션

git log 명령에 –abbrev-commit 이라는 옵션을 추가하면 짧고 중복되지 않는 해시 값을 보여준다.
기본으로 7자를 보여주고 해시 값이 중복되는 경우 더 긴 해시 값을 보여준다.
보통은 8자에서 10자 내외로도 충분히 유일하게 커밋을 나타낼 수 있다. p.208

$ git log --abbrev-commit --pretty=oneline
ca82a6d changed the version number
085bb3b removed unnecessary test code
a11bef0 first commit

Git은 자동으로 브랜치와 HEAD가 지난 몇 달 동안에 가리켰었던 커밋을 모두 기록하는데 이 로그를 Reflog라고 부른다.
git reflog 를 실행하면 Reflog를 볼 수 있다.
Reflog의 일은 모두 로컬의 일이기 때문에 내 Reflog가 동료의 저장소에는 있을 수 없다. 이제 막 Clone 한 저장소는 아무것도 한 것이 없어서 Reflog가 하나도 없다.p.209

$ git reflog
734713b HEAD@{0}: commit: fixed refs handling, added gc auto, updated
d921970 HEAD@{1}: merge phedders/rdocs: Merge made by recursive.
1c002dd HEAD@{2}: commit: added some blame and merge stuff
1c36188 HEAD@{3}: rebase -i (squash): updating HEAD
95df984 HEAD@{4}: commit: # This is a combination of two commits.
1c36188 HEAD@{5}: rebase -i (squash): updating HEAD

ETC

gc 명령
최적화하고 나서 저장소 크기가 얼마나 되는지 확인한다.

$ git gc

count-objects 명령은 사용하는 용량이 얼마나 되는지 알려준다.

$ git count-objects -v
count: 7
size: 32
in-pack: 17
packs: 1
size-pack: 4868
prune-packable: 0
garbage: 0
size-garbage: 0

size-pack 항목의 숫자가 Packfile의 크기다.
단위가 킬로바이트라서 이 Packfile의 크기는 약 5MB이다. p.430

개발 시나리오

디자인팀 협업시

디자인팀 브랜치 이어서 개발팀 브랜치 생성합니다.
개발작업 완료 후 develop 브랜치 병합을 하는 시나리오 입니다.
(Jira 에서 브랜치 생성안하고 cli 에서 생성해도 Jira가 자동으로 잡아주네요! 야홋!)

(feature/DESIGN-99) $ git config --list| grep email # 저장소별 계정이 다른경우
(feature/DESIGN-99) $ git remote -v                 # 저장소별 원격 서버가 다른경우
(feature/DESIGN-99) $ git checkout -b feature/DEV-199 origin/feature/DESIGN-99
   (feature/DEV-99) $ git add .
   (feature/DEV-99) $ git commit -m"DEV-99: add option"
   (feature/DEV-99) $ git commit -am"DEV-99: change v2" # 기존파일을 수정후 commit 하는경우 -am 옵션 사용가능
   (feature/DEV-99) $ git push origin feature/DEV-99
   (feature/DEV-99) $ git checkout develop
          (develop) $ git merge feature/DEV-99
          (develop) $ git push origin

배포(CI)툴로 배포시 파일 실행권한

프로젝트 재 배포 후 스케쥴러에서 실행되거나 AWS에서 자동실행되어야하는 파일인 경우 실행권한이 필요하게 되지요.

스크립트 파일들에 실행 권한을 추가해서 Git에 올리고 싶다면 다음과 같은 명령어를 이용하면 된다.
git update-index –chmod=+x 서비스 운영이 쉬워지는 AWS 인프라 구축 가이드 p.133스크립트>

로컬에서 아래와 같이 명령어를 사용합니다.

(master) $ git update-index --chmod=+x scripts/stop_application.sh

AWS에서 git clone 후 확인해보니 실행권한이 있네요.

[ec2-user@ip-172-xx-xx-xx scripts]$ ls -al
-rwxr-xr-x 1 root root   86  9월 25 05:26 stop_application.sh

git commit featured

Blog Logo

Weeping Willow


Published

Image

Willow's Blog

Welcome!

Back to Overview