包括三种配置文件:

  • .gitconfig
  • .gitattributes
  • .gitignore

.gitconfig

.gitignore是Git的忽略规则配置文件,Git 会在如下位置依次进行检查(优先级由高到低):

  1. 第一层是仓库级,在仓库目录下,文件为.git/config
  2. 第二层是用户级,在用户主目录下,文件为~/.gitconfig(主要修改的是用户级配置)
  3. 第三层是系统级,在安装目录下,安装时的选项会保存在这里

Git也可以使用符合XDG规范的配置文件:~/.config/git/config

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
[user]
name = xxx
email = xxx@xx.com
[init]
# 默认主分支名称
defaultBranch = main
[core]
# 默认编辑器
editor = vim
# 确保git正确显示中文信息
quotepath = false
# 在提交时将所有文本的换行符转换为LF,检出时不转换
autocrlf = input
# 检查文本的换行符,对于混合换行符的文件不允许提交
safecrlf = true
[i18n]
# 确保提交信息utf-8编码
commitEncoding = utf-8
[gui]
# 确保gui使用utf-8编码
encoding = utf-8

.gitattributes

.gitattributes是关于文件格式的配置,这个配置文件主要解决这些问题: 把哪些文件视作文本文件,哪些视作二进制文件,这涉及到 git 的差异比较和合并,以及换行符的处理。 更多细节参考官方文档

这里提供一个参考的.gitattributes 文件,含义见注释

1
2
3
4
5
6
7
8
9
10
11
12
13
# 对所有 .bat, .cmd 文件强制使用 CRLF
*.bat text eol=crlf
*.cmd text eol=crlf

# 对所有 .ps1 文件强制使用 CRLF
*.ps1 text eol=crlf
*.psd1 text eol=crlf
*.psm1 text eol=crlf

# 对所有 Visual Studio 解决方案和项目文件强制使用 CRLF
*.sln text eol=crlf
*.vcproj text eol=crlf
*.vcxproj text eol=crlf

.gitignore

.gitignore是Git关于排除文件的规则配置,Git 会在如下位置依次进行检查(优先级由高到低):

  1. 从命令行中读取可用的忽略规则
  2. 当前目录定义的.gitignore 规则
  3. 父级目录定义的.gitignore 规则,依次递推向上查找,直到仓库根目录
  4. $GIT_DIR/info/exclude文件中定义的规则
  5. core.excludesfile中定义的全局规则

下面整理一下基本的语法,更完整的语法规则参考官方文档

  1. 空行被直接忽略
  2. 以#开头的行视为注释,不要让注释出现在规则之后,以下语法可能有错误
1
*.log # 所有日志文件
  1. 其余每行表示一个 pattern,行尾的空格被忽略
  2. !意味着取反,即原本被匹配上的文件被忽略,加上!后这些文件则被包含进来,但是这里需要保证它的各级父目录没有被忽略,否则仍然无法包含
  3. pattern 严格区分大小写
  4. pattern 含有特殊字符例如#!时需要使用转义,例如\!\#
  5. pattern 视/为路径分隔符,是否含有/对匹配规则影响很大

在 pattern 不含有/时,执行如下的简单规则:(匹配当前位置和所有子文件夹的所有文件和文件夹)

  • 星号(*)匹配零个或多个任意字符,不包括/
  • 问号(?)只匹配一个任意字符,不包括/
  • [abc]匹配任何一个列在方括号中的字符(要么匹配一个 a,要么匹配一个 b,要么匹配一个 c);
  • 如果在方括号中使用短划线分隔两个字符,表示所有在这两个字符范围内的都可以匹配(比如 [0-9] 表示匹配所有 0 到 9 的数字);

在简单规则下,我们不需要考虑路径问题,只需要关注文件名和文件夹名自身的匹配,因为规则会遍历所有子文件夹。

简单规则示例:

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
# 忽略所有以 ~ 结尾的文件(通常是临时文件)
*~

# 忽略以 .tmp 结尾的临时文件
*.tmp

# 忽略日志文件
*.log

# 忽略备份文件
*.bak

# 忽略 Visual Studio 生成的文件和目录
*.sln
*.vcproj
*.vcxproj
*.vcxproj.filters

# 忽略所有 .html 和 .htm 文件
*.[html,htm]

# 忽略Release和release目录(兼顾开头大小写)
[Rr]elease/

# 忽略所有 .txt 文件
*.txt
# 特别保留 specific.txt 文件
!specific.txt

在 pattern 含有/时,匹配规则会考虑路径问题,更加复杂:

  • 如果在 pattern 的开头或者中部出现/,则只会匹配相对于.gitignore 文件所在位置的相对路径,例如/doc/testdoc/test效果一样
  • 如果在 pattern 的结尾出现/,则只会匹配到文件夹,不会匹配任何文件

使用**/结合还有如下的特殊规则,以满足复杂规则下的需求:

  • 例如**/foo可以匹配任何位置的 foo 文件或文件夹,效果和foo一样
  • 例如**/foo/bar可以匹配任意位置下的 bar 文件或文件夹,但是要求它的父文件夹为 foo
  • 例如/**匹配当前位置下的所有项,abc/**匹配当前位置的子文件夹 abc 下的所有项
  • 例如a/**/b可以匹配任意个中间目录,还可以没有中间目录,包括a/ba/x/ba/x/y/b
  • 在其它情形,即**不直接和/相邻时,效果同*

复杂规则示例

1
2
3
4
5
6
7
8
9
10
11
12
# 忽略build目录自身(也忽略了它的所有子项)
# build可能是当前目录下或者子目录中的build文件夹
build/

# 忽略doc目录下的所有.pdf文件,但不包括它的子目录下的.pdf文件
doc/*.pdf

# 忽略dox目录下的所有.pdf文件,以及它的子目录下的.pdf文件
doc/**/*.pdf

# 忽略所有 .log 文件,包括嵌套目录下的,效果与*.log一样
**/*.log

我们可以先忽略一般项,再添加特殊项

1
2
3
4
5
6
7
8
9
10
11
12
# 忽略所有 .txt 文件
*.txt

# 特别保留 specific.txt 文件
!specific.txt

# 忽略当前位置的build目录下的所有内容,
# 但是不忽略build目录自身,保留这个目录,使得其中的文件可以被特别保留
build/*

# 保留build目录下的指定文件
!build/config.xml

注意这里build/*build/效果是不一样的,前者才支持重新添加 build 中的某些文件。

对于当前目录下以点开头的文件(通常为配置脚本)我们希望默认包含,对于以点开头的文件夹则希望默认排除,可以使用如下设置

1
2
/.*/
!/.*