Joke's Blog World

GitHub 学习笔记

引言

很早之前就听说过和使用过 GitHub,那时仅仅是在 GitHub 上下载一些优秀的项目。最近有时间,正好可以比较全面的对 GitHub 做一个了解,学习如何熟练地使用 GitHub。


一、认识 GitHub

GitHub 是一个通过 Git 进行版本控制的软件源代码托管服务。通过 GitHub 提供的 Git 仓库的托管服务,可以让我们和其他人轻松地分享代码。GitHub 为开发者或团队主要提供了以下的功能:

  • Git仓库

一般情况下,我们可以免费建立任意个 GitHub 提供的 Git 仓库。如果需要建立只对特定任务或只对自己公开的私有仓库,则需要付费。

  • Organization

Organization 账户可以统一管理账户和权限。

  • Issue

Issue 功能,是将一个任务或问题分配给一个 Issue 进行追踪和管理的功能。在使用中,项目每一个功能更改或修改都对应一个 Issue,讨论或修正都以这个 Issue 为中心进行。只要查看 Issue,就能知道和这个更改相关的一切信息,并以此进行管理。

  • Wiki

Wiki 功能,可以让任何人都能随时对一篇文章进行更改并保存,这样,就可以允许多人协同来完成一篇文章。Wiki 功能常用在开发文档或手册的编写中。

  • Pull Request

开发者向 GitHub 的仓库推送更改或功能添加后,可以通过 Pull Request 功能向别人的仓库提出申请,请求对方合并。

通过这些功能,能够帮助开发者和团队高效率、高品质的进行代码编写。

GitHub 与 Git 的区别:
GitHub 和 Git 是完全不同的两个东西。在 Git 中,开发者将源代码存入名叫 “Git 仓库” 的资料库中并加以使用。而 GitHub 则是在网络上提供 Git 仓库的一项服务。也就是说,GitHub 上公开的软件源代码全都由 Git 进行管理。

二、Git 的安装

Git 仓库管理功能是 GitHub 的核心。而在使用 GitHub 之前,除了掌握 Git 相关知识,还需要在本地的设备上安装 Git 的环境。

2.1 版本管理

Git 属于分散型版本管理系统,是一款为版本管理而设计的软件。所谓 版本管理 ,就是管理更新的历史记录。通过版本控制提供的功能,我们可以在软件开发的过程中做到:记录一款软件添加或更改源代码的过程,回滚到特定阶段,恢复误删除的文件等。

2.2 版本管理系统的类型

版本管理系统分为 Subversion 这类 集中型 的与 Git 这类 分布型 的。

  • 集中型
    集中型,顾名思义,就是将仓库集中存放在服务器中,所以只存在一个仓库。集中型将所有数据集中存放在服务器当中,有便于管理的优点。但是一旦开发者所处的环境不能连接服务器或者服务器宕机,就无法获取最新的源代码,开发也就无法进行。特别的,当服务器故障导致数据消失,那么,开发者将无法在获得最新的源代码。

集中型

  • 分布型
    分步型,相比于集中型,拥有多个仓库。而且,由于本地的开发环境中就有仓库,所以开发者不必连接远程仓库就可以进行开发。以 Git 为代表的分布型,Github 将仓库 Fork 给了每一个用户。Fork 就是将某个特定仓库复制到自己的账户下。Fork 出的仓库与原仓库是两个不同的仓库,开发者可以随意编辑。

2.3 安装

2.3.1 Mac 与 Linux

在最近的 Mac 中都预装了 Git,而各个版本的 Linux 中都也以软件包(Package)的形式提供给用户,所以我们可以直接使用。

2.3.2 Windows

在 Windows 环境下,最简单快捷的方法是使用 msysGit 下载安装包。安装包下载完成以后,只要双击运行,按照向导一步步安装即可。在安装完成以后,我们需要对本地计算机里安装的 Git 进行如下的初始设置:

  • 设置姓名和邮箱
    1
    2
    git config --global user.name "your name"`
    git config --global user.email "your_email@example.com"

上述的命令,会在 “~/.gitconfig” 中以如下的形式输出设置文件:

1
2
3
[user]
name = your name
email = your_email@example.com

通过直接编辑上述设置文件,我们就可以更改姓名和邮箱信息。

  • 提高命令输出的可读性

将 color.ui 设置为 auto 可以让命令的输出拥有更高的可读性。

1
git config --global color.ui auto

运行上述命令之后,“~/.gitconfig” 配置文件中会增加下面一行:

1
2
[color]
ui = auto

而通过这样的设置,各种命令的输出就会变得更加容易分辨。

三、使用 Github 的前期准备

3.1 创建 Github 账户

访问 Github官网 即可免费创建账户。在创建账户时,Username 一栏中用英文和数字设置自己喜欢的 ID。创建账户成功以后,这个 ID 就是你的公开页面的 URL。

3.2 设置 SSH Key

Github 上连接已有仓库时的认证,是通过使用 SSH 的公开密钥认证的方式进行。

  • 生成 SSH Key

运行下面的命令就可以创建 SSH Key:

1
ssh-keygen -t rsa -C "your_email@example.com"

运行完上述命令之后,执行 clip < ~/.ssh/id_rsa.pub 或者到运行命令的过程中出现的路径里去打开文件并复制 SSH Key:

复制key的内容

  • 添加 SSH Key
    登录 Github,点击右上角的账户设定按钮,选择 Settings,在打开的页面中,点击左边的 SSH and GPG keys,然后选择右上角的 New SSH Key,将复制的 SSH Key 粘贴到 Key 输入框,Title 框中可以输入适当的密钥名称,完成后,点击下面的 Add SSH key 就成功了:

add_key

添加成功以后,我们需要测试一下,执行下面的命令:

1
ssh -T git@github.com

当出现如下结果,即为成功:

key_test

3.3 创建远程仓库

点击右上角工具栏里的 New repository 图标,选择 New repository,创建新的仓库:

New repository

接着,在 Repository name 栏中输入仓库的名称:

输入仓库名

点击 Create repositiry 按钮,完成仓库的创建。

3.4 创建版本库

版本库即 .git 目录。版本库你可以简单的理解成一个文件夹,在这个文件夹里的所有文件都可以被 Git 管理起来。包括每个文件的修改、删除,Git都能跟踪,以便任何时刻都可以追踪历史,或者在将来某个时刻可以“还原”。创建一个版本库非常简单,首先,选择一个合适的地方,比如自己计算机下的某个盘,创建一个空目录即可。这里,我们以一个现有的项目为例子,例如:

本地项目

我们在 G:\My Repository\NJUPT 目录下,运行以下命令 git init ,如下:

创建仓库

运行完上述命令后,瞬间 Gi t就把仓库建好了,而且告诉你是一个空的仓库(empty Git repository),同时,可以发现在 G:\My Repository\NJUPT 目录下多了一个 .git 的目录,这个目录是 Git 来跟踪管理版本库的。注意不要随意修改这个目录里面的文件,不然可能会破坏 Git 仓库。(如果你没有看到.git目录,那是因为这个目录默认是隐藏的)

接下来,我们将项目的包含的所有文件都添加到仓库:

添加项目到仓库

然后,把文件提交到仓库,双引号内是对此次提交的注释。如下所示:

确认项目提交到仓库

这样,本地仓库就建立好了。

总结:

  1. 初始化一个 Git 仓库,使用 git init 命令;
  2. 添加文件到Git仓库,分两步:
  • 第一步,使用以下命令添加文件:

    1
    2
    git add <file> //添加单个文件;也可反复多次使用,添加多个文件
    git add . //将当前目录下所有文件添加
  • 第二步,使用命令 git commit "xxx" ,提交文件。

3.5 将本地仓库的项目上传到 Github 远程仓库

3.5.1 关联本地仓库与远程仓库

首先,我们到 Github 上创建的仓库 Android_Bmob_Demo 复制仓库地址:

关联仓库

然后,执行命令:

1
git remote add origin https://github.com/JokeYang/Android_Bmob_Demo.git

3.5.2 上传本地项目到远程仓库

接着,执行命令 git push -u origin master 上传本地项目代码,如下所示:

上传本地项目

完成后,本地项目代码就已经推送到 Github 远程仓库,我们可以看到:

远程仓库

注意:git 是不能管理空的文件夹的,文件夹里必须有文件才能add,空的文件夹是不会被上传。

3.6 从远程库克隆

上面我们讲述的是如何在有了本地库的情况下,创建远程库并将本地库与远程库关联。假如我们打算从零开始开发一个项目,同时打算将项目托管到 Github,我们在要做的是先创建远程库,然后,从远程库克隆。克隆一个远程库使用 git clone 命令,命令后面是项目的地址,如下所示:

从远程库克隆

当我们多个人协作开发或者我们要下载别人的项目时,就可以使用 git clone 命令从远程仓库克隆一份代码。

四、开始使用 Git

4.1 基本操作

  • git init —— 初始化仓库
    要使用 Git 进行版本管理,必须先初始化仓库。我们只要建立一个目录,进入该目录,通过 git init 命令,即可让目录变成仓库。如果初始化成功,执行了 git init 命令的目录下就会生成 .git 目录。这个 .git 目录里存储着当前目录内容所需的仓库数据。在 Git 中,.git 目录的内容被称为 “附属于该仓库的工作树。

  • git status —— 查看仓库状态
    git status 命令用于显示 Git 仓库的状态。在工作的过程中,我们使用 git status 命令,可以时刻掌握仓库当前的状态。

  • git add —— 向暂存区中添加文件
    要想让文件成为 Git 仓库的管理对象,就需要用 git add 命令将其加入暂存区(Stage 或者 Index)中。暂存区是提交之前的一个临时区域。

  • git commit —— 保存仓库的历史记录
    git commit 命令可以将当前暂存区中的文件实际保存到仓库的历史记录中。通过这些记录,我们就可以在工作树中复原文件。git commit 命令一般的格式是:git commit -m "First commit", -m 参数后的 “First commit” 称作提交信息,是对这个提交的概述。

  • git log —— 查看提交日志
    git log 命令可以查看以往的仓库中提交的日志。包括可以查看什么人在什么时候进行了提交合并,以及操作前后有怎样的差别。如果只想让程序显示第一行简述信息,可以使用 git log --pretty=short 。而只要在 git log 命令后面加上目录名或者文件名,即 git log xxx ,便会只显示该目录下的日志或该文件相关的日志。想查看提交所带来的改动,可以使用 git log -p ,文件的前后差别就会显示在提交信息之后。

  • git diff —— 查看更改前后的差别
    git diff 命令可以查看工作树、暂存区、最新提i叫之间的差别。

4.2 分支管理

在进行多个并行作业时,我们会用到分支。在这类开发的过程中,往往同时存在多个最新的代码状态。不同的分支同时进行完全不同的作业,等当前分支的作业完成以后再与 master 分支合并。

说明:因为我们创建 Git 版本库时,Git 自动为我们创建了唯一一个 master 分支,所以,现在,git commit 就是往 master 分支上提交更改。

4.2.1 工作区和暂存区

  • 工作区
    工作区可以理解为存放代码的目录。

  • 版本库
    工作区有一个隐藏目录 .git,也就是Git的版本库。

  • 暂存区
    Git的版本库里存了很多东西,其中最重要的就是称为 Stage(或者叫 Index)的暂存区。如下所示:

git 提交原理

在前面,我们讲了我们把文件往 Git 版本库里添加的时候,是分两步执行的:

  • 第一步是用git add把文件添加进去,实际上就是把文件修改添加到暂存区;

  • 第二步是用git commit提交更改,实际上就是把暂存区的所有内容提交到当前分支。

也就是说,首先是将工作区文件修改一个个添加(add)到暂存区(stage)中,然后将暂存区中的内容一次性提交到分支中(master)。

4.2.2 分支的操作

  • git branch —— 显示分支一览表
    git branch 命令可以将分支名列表显示,同时可以确认当前所在的分支,当前分支前面会标一个 * 号。

  • git checkout -b —— 创建、切换分支
    如果想以当前的 master 分支为基础创建新的分支,我们需要用到 git checkout -b 命令。例如,执行 git checkout -b branch-home ,就会创建名为 branch-home 的分支。而当我们想切换到 master 分支时,执行 git checkout master 就可以。在当前分支下切换到上一分支:git checkout -

  • git merge —— 合并分支
    假设我们完成了 branch-home 的工作,想要将它合并到主分支 master,首先,我们切换到 master 分支:git checkout master ,然后执行命令:git merge branch-home;如果想在历史记录中明确记录下本次分支合并,我们需要创建合并并提交,因此,在合并时加上 –no-ff 参数:git merge --no-ff branch-home

  • git branch -d —— 删除分支
    当我年将某一分支与主分支合并之后,就可以放心地删除这一分支了,执行:git branch -d branch-home

  • git log –graph —— 以图表形式查看分支
    用 git log –graph 命令进行查看的话,能很清楚、直观的看到分支提交的内容已经被合并。

4.2.3 更改提交的操作

  • git reset —— 回溯历史版本
    在使用 Git 的过程中,我们如果注意在一定的阶段就保存一次文件,给文件一个“快照”,这个快照就是 Git 中的 commit。这样,当我们在开发的过程中,一旦我们把文件弄乱了或者误删了文件,就可以从最近的一个 commit 恢复。
    假设我们误删了文件。需要恢复到最近的一个版本,首先我们需要用 git log 命令来查看文件更改的历史记录。例如:

日志

需要注意的是:commit 后面的一大串数字:02a475d8330fea7…10dd3fb2f215b9d1882 是 commit id(版本号)。

这样,当我们想回退到某个版本时,只需要执行:git reset --hard HEAD 即可。其中,HEAD 表示当前版本,上一个版本就是 HEAD^,上上一个版本就是 HEAD^^,而 HEAD~100 表示往上100个版本。

  • git reset —— 回到未来版本
    当我们回退到某个版本后,我们后悔了,想重新回到之前的版本,应该怎么做呢? git log 命令只能查看以当前状态为终点的历史日志。而使用 git reflog 命令,就可以查看当前仓库的操作日志,这个命令记录了你的每一次命令。通过查看仓库的操作日志,找出要恢复的那个版本的 commit id ,就可以恢复到之前的状态。

4.2.4 操作远程仓库

前面 3.5.1 我们已经讲述过怎么添加远程仓库,即执行命令:git remote add origin https://github.com/JokeYang/Android_Bmob_Demo.git 以及 3.6 获取远程仓库,即执行命令:git clone

  • git push —— 推送至远程仓库
    当我们想将当前分支下本地仓库中的内容推送给远程仓库时,需要执行 git push命令。例如,执行 git push -u origin master ,当前分支的内容就会被推送到远程仓库 origin 的 master 分支。-u 参数可以在推送的同时,将 origin 仓库的 master 分支设置为本地仓库当前分支的 upstream (上游)。同时,添加了这个参数,将来运行 git pull 命令从远程仓库获取内容是,本地仓库的这个分支就可以直接从 origin 的 master 分支获取内容。

向远程仓库 push

  • git pull —— 获取最新的远程仓库分支
    除了 master 分支之外,远程仓库也可以创建其他分支。当我们想获取新的远程仓库分支时,就需要执行 git pull 命令,命令的作用是,取回远程主机某个分支的更新,再与本地的指定分支合并。

4.2.5 解决冲突

在真实的 Git运行环境中,往往涉及多个用户对版本仓库的协作,而每个用户都有一个完整的 Git 版本仓库副本,所以在把各自的操作结果推送到远程仓库的时候出现冲突的可能性就非常高。冲突的类型有:逻辑冲突内容冲突树冲突 三种。解决这三种类型冲突的方法可以看这篇 博客

4.3 其他操作

  • 撤销修改
    使用 git checkout -- file 可以撤销修改。例如,git checkout -- readme.txt 就是把 readme.txt 文件在工作区的修改全部撤销。

  • 删除文件
    使用 git rm 命令可以删除文件。如果你要从版本库中删除该文件,那就用命令 git rm 删掉,并且 git commit ,这样,文件就从版本库中被删除了。