本文章為拋磚引玉,可能有概念或理解錯誤,懇請讀者斧正!
要做畢業設計了,想把畢業設計作為一個項目好好做一下,在公司實習了半年也對項目開發的流程有了一定的了解,那么一個正式的開發項目通常都會使用一種版本控制系統,有了版本控制系統一方面可以記錄每次對代碼編寫和修改的操作,另一方面也可以很方便的對代碼進行備份,如果有機會發展成開源項目的話,也可以直接變成公共版本庫,然后成立開源社區,廣受業內關注,最后達到技術的巔峰(想想還有些小激動呢~)。
咳咳~常見的版本控制基本上有SVN、CVS(傳說是SVN的前身)、Git。在實習單位使用CVS使用到吐,功能很局限,而且經常莫名其妙地或因為一個空行爆出代碼沖突;至於SVN嘛——哼哼,每一個文件夾下有個配置文件,不小心動了配置文件就可能會發生錯誤,而且還要現安裝和配置,個人技拙,之前在學校里配置SVN的服務端配置了好久都沒成功;Git的分布式特性雖然我個人開發的時候用不到,但是Git既小巧、又完善,而且在大多Linux發行版下是預裝的,所以我選擇用Git。
據說如果以前沒有用到任何版本控制系統的人去學Git是比較容易的,反而如果用過其他版本控制系統就不是很容易理解Git的思想了(我恰恰就是這種情況)。因為Git與其他的如CVS在思想上是完全不同的。說起不同,哼哼,也沒什么,就是分支(Branch)機制,你會發現在你使用的過程中充斥着各種各樣的分支,比如服務器上一個版本庫中就有穩定分支和Nightly分支(程序員多是夜喵子?),Clone下來的版本庫一般也有服務器上的所有分支,自己改寫代碼要新建分支,改完代碼要清理、切換和合並分支,嘗試不同思路還要多建幾個分支,改代碼改到吐果斷刪除分支……囧
好吧,再吐槽呆毛就啵兒起了,我們言歸正傳。大體需求是醬紫的:
1.因為是我的畢業設計,在被指導老師虐完之前不希望其他人各種拉來、推去、吐槽和賣萌,所以我希望我的版本控制系統是私有的。
2.有人說在新建的分支上編寫和修改代碼有助於使主干(master)的提交記錄更加“干凈整潔(clean history)”,所以我要在本地創建至少一個工作分支。
3.前段時間內心深處和被窩里都充斥着空虛寂寞冷,終於按捺不住燃起了熊熊烈火—→_→—在DigitaloCean上買了個VPS,所以我希望可以在服務器上有一個遠程版本庫作為備份。
那么根據我這兩天的學(zhē)習(teng),大體了解了Git的使用流程,做出結構設計如下(莫噴,多提建設性意見):
下面是我的搭建過程:
#服務器上: #創建一個文件夾,用於存放項目 mkdir /home/libook/Git/myProject #進入這個文件加 cd /home/libook/Git/myProject #創建一個空的版本庫,這種版本庫單純作為版本的儲存,不能用於修改代碼(實際上根本看不到代碼),但是能被clone或pull成可以進行開發的源代碼版本庫 git init --bare
#本地上: #進入你的代碼目錄,假設情況是這樣 /home/libook/Documents/theProject/myProject/各種代碼和目錄 cd /home/libook/Documents/theProject #初始化Git,下面這個語句會在theProject下生成一個.git目錄 git init #創建一個篩選規則,用來忽略一些我們不想加入到版本庫中的文件或目錄,具體篩選規則請自行搜索 vim .gitignore #將源代碼和目錄結構添加到Git中,還有別忘了.gitignore文件 git add ./myProject git add ./.gitignore #提交剛剛做的操作 git commit -m "寫點說明描述神馬的" #[可選]看一下版本庫狀態,是否有問題 git show #[可選]看一下剛剛提交的記錄 git log #添加遠程服務器上的版本庫;最后一個斜杠“/”千萬不能丟!!;指定一個別名gitserv,以后就可以用這個別名來直接進行遠程操作了;另外我使用的是SSH協議,也可以用其他的協議,自己搜索啦2333~ git remote add gitserv ssh://用戶名@IP/home/libook/Git/myProject/ #將本地版本庫提交到服務器上去,由於我們一般只提交主干,所以指定分支的地方就寫master git push gitserv master
#服務器上
#[可選]看一下版本庫狀態,是否有問題
git show
#[可選]看一下剛剛提交的記錄是否Push上來了
git log
搭建完成,那么平時使用的時候怎么用呢?
大體使用流程是這樣的:
#本地上: #進入版本庫目錄 cd /home/libook/Documents/theProject #[可選]切換到主干,一般默認就是在主干上 git checkout master
#本地上: #[可選]這塊是與服務器同步一下,由於目前是我自己用,所以這步驟可以忽略: #把遠程服務器上的主干(master)同步到本地的臨時分支(如tmp) git fetch gitserv master:tmp #看看是否有別人改過代碼 git diff tmp #如果有人改過的話在同步之后需要把tmp合並到主干上 git merge tmp
#本地上
#[可選]上面這塊基本上等價於
git pull gitserv master
#本地上 #創建分支 git branch 分支名 #切換到分支 git checkout 分支名 #修改代碼 ###################### #[可選]每修改完一個文件,保存后需要更新這個文件的快照 git add 文件名 #提交代碼(這個步驟可能會執行多次) git commit -m "寫點什么描述" #如果之前修改的文件沒有用git add進行更新,那么可以使用下面的語句自動更新、提交(這個不會更新沒有git add過的文件) git commit -a -m "寫點什么描述"
#本地上 #將工作分支上的修改記錄合並到主干上 #切換到主干 git checkout master #方法1:將分支上所有的提交記錄合並到主干,在主干上保留分支合並的記錄 git merge 分支名 #方法2:將分支上所有的提交記錄壓縮成一條提交記錄合並到主干,在主干上保留此分支合並的記錄 git merge --squash 分支名 #方法3:衍合,將分支上所有的提交記錄作為一個個補丁合並到主干,主干上沒有此分支合並的記錄,只有提交記錄 git rebase 分支名 #以上合並方式出現沖突后查看沖突 git status #衍合分支解決沖突后繼續衍合 git rebase --continue #衍合分支出現沖突后撤銷衍合 git rebase --abort
#本地上
#刪除分支
git branch -d 分支名
#本地上
#把本地的主干推送提交到遠程版本庫上
git push gitserv master
需要說明的是網上好多人都在呼吁與遠程版本庫同步的時候盡量不用pull,盡量用fetch,因為那樣可以看看服務器上的代碼被別人改成了啥尿性,然后再取舍合並。還有,其實fetch有豐富的選擇分支進行同步的功能,還有刪除分支的功能,具體這里就不細談了。
關於merge和rebase,我個人也不是特別理解,不過我知道rebase一般用在自己私下寫的分支。假設自己在主干分了一個work分支,這個work分支又分了3個分支,且沒有向公共版本庫推送過,那我完全可以在寫寫改改后用rebase把這三個分支合並到我的work分支上;這個work分支會很干凈,只有一條線,沒有之前的3個分支的歷史記錄,但是之前3個分支的提交記錄都保留在了work的提交記錄里;就好像從來沒有這3個分支,所有提交記錄都是我這個work分支上完成的;然后我們就可以用merge把這個work分支合並到主干上。再設想一下,如果我們把其他人的分支同步了下來,然后修改了一下,再rebase到主干上,那么這個分支在主干上就不存在了,如果別人已經正在用這個分支開發的話,那么他在經歷了蛋疼地調式和編碼之后就會呵(mā)呵(bī)地發現自己的分支不存在了,可能還要重新做一遍這個分支(此乃居家旅行惡作劇找噴找打找死必備~~)。
另外,git所有功能的man手冊都挺詳細的,特別是rebase還有圖示,只是沒過CET-4的鄙人看着有點麻煩。當然,M$黨就沒這福分了。。。
本文章系受著作權法保護,未經著作人同意,不得盜用;使用或引用本文章內容請注明作者名、原地址:書中葉http://www.cnblogs.com/libook