简体中文 ▾ 主题 ▾ 最新版本 ▾ giteveryday 最后更新于 2.43.0

名称

giteveryday - 日常使用 Git 的一组最小实用命令集

概要

大约 20 个命令的日常 Git 指南

描述

为了描述日常 Git 的少量有用命令,Git 用户大致可以分为四类。

独立开发者(单机)

单机独立开发者不与其他人交换补丁,仅在单个版本库中独自工作,使用以下命令。

示例

使用压缩包作为新版本库的起点。
$ tar zxf frotz.tar.gz
$ cd frotz
$ git init
$ git add . (1)
$ git commit -m "import of frotz source tree."
$ git tag v2.43 (2)
  1. 添加当前目录下的所有内容。

  2. 创建一个轻量级的、未注释的标签。

创建主题分支并进行开发。
$ git switch -c alsa-audio (1)
$ edit/compile/test
$ git restore curses/ux_audio_oss.c (2)
$ git add curses/ux_audio_alsa.c (3)
$ edit/compile/test
$ git diff HEAD (4)
$ git commit -a -s (5)
$ edit/compile/test
$ git diff HEAD^ (6)
$ git commit -a --amend (7)
$ git switch master (8)
$ git merge alsa-audio (9)
$ git log --since='3 days ago' (10)
$ git log v2.43.. curses/ (11)
  1. 创建一个新的主题分支。

  2. 还原你在 curses/ux_audio_oss.c 中搞砸的修改。

  3. 如果你添加了新文件,需要告知 Git;如果稍后执行 git commit -a,则会自动捕获删除和修改。

  4. 查看你正在提交的更改。

  5. 提交所有经过测试的内容,并附上你的签名(sign-off)。

  6. 查看你所有的更改,包括上一次提交。

  7. 修正上一次提交,添加所有新更改,并沿用原始提交说明。

  8. 切换到 master 分支。

  9. 将主题分支合并到你的 master 分支中。

  10. 查看提交日志;可以结合其他限制输出的形式,包括 -10(显示最近 10 条提交)、--until=2005-12-10 等。

  11. 仅查看自 v2.43 标签以来,涉及 curses/ 目录的更改。

个人开发者(参与者)

作为团队项目参与者的开发者需要学习如何与他人沟通,除了独立开发者所需的命令外,还需使用这些命令。

示例

从上游克隆并开展工作。将更改反馈给上游。
$ git clone git://git.kernel.org/pub/scm/.../torvalds/linux-2.6 my2.6
$ cd my2.6
$ git switch -c mine master (1)
$ edit/compile/test; git commit -a -s (2)
$ git format-patch master (3)
$ git send-email --to="person <email@example.com>" 00*.patch (4)
$ git switch master (5)
$ git pull (6)
$ git log -p ORIG_HEAD.. arch/i386 include/asm-i386 (7)
$ git ls-remote --heads http://git.kernel.org/.../jgarzik/libata-dev.git (8)
$ git pull git://git.kernel.org/pub/.../jgarzik/libata-dev.git ALL (9)
$ git reset --hard ORIG_HEAD (10)
$ git gc (11)
  1. 从 master 签出一个新分支 mine

  2. 根据需要重复操作。

  3. 从你的分支中提取相对于 master 的补丁,

  4. 并发送邮件。

  5. 回到 master,准备查看新内容。

  6. git pull 默认从 origin 获取并合并到当前分支。

  7. 拉取后立即查看自上次检查以来上游所做的更改,仅限我们感兴趣的区域。

  8. 检查外部版本库中的分支名称(如果未知)。

  9. 从特定版本库的特定分支 ALL 获取并合并。

  10. 撤销拉取。

  11. 垃圾回收撤销拉取后留下的对象。

推送到另一个版本库。
satellite$ git clone mothership:frotz frotz (1)
satellite$ cd frotz
satellite$ git config --get-regexp '^(remote|branch)\.' (2)
remote.origin.url mothership:frotz
remote.origin.fetch refs/heads/*:refs/remotes/origin/*
branch.master.remote origin
branch.master.merge refs/heads/master
satellite$ git config remote.origin.push \
	   +refs/heads/*:refs/remotes/satellite/* (3)
satellite$ edit/compile/test/commit
satellite$ git push origin (4)

mothership$ cd frotz
mothership$ git switch master
mothership$ git merge satellite/master (5)
  1. 主节点(mothership)机器在你的主目录下有一个 frotz 版本库;从中克隆以在卫星(satellite)机器上启动版本库。

  2. clone 默认会设置这些配置变量。它安排 git pull 获取主节点机器的分支并存储到本地的 remotes/origin/* 远程跟踪分支中。

  3. 安排 git push 将所有本地分支推送到主节点机器对应的分支。

  4. push 将把我们所有的工作存放在主节点机器上的 remotes/satellite/* 远程跟踪分支中。你可以将其作为备份手段。同样地,你可以假装主节点从你这里“获取”(在只有单向访问权限时很有用)。

  5. 在主节点机器上,将卫星机上完成的工作合并到 master 分支。

从特定标签切出分支。
$ git switch -c private2.6.14 v2.6.14 (1)
$ edit/compile/test; git commit -a
$ git checkout master
$ git cherry-pick v2.6.14..private2.6.14 (2)
  1. 基于一个广为人知(但稍微落后)的标签创建一个私有分支。

  2. private2.6.14 分支中的所有更改转发移植到 master 分支,而不进行正式的“合并”。或者详细写法:
    git format-patch -k -m --stdout v2.6.14..private2.6.14 | git am -3 -k

另一种参与者提交机制是使用 git request-pull 或 pull-request 机制(例如在 GitHub (www.github.com) 上使用的)来通知上游你的贡献。

集成者

集成者在团队项目中扮演相当核心的角色,负责接收他人的更改、审阅并集成它们,最后发布结果供他人使用。除了参与者所需的命令外,集成者还需要使用这些命令。

本章节也适用于那些在 GitHub (www.github.com) 上响应 git request-pull 或 pull-request,将他人工作集成到自己历史记录中的人。版本库的子区域负责人(lieutenant)既是参与者也是集成者。

示例

集成者典型的 Git 工作日。
$ git status (1)
$ git branch --no-merged master (2)
$ mailx (3)
& s 2 3 4 5 ./+to-apply
& s 7 8 ./+hold-linus
& q
$ git switch -c topic/one master
$ git am -3 -i -s ./+to-apply (4)
$ compile/test
$ git switch -c hold/linus && git am -3 -i -s ./+hold-linus (5)
$ git switch topic/one && git rebase master (6)
$ git switch -C seen next (7)
$ git merge topic/one topic/two && git merge hold/linus (8)
$ git switch maint
$ git cherry-pick master~4 (9)
$ compile/test
$ git tag -s -m "GIT 0.99.9x" v0.99.9x (10)
$ git fetch ko && for branch in master maint next seen (11)
    do
	git show-branch ko/$branch $branch (12)
    done
$ git push --follow-tags ko (13)
  1. 查看你是否正处于某项工作的中间状态。

  2. 查看哪些分支尚未合并到 master。同样适用于其他集成分支,如 maintnextseen

  3. 阅读邮件,保存可用的,以及那些尚未完全准备好的(也可以使用其他邮件阅读器)。

  4. 交互式地应用它们,并附上你的签名。

  5. 根据需要创建主题分支并应用,同样附上签名。

  6. 变基尚未合并到 master 或尚未作为稳定分支一部分公开的内部主题分支。

  7. 每次都从 next 重新启动 seen 分支。

  8. 并打包仍在酝酿中的主题分支。

  9. 回传(backport)一个关键修复。

  10. 创建一个带签名的标签。

  11. 确保 master 没有意外回退到已经推送出去的范围之外。

  12. git show-branch 的输出中,master 应该包含 ko/master 的所有内容,next 应该包含 ko/next 的所有内容,依此类推。

  13. 推送前沿版本,以及指向已推送历史的新标签。

在这个例子中,ko 简写指向 kernel.org 上 Git 维护者的版本库,如下所示:

(in .git/config)
[remote "ko"]
	url = kernel.org:/pub/scm/git/git.git
	fetch = refs/heads/*:refs/remotes/ko/*
	push = refs/heads/master
	push = refs/heads/next
	push = +refs/heads/seen
	push = refs/heads/maint

版本库管理

版本库管理员使用以下工具为开发者设置和维护版本库访问权限。

更新钩子 (update hook) 教程 有一个管理共享中央版本库的很好示例。

此外,还有许多其他广泛部署的托管、浏览和评审解决方案,例如:

  • gitolite, gerrit code review, cgit 等。

示例

假设 /etc/services 中有以下内容:
$ grep 9418 /etc/services
git		9418/tcp		# Git Version Control System
运行 git-daemon 以通过 inetd 提供 /pub/scm 服务。
$ grep git /etc/inetd.conf
git	stream	tcp	nowait	nobody \
  /usr/bin/git-daemon git-daemon --inetd --export-all /pub/scm

实际配置行应在同一行中。

运行 git-daemon 以通过 xinetd 提供 /pub/scm 服务。
$ cat /etc/xinetd.d/git-daemon
# default: off
# description: The Git server offers access to Git repositories
service git
{
	disable = no
	type            = UNLISTED
	port            = 9418
	socket_type     = stream
	wait            = no
	user            = nobody
	server          = /usr/bin/git-daemon
	server_args     = --inetd --export-all --base-path=/pub/scm
	log_on_failure  += USERID
}

检查你的 xinetd(8) 文档和设置,这是来自 Fedora 系统的示例。其他系统可能有所不同。

通过 git-over-ssh 仅给予开发者推送/拉取权限。

例如使用:$ git push/pull ssh://host.xz/pub/scm/project

$ grep git /etc/passwd (1)
alice:x:1000:1000::/home/alice:/usr/bin/git-shell
bob:x:1001:1001::/home/bob:/usr/bin/git-shell
cindy:x:1002:1002::/home/cindy:/usr/bin/git-shell
david:x:1003:1003::/home/david:/usr/bin/git-shell
$ grep git /etc/shells (2)
/usr/bin/git-shell
  1. 登录 shell 设置为 /usr/bin/git-shell,除了 git pushgit pull 之外不允许任何操作。用户需要该机器的 ssh 访问权限。

  2. 在许多发行版中,/etc/shells 需要列出用作登录 shell 的程序。

CVS 风格的共享版本库。
$ grep git /etc/group (1)
git:x:9418:alice,bob,cindy,david
$ cd /home/devo.git
$ ls -l (2)
  lrwxrwxrwx   1 david git    17 Dec  4 22:40 HEAD -> refs/heads/master
  drwxrwsr-x   2 david git  4096 Dec  4 22:40 branches
  -rw-rw-r--   1 david git    84 Dec  4 22:40 config
  -rw-rw-r--   1 david git    58 Dec  4 22:40 description
  drwxrwsr-x   2 david git  4096 Dec  4 22:40 hooks
  -rw-rw-r--   1 david git 37504 Dec  4 22:40 index
  drwxrwsr-x   2 david git  4096 Dec  4 22:40 info
  drwxrwsr-x   4 david git  4096 Dec  4 22:40 objects
  drwxrwsr-x   4 david git  4096 Nov  7 14:58 refs
  drwxrwsr-x   2 david git  4096 Dec  4 22:40 remotes
$ ls -l hooks/update (3)
  -r-xr-xr-x   1 david git  3536 Dec  4 22:40 update
$ cat info/allowed-users (4)
refs/heads/master	alice\|cindy
refs/heads/doc-update	bob
refs/tags/v[0-9]*	david
  1. 将开发者放入同一个 git 组。

  2. 并使共享版本库对该组可写。

  3. 使用 Documentation/howto/ 中由 Carl 提供的 update-hook 示例进行分支策略控制。

  4. alice 和 cindy 可以推送到 master,只有 bob 可以推送到 doc-update。david 是发布经理,是唯一可以创建并推送版本标签的人。

GIT

Git[1] 套件的一部分