git教程

本文最后更新于:2024年11月4日 晚上

git教程

密码

Github.token

Git 仓库配置用户和邮箱

特定仓库

要为一个特定的 Git 仓库配置用户和邮箱,可以使用以下命令:

  1. 进入你要配置的 Git 仓库目录

    1
    cd /path/to/your/repo
  2. 配置用户名称

    1
    git config user.name "Your Name"
  3. 配置用户邮箱

    1
    git config user.email "your.email@example.com"

可以通过查看 .git/config 文件来确认配置是否已被成功写入:

1
cat .git/config

在文件中,你应该能看到类似以下的配置:

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

全局配置用户和邮箱

这表示 user.nameuser.email 已经被成功配置到该仓库的本地配置文件中。

这些配置只会影响当前仓库,不会影响全局配置。如果你需要配置全局的用户和邮箱,可以使用 --global 选项:

1
2
git config --global user.name "Your Global Name"
git config --global user.email "your.global.email@example.com"

全局配置的信息会存储在用户主目录下的 Git 配置文件中,具体路径是:

  • ~/.gitconfig~/.config/git/config 文件:这个文件包含了你为所有 Git 仓库配置的全局设置。

当你使用 git config --global user.name "Your Name"git config --global user.email "your.email@example.com" 时,这些配置信息会被写入到 ~/.gitconfig 文件中。

你可以通过以下命令查看全局配置文件内容:

1
cat ~/.gitconfig

这个文件中的配置对系统中所有的 Git 仓库都有效。

命令

reset

在本地修改文件、或者删除文件后,如果想恢复这些文件内容为git仓库保存的版本,可以使用下面几个命令:

  • git checkout [--] <filepath>:可以恢复还没有执行 git add 的文件,但不能恢复已经执行过 git add 的文件
  • git reset [--] <filepath>:把文件从git的staged区域移除,即取消git add,再使用 git checkout 进行恢复
  • git reset --hard:恢复整个git仓库的文件内容为当前分支的最新版本

commit

1
git rebase -i HEAD~2

根据提示,把第二个“pick”改成“squash”,这样就可以把第二个commit合并到到第一个里。

git 修改最新commit的作者

使用 git commit --amend --author 修改提交的作者信息:

1
git commit --amend --author="新作者名 <新作者邮箱>"
1
git commit --amend --author="realwujing <realwujing@qq.com>"

git 修改指定commit的作者

要修改指定提交(commit)的作者信息,你可以使用以下步骤:

  1. 找到你要修改的提交的哈希值: 你可以通过 git log 来查看提交历史,并找到需要修改的提交哈希值。

  2. 使用交互式变基来修改提交

    执行以下命令以启动交互式变基,从而修改指定的提交:

    1
    git rebase -i <commit-hash>^

    其中 <commit-hash> 是你要修改的提交的哈希值。^ 表示从前一个提交开始。

  3. 标记为编辑(edit)

    在进入交互式变基编辑界面后,将要修改的提交前面的 pick 改为 edit,然后保存并退出。

  4. 修改作者信息

    运行以下命令修改提交的作者信息:

    1
    git commit --amend --author="New Author Name <new.email@example.com>"

    这会修改该提交的作者为你指定的新作者。

  5. 继续变基

    修改完作者信息后,继续执行变基过程:

    1
    git rebase --continue
  6. 强制推送到远程仓库(如果提交已推送到远程仓库):

    由于你修改了历史提交,你需要强制推送到远程仓库:

    1
    git push --force

注意:强制推送会覆盖远程仓库的历史,可能影响其他协作者,因此应谨慎使用。

查看文件每次提交的diff

1
git log -p kernel/sched/fair.c

git diff查看改动内容

  • 查看已暂存文件的改动:使用 git diff --cached <file>
  • 查看工作目录中未暂存文件的改动:使用 git diff <file>

<file> 替换为具体的文件路径。

查找某句代码在哪个提交中出现

1
2
3
4
5
6
7
8
git log -S 'cpumask_test_cpu(cpu, sched_domain_span(sd))' --oneline kernel/sched/fair.c | cat

8aeaffef8c6e sched/fair: Take the scheduling domain into account in select_idle_smt()
3e6efe87cd5c sched/fair: Remove redundant check in select_idle_smt()
3e8c6c9aac42 sched/fair: Remove task_util from effective utilization in feec()
c722f35b513f sched/fair: Bring back select_idle_smt(), but differently
6cd56ef1df39 sched/fair: Remove select_idle_smt()
df3cb4ea1fb6 sched/fair: Fix wrong cpu selecting from isolated domain

kernel/sched/fair.c参数可以去掉。

进一步使用git show 查看上述所有commit的具体内容:

1
git log -S 'cpumask_test_cpu(cpu, sched_domain_span(sd))' --oneline kernel/sched/fair.c | awk {'print $1'} | xargs git show > sched_domain_span.log

kernel/sched/fair.c参数可以去掉。

查找所有使用 @example.com 域名的提交作者

1
git log --pretty=format:"%an <%ae>" | grep "@example.com" | awk '!seen[$0]++'
  • awk '!seen[$0]++'awk 命令的这个用法可以用来去除重复行。seen[$0]++ 是一个关联数组,用于跟踪已经看到的行,如果行第一次出现,它会被打印;如果是重复的行,则不会被打印。

这个命令可以帮助确保每个作者的邮箱地址只显示一次。

查找所有使用 @example.com 域名的提交

git log 中显示简短的提交信息(--oneline 格式),同时包含作者的姓名、邮箱以及提交的 commit id

1
git log --pretty=format:"%h %s %an <%ae>" | grep "@example.com"
  • %h:简短的 commit id
  • %s:提交信息的简短描述(相当于 --oneline 格式的描述)。
  • %an:作者的名字。
  • %ae:作者的邮箱。

通过这种方式,你将获得包含简短 commit id、提交信息、作者姓名和邮箱的输出,并且只显示 @example.com 域名的提交记录。

查看某个补丁在内核哪些版本中有

在Linux kernel stable tree mirror中查找某个提交:

1
2
3
git remote -v
origin https://github.com/gregkh/linux.git (fetch)
origin https://github.com/gregkh/linux.git (push)
1
2
git log --oneline | grep "arm64: implement ftrace with regs"
3b23e4991fb6 arm64: implement ftrace with regs

在Linux kernel source tree中查找这个提交:

https://github.com/torvalds/linux/commit/3b23e4991fb6

3b23e4991fb6替换成要查找的commit:

3b23e4991fb6最早出现在linux-v5.5-rc1上
3b23e4991fb6最早出现在linux-v5.5-rc1上

statsh

rebase merge

pull

pull request

push

tag

要查看某个提交是否被标签包含,可以使用以下命令:

1
git tag --contains <commit-id>

示例

检查提交 3b23e4991fb6 是否被任何标签包含:

1
2
3
4
5
6
7
8
9
10
11
git tag --contains 3b23e4991fb6 | head -n10
v5.10
v5.10-rc1
v5.10-rc2
v5.10-rc3
v5.10-rc4
v5.10-rc5
v5.10-rc6
v5.10-rc7
v5.10.1
v5.10.10

branch

  1. 查看远程仓库的分支

    • 查看所有远程仓库的分支:

      1
      git branch -r
    • 查看已知的远程仓库及其分支:

      1
      git remote show <remote-name>
  2. 重命名远程仓库

    • 将远程仓库重命名:

      1
      git remote rename <旧名称> <新名称>

      例如,将 origin 重命名为 upstream

      1
      git remote rename origin upstream

      执行完这个命令后,你的远程仓库名称就会从 origin 改为 upstream

  3. 克隆特定远程分支

    • 获取特定远程分支而不影响其他分支:

      1
      git fetch <远程仓库名> <远程分支名>:refs/remotes/<远程仓库名>/<远程分支名>
    • 将该远程分支检出为本地分支:

      1
      git checkout -b <本地分支名> <远程仓库名>/<远程分支名>
  4. 查看当前分支对应的远程分支

    • 查看所有本地分支及其对应的远程分支:

      1
      git branch -vv
    • 查看当前分支对应的远程分支:

      1
      git rev-parse --abbrev-ref --symbolic-full-name @{u}
  5. 查看包含指定提交的本地分支

    • 要查看包含特定提交(如 3b23e4991fb6)的所有分支,可以使用以下 Git 命令:

      1
      git branch --contains 3b23e4991fb6

      git branch --contains <commit>:这个命令将列出所有包含指定提交的本地分支。

    • 如果你想查看所有远程和本地分支中包含该提交的分支,可以使用以下命令:

      1
      git branch -a --contains 3b23e4991fb6

      运行以上命令后,输出可能类似于:

      1
      2
      3
      4
      * develop
      feature-branch
      remotes/origin/master
      remotes/origin/develop

      在输出中,带有 * 的分支表示当前所在的分支,其他分支则表示包含指定提交的所有分支。如果输出为空,则表示没有分支包含该提交。

name-rev

使用 git name-rev 命令可以帮助开发者更方便地识别提交在版本历史中的位置,提供一个更人性化的提交引用方式。

用法示例

  1. 查找提交的符号名称

    1
    git name-rev 1b06a0

    输出示例

    1
    1b06a0 tags/release-0074~744

    解释

    • 该命令查找提交 1b06a0 的符号名称。
    • 输出显示 1b06a0 距离标签 release-0074 有 744 次提交。

submodule

.gitignore

.gitkeep

gerrit

Github Action

patch

将某个作者的所有提交打成序列号递增的patch

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
#!/bin/bash

# 定义补丁目录变量
PATCH_DIR="../patchs"

# 生成补丁文件到指定目录
git log --oneline --reverse --author="^realwujing" | awk '{print $1}' | xargs -I {} git format-patch -1 {} -o "$PATCH_DIR"

# 切换到补丁目录
cd "$PATCH_DIR" || { echo "Directory $PATCH_DIR does not exist"; exit 1; }

# 计数器初始化
i=1

# 遍历所有 .patch 文件,按照当前目录中的排序方式处理
for patch in $(ls -lt | tac | awk '{print $NF}' | grep '\.patch$'); do
# 使用 sed 删除原有的序号部分
base_name=$(echo "$patch" | sed 's/^[0-9]\{4\}-//')

# 使用 printf 格式化为四位数字,不足前面补零
new_name=$(printf "%04d-%s" $i "$base_name")

# 显示原始文件名和新的文件名
echo "Renaming $patch to $new_name"

# 重命名文件
mv "$patch" "$new_name"

# 增加计数器
i=$((i + 1))
done
  1. 定义补丁目录变量PATCH_DIR="../patchs" 将目标目录存储在一个变量中。

  2. 生成补丁文件到指定目录git format-patch 命令将补丁文件生成到 "$PATCH_DIR" 目录。

  3. 切换到补丁目录cd "$PATCH_DIR" 进入指定目录。如果目录不存在,则输出错误信息并退出。

  4. 遍历并重命名文件

    • 使用 sed 删除原有的序号部分,得到文件的基本名称。
    • 使用 printf 格式化新的文件名,包括递增的序号。
    • 增加对比输出:使用 echo 显示每个文件的原始名称和新的名称。
    • 使用 mv 重命名文件。
  5. 计数器递增:每处理一个文件,计数器 i 递增。

这个脚本在重命名过程中会输出每个文件的原始名称和新的名称,便于跟踪文件的变化。

使用git am,可以将上述一系列补丁应用到某个分支上,如果存在冲突,则会报错并生成reject文件,需要手动处理冲突:

1
git am ../patchs/*.patch --reject

send-email

.gitconfig中的配置如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
[user]
email = realwujing@qq.com
name = wujing
[url "git@github.com:"]
insteadOf = https://github.com/
[commit]
template = ~/.gitcommit_template
[sendemail]
smtpServer = smtp.qq.com
smtpServerPort = 587
smtpEncryption = tls
smtpUser = realwujing@qq.com
smtpPass = kpdkskfgpbaxsrnwbifi

测试连接和认证:

1
git send-email -v --to="realwujing@qq.com" HEAD^
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
/var/folders/hh/0wpdzj8s79scygrdntrwy32h0000gn/T/xctMCK9Q3r/v-to-realwujing-qq.com-0001-git-send-email-and-Signed-off.patch
The following files are 8bit, but do not declare a Content-Transfer-Encoding.
/var/folders/hh/0wpdzj8s79scygrdntrwy32h0000gn/T/xctMCK9Q3r/v-to-realwujing-qq.com-0001-git-send-email-and-Signed-off.patch
Which 8bit encoding should I declare [UTF-8]?
To whom should the emails be sent (if anyone)? realwujing@qq.com
Message-ID to be used as In-Reply-To for the first email (if any)?
(mbox) Adding cc: wujing <realwujing@qq.com> from line 'From: wujing <realwujing@qq.com>'
(body) Adding cc: wujing <realwujing@qq.com> from line 'Signed-off-by: wujing <realwujing@qq.com>'

From: wujing <realwujing@qq.com>
To: realwujing@qq.com
Subject: [PATCH v--to=realwujing@qq.com] git: send-email and Signed-off-by
Date: Sat, 6 Jul 2024 19:19:17 +0800
Message-ID: <20240706111927.56825-1-realwujing@qq.com>
X-Mailer: git-send-email 2.45.2
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

The Cc list above has been expanded by additional
addresses found in the patch commit message. By default
send-email prompts before sending whenever this occurs.
This behavior is controlled by the sendemail.confirm
configuration setting.

For additional information, run 'git send-email --help'.
To retain the current behavior, but squelch this message,
run 'git config --global sendemail.confirm auto'.

Send this email? ([y]es|[n]o|[e]dit|[q]uit|[a]ll): y
OK. Log says:
Server: smtp.qq.com
MAIL FROM:<realwujing@qq.com>
RCPT TO:<realwujing@qq.com>
From: wujing <realwujing@qq.com>
To: realwujing@qq.com
Subject: [PATCH v--to=realwujing@qq.com] git: send-email and Signed-off-by
Date: Sat, 6 Jul 2024 19:19:17 +0800
Message-ID: <20240706111927.56825-1-realwujing@qq.com>
X-Mailer: git-send-email 2.45.2
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Result: 250

git教程
https://realwujing.github.io/git/git教程/
作者
Wu Jing
发布于
2023年4月21日
许可协议