ASTRO Camp Day35 - GIT(03)
GIT 第三堂課
1、ssh-keygen設定
設定GitHub的SSL
1-1、ssh-keygen指令
首先在終端機打上
> ssh-keygen
這樣打後,會產出一份public、private的key
通常放的路徑是在這/home/aaaaaa/.ssh/id_rsa
如果想看到實際資料夾的位置,可以在mac搜尋bar打 ~/
這樣打後選擇進自己使用者的資料夾位置,然後打
command + shift + . ,這樣就可以看到/ssh資料夾
如果不會用終端機進到.ssh的位子,可以照著下面做
(1) 開啟 Finder
(2) 對著”下載項目”按右鍵
(3) 點選”顯示上層資料夾”
(4) 最後鍵盤同時按下,shift + command + .
(5) 這樣就可以成功看到.ssh的資料夾了
1-2、查看金鑰
那要怎麼看自己金鑰呢?只要切到使用者的資料夾,並輸入以下指令
> cat id_rsa.pub -> 可以印出你的鑰匙
!!印出鑰匙後,可以把鑰匙放到GitHub上!!
2、Git push
接下來到github建立空的repository,並在終端機輸入以下的指令,就可以把本機的檔案推到github上
如果想要知道指令,可以打下面的指令
git help branch
2-1、把本機檔案推上遠端
輸入以下指令,可以把本機檔案推上去
> git remote add origin git@github.com:eagle0526/git3-test.git # 在遠端加分支
> git branch -M (current_branch) main # 強制把目前的分支改成main分支
> git push -u origin main # 我想要把畚箕的main分支的進度,推一份origin上
2-2、查看遠端節點
到終端機下這一行,可以看到目前有的遠端節點,不過現在會發現啥都沒有(因為啥都還沒加上去)
> git remote -v
2-3、新增遠端節點分支
第一行的origin可以改,這一行的意思就是在遠端加上一個tiger分支
> git remote add tiger git@github.com:eagle0526/git3-test.git
接著我們在下這一行,這時候就會發現,遠端有一個tiger的節點
> git remote -v # 印出遠端節點
2-4、更改遠端節點
更改遠端節點,把目前的tiger節點,改成dragon節點
> git remote rename tiger dragon
2-5、刪除遠端節點
刪除遠端節點,把目前的dragon節點刪掉
> git remote remove dragon
2-6、把本機分支推上遠端
最後下push指令,就可以把目前本機的main分支,推一份到遠端節點上面
> git push -u origin main
2-7、git push upstream
如果現在重新在檔案加上新的檔案,並git add . 、 git commit,此時直接推上去,會發生上游衝突,他會說起前的main沒有上游分支
因此我們這樣打,給main一個上游分支,像下面這樣打,把本機的分支跟遠端的分支做掛鉤,origin是遠端也就是上游,把main當作預設的本地分支
> git push -u origin main
> ps. 這個-u是upstream的意思
設定好上游分支後,之後就可以只打git push,就都會預設幫你把main分支的東西一起推上去了
如果你之後想改預設的本機分支,可以這樣改
> git push -u origin feature/abc
這樣的意思是,我要把本機的feature/abc設定為預設分支,並且推上去
github禁止直接推到某個分支上
branch protection rules
3、Git push 的進階用法
3-1、把本地分支推上去改成別的分支
今天如果想把本地的main推一份到遠端的origin分支,並形成一個main分支
這是一個簡寫
> git push origin main
上面那行指令的完整型態
> git push origin main:main
如果知道完整型態的寫法的話,可以修改成下面這樣
這行的意思是,把一份本地的main,推一份到遠端的origin,並在線上行程一個cat分支
> git push origin main:cat
3-2、Heroku範例
之後做專案會用到的Heroku,我們會下這段指令,推一份本地的main分支,到遠端的heroku上面,並建立一個main分支
> git push heroku main
你只要推上一個main分支上去,heroku就會自動幫你執行一大段東西
如果你今天在做feature的member分支,你可以直接這樣打,這樣就可以直接讓heroku吃到main分支
> git push heroku feature/member:main
3-3、把遠端的cat分支刪掉
用這種方法把遠端分支刪掉,他的原理是
:前面的是一個空分支,用空分支推到遠端的origin,並形成cat分支
> git push origin :cat
4、Git Pull vs. Git Fetch vs. Git Merge
剛剛講完了如何把本機檔案推上git,現在來說明一下如何把檔案從GitHub載下來
4-1、git clone 下載檔案
首先隨便開一個資料夾,cd到裡面後,下指令
> git clone git@github.com:eagle0526/git3-test.git
4-2、git remote -v 查看遠端分支
抓下來後,可以看一下遠端分支現在在哪
會發現clone下來的時候,還會順便幫你遠端節點設定好
> gti remote -v
4-3、git fetch 線上抓下新檔案
如果今天線上進度比本機還新,要怎麼把檔案抓下來呢
> 本機 github
>
> 口 git在這
>
> 口 本機進度在這 口
>
> 口 口
>
> 口 口
接下來用fetch指令,他會在本機抓線上最新的檔案回來,並且在本機形成一個遠端分支,origin/main為啥叫這個名字呢。因為遠端分支是origin,本機分支是main
> 本機 github
>
> 口 本機要更新到這 口 git在這
> origin/main
> 口 口
>
> 口 口
>
> 口 口
把遠端分支最新的檔案抓下來到本機
> git fetch origin main
4-4、git merge 線上融合本機分支
把剛剛線上fetch下來的檔案,跟本機的進度merge
已下指令就可以把本機的main跟origin分支融合
> git merge origin/main
4-5、git pull 拉下遠端分支、融合本地分支
pull的指令是一次做完fetch、merger在做的事
> git pull = git fetch + git merge
如果今天git pull有衝突,是git merge的衝突喔,因為純粹fetch拉下來,不會有錯誤
錯誤是發生在東西合併
5、多人協作
如果今天A先推一份上去到github,這時候B也想推上去,會造成B推不上去
因為A已經推新的上去了,B需要先拉一份檔案下來,再推上去
> A人 main分支 B人
>
> O --> 先推上去 O <-- 推不上去 X
>
> 口 口 git原先在這 口
>
> 口 口 口
>
> 口 口 口
>
> 口 口 口
解決方法,B先拉一份下來,再推上去
> A人 github B人
>
> X + O <--推上去 X + O
>
> O --> 先推上去 O X + O (先拉下來)
>
> 口 口 git原先在這 口
>
> 口 口 口
>
> 口 口 口
>
> 口 口 口
如果今天都在main分支上做,會讓main分支很混亂 所以通常會開其他分支,確定好後再推到main分支上
6、PUll Request(PR)
6-1、發PR的人
如果你今天對某個專案感興趣,並且想要給他修改建議,你可以先fork一份他的專案到你自己的GitHub上
接著你就可以更改這個專案的內容了,改好之後,就可以點選Pull Request,然後寫下你這次的改動
6-2、收PR的人
假設原作同意收下這個pr,下面會有一個Merge pull request的按鈕可以按,按下去之後,檔案就會直接更動
Ps. 原作者在收的時候,可以在右邊的部分,對這個PR評論,並且如果覺得他寫得太爛,可以直接退還給他
之後團隊合作,都是用PR的方式來協作
6-3、Finish your review
看完PR後有三個選項可以選
- comment - 單純評論
- approve - 認同這則改動(如果到一定數量的認同,就會開啟可以點擊receive的功能)
- request change - 寫太爛,請改過
6-4、三種收pr的方式
假設原本的commit數量有2個
> create a merge commit -> 會有一個新的節點(對方發的commit有兩個,收完之後變五個)
> rebase and remote -> 不會有節點(對方發的commit有兩個,收完之後變四個)
> squash and merge -> 全部搜集成一個commit(對方發的commit有兩個,收完之後變三個)
如果PR衝突怎麼辦,主辦人退回給寫PR的人,叫他改過再來
什麼時候會用到squash?就是發PR的人寫太多無用訊息
Approve的效用
可以設定,每一個PR有多少人Approve,才可以merge進去專案裡面
所以在做專案的時候,如果團隊有五個人,一定要設定approve是四個
這樣代表大家都要同意這件事,才能讓專案推上去
7、Git世界觀 - 11/29 - 下午筆記還沒做
寶藏都在.git目錄裡面(git init會產生的檔案)
blob代表檔案 tree代表目錄 commit tag
7-1、git的blob物件計算
> #引用sha1
> require "digest/sha1"
> 寫一段內容
> content = "hello, 5xRuby"
> 計算公式
> input = "blob #{content.length}\0#{content}"
> 可以把blob後的結果印出來試試
> puts Digest::SHA1.hexdigest(input)
14:10
這個東西 -> “|” 可以把後面的指令,倒給前面 因此我們可以下這個指令,來印出index檔的sha1
> git index.html | git hash-object --stdin
> 印出e90bdb3679f7cfd0278b8d1aa9e8626c46eedf21
上面那個結果,會被塞到.git檔案裡面的.objects資料夾 並且取e9做一個資料夾,後面其他值會變成裡面的檔案的名字
在git的世界,空的資料夾是無法被版控的 裡面至少要有一個檔案,就算檔案是空的也沒關係
可以看某一串sha-1的型態
> git cat-file cda3d2e -t
可以看該commit的詳細資訊
> git cat-file cda3d2e -p
這個commit裡面有一個tree,叫做417e Ps. 每一個commit底下都會有個tree
繼續往下追
> git cat-file 417e -p
會發現裡面有一個tree、一個blob
第一次commit,會指向
7-2、第二次commit
先把某個檔案的內容改過(index.html)
當你git add、commit 後,他又生成了另外一個commit
叫做b7c7
git cat-file b7c7aad
會發現裡面有一個tree(1480)、parent(cda4 -> 指向前一個commit)
git cat-file 1480 -p
裡會有一個e6928,他就是剛剛的database的tree
如果今天有兩個檔案內容一樣,標題不一樣,會被算同一個blob
7-4、第三次commit
產生出ba90的blob
git cat-file ba90
裡面有一個123c的commit、前一個的tree
14:46 git世界觀的動畫
git設計概念
DAG 有相無還圖 -> 有方向但是不會造成循環
7-5、切換分支的時候發生了什麼事
首先HEAD會移動,並且整個專案的資料都會回到當時檔案的狀態
git不是在做差異備份
git是整個一起備份
7-6、git完整備份的好處
雖然完整備份比較比較浪費空間,但是還原速度很快
因為我是整個檔案拉下來,不用去比較差異
7-7、既然git只記錄檔案內容,那怎麼知道他叫什麼名字?
blob物件決定檔案的內容
tree物件決定檔案的樣子
blob是在add時候會產生
tree是在commit之後才會產生的
7-8、git add指令可以把檔案加到暫存區,為什麼有些資料被說是加到索引
當我們git add的時候,會建立一個份資料到index那邊
Ps. 暫存區又稱為索引index區
7-9、關於分支
開一個新分支,會在res/head裡面,新增一個檔案 如果今天直接把檔案名改掉,分支的名稱就會變了 或者是你把分支裡面的sha1值換掉,那個分支會直接換到新改的sha1
如果今天下此指令,會在head那邊新增一個aaa的資料夾,裡面有bbb的檔案
> git branch aaa/bbb
如果今天先開一個feature的分支,然後再建立一個feature/aaa
這樣會報錯喔,原因是因為檔案名相撞了
7-10、HEAD是什麼東西
內容 = 某個commit的sha1或者是某個分支的名稱
7-11、關於標籤
通常會打一個標籤,有可能是因為有一個里程碑 如果今天有新增tag,會出現在refs的tags裡面
輕量化標籤 vs 普通標籤
普通標籤是有註記的標籤,如果今天去cat-file這個標籤,會發現裡面有藏一個物件
它的功用是可以讓這個標籤有更清楚的內容
輕量化標籤就單純只有標籤上面的名字
7-12、修改commit歷史
用reset修改,讓最新的的
> git reset HEAD \^ --soft
> git commit -m "add fish"
用”–amend”,可以對最後一個commit做修改
> git commit -m "add fish" --amend
我要從現在的所在地,指定的sha1,做互動式的修正 不過這個要到VIM介面修改
> git rebase --i sha1
> 在終端機輸入,就會跳出VIM的介面
如果今天老闆要你改歷史紀錄,但是因為內容改掉了,整個sha1會重設,會導致其他人都推不上去
所以如果真的要重改歷史紀錄,要記得通知其他協作人員,並且請他們重新clone這一份檔案
> git push -f # 強推上github
7-13、revert
再多人協作的情況下,可以對某個commit,對他下revert指令
這樣當其他人收到clone下來時,他不會拿到被revert的那個檔案
7-14、Flow
多人協作一定會用到的流程