引言:
不積跬步,無以至千里;不積小流,無以成江海。原本自以爲對git相關的東西以及原理已經有了不錯的認識和理解,然而當碰到一個小小的problem才發現自己掌握得並沒有自己想象的那麼好,好記性不如爛筆頭,於是決定把自己對.gitignore以及submodule的部分理解簡單記錄下來,由於個人能力有限,如有不當之處,歡迎指正。
git submodule
git submodule在項目中雖一直在使用(用於維護自有公共類庫),不過對此知之甚少,於是抽空做一個小小的總結。可運行git submodule –help獲取幫助doc。
目地:多項目維護共用公共類庫starjazz
步驟:
在項目中初始化submodule
- 在即將引用的項目中初始化此git submodule
git submodule add http://gitlab-ce.yougitlabname.com/backend/starjazz
git status
新文件: .gitmodules
新文件: starjazz
生成的.gitmodules文件中記錄了submodules的path路徑以及url指針,同時在.git文件夾下你能找到你剛剛添加的子模塊starjazz
- cd starjazz && git status
mkdir: 已創建目錄 '/home/zhoudazhuang/.zsh_history/home/zhoudazhuang/x/wechatMetric/starjazz'
位於分支 master
您的分支與上游分支 'origin/master' 一致。
無文件要提交,乾淨的工作區
即可作爲一個獨立的公共類庫進行提交和變更。
- cd starjazz && git status
- 在主(父)項目中提交加入的git submodule
- cd .. && git status
- git add .
- git commit -m ‘submodule’
- git push origin test
提交後會在主(父)項目中生成對submodule的引用,但不會提交submodule內部代碼。
pull 帶有submodule的項目
- git clone http://gitlab-ce.youname.com/backend/wechatMetric
此時submodule starjazz爲一個沒有任何文件的空文件夾 執行如下拉取子模塊代碼
init 會把.gitsubmodule中的配置註冊到.git/config文件中 $ git submodule init 子模組 'starjazz' (http://gitlab-ce.youname.com/backend/starjazz) 未 對路徑 'starjazz' 註冊 # zhoudazhuang at zhoudazhuang-pc in ~/youname/submodule-test/wechat Metric on git:test o [22:58:32] $ git submodule update 正克隆到 'starjazz'... Username for 'http://gitlab-ce.youname.com': [email protected] Password for 'http://[email protected]@gitlab-ce.youname.com': remote: Counting objects: 385, done. remote: Compressing objects: 100% (331/331), done. remote: Total 385 (delta 78), reused 213 (delta 6) 接收對象中: 100% (385/385), 252.75 KiB | 0 bytes/s, 完成. 處理 delta 中: 100% (78/78), 完成. 檢查連接... 完成。 子模組路徑 'starjazz':檢出 '21d99fdd97b76bbb524c264aa619431143b6cf83 '
- cd starjazz && git status
mkdir: 已創建目錄 '/home/zhoudazhuang/.zsh_history/home/zhoudazhuang/
youname/submodule-test/wechatMetric/starjazz'
頭指針分離於 21d99fd
無文件要提交,乾淨的工作區
注意:git submodule update檢出項目的指定版本(HEAD),並不指向一個分支。頭指針和分支未綁定,是分離狀態。(並且每次執行submodule update都會從git倉庫覆蓋本地已變更的代碼),解決如下
- 強制將 master 分支指向當前頭指針的位置
# 強制將 master 分支指向當前頭指針的位置
$ git branch -f master HEAD
# 檢出 master 分支
$ git checkout master
即可正常進行代碼提交.
- 強制將 master 分支指向當前頭指針的位置
- git submodule add http://gitlab-ce.youname.com/backend/starjazz src/vendor/testsub/starjazz 可設置子模塊在當前項目的相對路徑.
- submodule有更新,在其他項目拉取代碼操作(同時也可以進入submodule項目進行處理)
foreach爲每一個遞歸循環更新recursive所有的submodule(這裏僅執行git submodule update是無效的,此update只在第一次拉去更新.git/config文件的子模塊有效)
git submodule foreach --recursive git pull origin master
- git clone –recursive … 可在拉取項目時把依賴的子模塊同時拉取下來.
- 更新.gitsubmodule中的remote url使用git submodule sync。
- 刪除submodule需要使用git rm –cached刪除倉庫文件,rm刪除本地文件,刪除.gitsubmodule文件在紅對應的子項目,刪除.git/config文件下的git配置文件。(注意:如果刪除文件後未執行git add操作,則重新加入git submodule會報錯’src/vendor/gitlab-ce.youname.com/backend/starjazz’ 已經存在於索引中,此時執行git add ,commit即可)
被忽略的.gitignore:
由一個文件引起的文件夾代碼未提交
.gitignore文件增加:
test1
bac
customerservice
對於customerservice,git倉庫中存在一個文件和文件夾(原目地爲忽略項目中生成的customerservice),最後此命名的文件和文件夾都被git忽略。
期間嘗試使用/customerservice,customerservice/,*/customerservice/*未果,最後參閱gitignore官方文檔,地址:https://git-scm.com/docs/gitignore,/customerservice,*/customerservice/*這兩種爲無效用法,/customerservice/這種也無效,,**/customerservice 此爲忽略文件和文件夾,**/customerservice/**,customerservice/ ,**/customerservice/這幾種效果一樣,也是同時忽略文件和文件夾。
小結及延伸:
1. 忽略某文件 *.exe,src/wechatmetric/microservice/customerservice/customerservice(從.git文件夾同目錄開始)
2. 同時忽略文件夾和文件 **/customerservice/**,customerservice/,**/customerservice , customerservice(不包含斜槓的命名,如3中customerservice,則按shell查找命令同時忽略)
4. 將匹配過的部分移出 !操作符 ,如 忽略aa文件夾,但排除其中bb:
aa/
!aa/bb/