文件超 100M 推送至 Github 解决方案
文件超 100M 推送至 Github 解决方案
-
问题原因:在使用
Git
将本地仓库代码推送到远端仓库时,发现本地仓库提交的commit
历史存在超100M文件(如"*.obj"或"*.stl")
,以致无法推送到Github
远端仓库。 -
控制台错误日志输出如下:
$ git push Enumerating objects: 13, done. Counting objects: 100% (13/13), done. Delta compression using up to 16 threads Compressing objects: 100% (8/8), done. Writing objects: 100% (8/8), 108.80 MiB | 610.00 KiB/s, done. Total 8 (delta 4), reused 0 (delta 0), pack-reused 0 (from 0) remote: Resolving deltas: 100% (4/4), completed with 4 local objects. remote: error: Trace: 4f7a3665ea0158c19bd462176d3879408954d9134fa690b6c38fb6a11c5325d1 remote: error: See https://gh.io/lfs for more information. remote: error: File BABYLONJS/7、上色/3066-vase-3d-model/vaze2.STL is 165.23 MB; this exceeds GitHub's file size limit of 100.00 MB remote: error: File BABYLONJS/7、上色/3066-vase-3d-model/vaze2.OBJ is 157.28 MB; this exceeds GitHub's file size limit of 100.00 MB remote: error: GH001: Large files detected. You may want to try Git Large File Storage - https://git-lfs.github.com. To github.com:vinca/my-project.git ! [remote rejected] master -> master (pre-receive hook declined) error: failed to push some refs to 'github.com:vinca/my-project.git' $
解决办法
1. 安装Git LFS
使用Git LFS
管理大文件,可以将大文件存储在Git LFS服务器
上,而不是将它们存储在Git仓库
中。这样可以避免将大文件存储在Git仓库
中,从而减少Git仓库的大小。
-
Git Large File Storage
Git 大文件存储 (LFS) 将音频样本、视频、数据集和图形等大文件替换为 Git 中的文本指针,同时将文件内容存储在 GitHub.com 或 GitHub Enterprise 等远程服务器上。
- 下载地址
下载并安装完成后(安装的时候它会提示你的Git安装所在目录,这里我是将Git LFS安装在和Git同一父级目录下,方便管理),通过运行以下命令为你的账户用户设置Git LFS
;
$ git lfs install
注释:若是在当前Git存储库(当前项目)下运行,可以到该Git存储库根目录下的.git文件夹
(看不到,请勾选,查看隐藏文件)里新增的lfs文件夹
。
2. 跟踪大文件
在要使用Git LFS
的Git存储库
中(也就是你的项目),选择你希望Git LFS
管理的文件类型(或者直接编辑.gitattributes
文件)。
你可以随时配置其他文件拓展名,如.jpg
、.png
、.mp4
、.psd
等。
在这里,我们将跟踪所有的.STL
和.OBJ
文件。(无大小写严格要求)
$ git lfs track "*.stl"
Tracking "*.stl"
$ git lfs track "*.obj"
Tracking "*.obj"
此时,该Git存储库(你的项目)根目录会多出一个.gitattributes
文件,内容如下:
*.stl filter=lfs diff=lfs merge=lfs -text
*.obj filter=lfs diff=lfs merge=lfs -text
提交并推送.gitattributes
文件,确保现在就要跟踪这些大文件:
git add .gitattributes
git commit -m "🧪 test: 添加.gitattributes文件"
git push origin master
添加所有大文件:
git add --all
git commit -m "🧪 test: 尝试添加大文件"
git push origin master
执行成功,日志如下:
$ git add --all
$ git commit -m "🧪 test: 尝试添加大文件"
[master 70b6e32] 🧪 test: 尝试添加大文件
2 files changed, 6 insertions(+)
create mode 100644 "BABYLONJS/7\343\200\201\344\270\212\350\211\262/3066-vase-3d-model/vaze2.OBJ"
create mode 100644 "BABYLONJS/7\343\200\201\344\270\212\350\211\262/3066-vase-3d-model/vaze2.STL"
$ git push origin master
Uploading LFS objects: 100% (2/2), 338 MB | 0 B/s, done.
Enumerating objects: 13, done.
Counting objects: 100% (13/13), done.
Delta compression using up to 16 threads
Compressing objects: 100% (8/8), done.
Writing objects: 100% (8/8), 901 bytes | 180.00 KiB/s, done.
Total 8 (delta 4), reused 0 (delta 0), pack-reused 0 (from 0)
remote: Resolving deltas: 100% (4/4), completed with 4 local objects.
To github.com:vinca/my-project.git
5c1eb4c..70b6e32 master -> master
$
操作总结
验证 Git Large File Storage
所说,大文件替换为 Git 中的文本指针。如下:
可以在 Git Graph 提交记录中点击对应大文件,打开内容如下:
version https://git-lfs.github.com/spec/v1
oid sha256:7ea7772336b108332f3202efa60d5cc0029a8ad12f2816284dc5dd772fbb7c70
size 164922655
1. version
- 这个字段指定了当前 Git LFS 元数据文件所遵循的规范版本。在 Git LFS 中,不同版本的规范在元数据的格式、存储方式或处理逻辑上有所不同。通过指定版本,Git LFS 客户端和服务器可以确保按照统一的规则来处理大文件的元数据。
- 关键字
version
:用于标识这是一个版本信息字段。后面跟着的https://git-lfs.github.com/spec/v1
是一个指向具体规范文档的 URL,这里明确表示当前使用的是 Git LFS 规范的版本 1。这意味着在后续处理这个大文件的元数据时,相关的操作(如上传、下载、校验等)都会依据这个版本的规范来执行。
2. oid
- 这个字段表示大文件的对象标识符(Object ID,简称 OID)。OID 是文件内容的唯一哈希值,用于在 Git LFS 系统中唯一标识一个特定的文件内容。
- 说明:
oid
是关键字,用于标识这是一个对象标识符字段。sha256
是哈希算法的名称,即 SHA-256 算法。SHA-256 是一种广泛使用的加密哈希函数,它可以将任意长度的输入数据转换为一个固定长度(256 位,即 64 个十六进制字符)的哈希值。这个哈希值具有唯一性,只要文件内容发生任何微小的变化,其 SHA-256 哈希值就会完全不同。7ea7772336b108332f3202efa60d5cc0029a8ad12f2816284dc5dd772fbb7c70
就是使用 SHA-256 算法对该大文件的内容进行哈希计算后得到的具体哈希值。Git LFS 使用这个 OID 来确定文件的唯一性,在文件上传、下载和存储过程中,通过比较 OID 来判断文件是否已经存在或是否需要更新。
3. size
- 含义:这个字段表示大文件的大小,单位是字节(Byte)。它记录了原始大文件在磁盘上占用的存储空间大小。
- 详细解释:
size
是关键字,用于标识这是一个文件大小字段。164922655
是具体的文件大小数值,即该大文件的实际大小为 164922655 字节。在 Git LFS 中,记录文件大小有助于在文件传输过程中进行进度监控、资源分配和完整性检查。例如,在下载文件时,可以根据文件大小和已下载的字节数来计算下载进度;在上传文件时,可以根据文件大小来合理分配网络带宽和服务器存储空间。
综上!文本指针的代码,通过版本信息、对象标识符和文件大小三个字段,为 Git LFS 系统提供了管理大文件所需的基本元数据。
注意事项
1. 跟踪注意
定义 Git LFS
应跟踪的文件类型本身不会将任何预先存在的文件转换为 Git LFS,例如其他分支上或之前提交历史记录中的文件,正如方才我的操作是,先提交.gitattributes
文件进行跟踪,然后再上传大文件。
2. Git LFS 的计费
每个账户每月可获得免费配额为 1GB 存储 + 1GB 流量,超出需付费。
- 关于 Git Large File Storage 的计费。
3. 本地大文件操作注意事项
-
大文件下载
当你克隆一个使用 Git LFS 管理大文件的项目时,默认情况下只会下载指针文件。如果你需要下载实际的大文件,可以使用以下命令:
git lfs pull
如果你只需要下载特定的大文件,可以指定文件路径:
git lfs pull --include="path/to/file.psd"
-
大文件更新
如果大文件在远程仓库有更新,你需要先拉取指针文件的更新,然后再使用
git lfs pull
下载更新后的大文件。 -
大文件清理
在本地项目中,你可能会有一些不再需要的大文件。可以使用
git lfs prune
命令清理本地缓存的大文件,释放磁盘空间:git lfs prune
后续
后续我会推出 《交互式变基》 的方案来解决 "历史记录中存在大文件导致无法 git push origin master" 推送,该文章正好解决“注意事项的第一项”,欢迎评论留言。