文档章节

Gitee 存储库体积控制策略

Force武装卫队
 Force武装卫队
发布于 11/05 17:29
字数 1679
阅读 2393
收藏 15

前言

作为全球 Top2 的代码托管平台之一,Gitee 拥有350W 用户和 600W 存储库,海量的存储库对 Gitee 的硬件设施提出了更高的要求,以 600W 存储库为例,如果按照平均 1GB 的大小磁盘体积,这些存储库将需要总共 5860 TB 的空间,按照 Gitee 每台存储磁盘 14TB,则需要 419 台存储设备。实际上在 Gitee 中,绝大多数存储库的体积都小于 100 M,超过 100 M 的存储库通常都是未合理使用 git。尽管如此,Gitee 仍然需要投入大量的存储设备来支撑用户的接入。为了能够让更多的人能够免费使用 Gitee,我们迫不得已只能限制大存储库的访问。近期,Gitee 存储库路由架构改造第一阶段已经到了收尾阶段,在此期间,我们将陆续将服务端的钩子切换到 GNK (Gitee Native Hook),GNK 基于 C++ 编写,使用了 Git 环境隔离等高级特定,意味着大文件检测和存储库体积检测不会再有漏网之鱼。一些用户的存储库体积已经超过了 Gitee 配额限制,而之前的钩子检测存在缺陷,无法实时拦截大存储库和大文件,当切换到 GNK 后,这些用户修改他们的存储库却无法推送到 Gitee,这让他们产生了困扰,本文就这一困扰解答若干问题。当然如果用户有其他问题也可以在本文下留言。

Gitee 套餐信息

Gitee 分为普通用户,和企业用户,个人的套餐实际和企业免费版一致,最新的套餐信息 如下:

大存储库的产生

Git 是基于文件快照的,但并不是所有时候都存储快照,当对象被打包到 .pack 文件中时,则有可能存储对象的差异,即 OBJ_OFS_DELTA/OBJ_REF_DELTA。这种机制使得在文件大小不变的情况下,每次修改文件都会导致存储库体积按大于文件压缩后体积增长,以一个 Zip 压缩文件为例,每次修改后大小为 50 MB,提交 20次便能够超过 1000 MB。当用户将项目中的构建文件诸如 .exe,.pdb,.so,.jar 或者依赖文件/文件夹 node_modules,packages 以及资源文件 .psd,.raw,.avi,.jpg 添加到版本控制中后,很容易使得存储库体积超出限制。

大文件除了容易让存储库超出限制,而且也会降低用户拉取代码的体验,git 在处理二进制文件时需要花费更多的 CPU。

GNK 的拦截

随着存储服务器陆续切换到 GNK,超出配额的报告也可能会更多。GNK 的拦截是实时的,即用户将代码推送到服务器后,git-receive-pack 将调用 GNK 中的 pre-receive 钩子,这个钩子将统计存储库的 objects 目录,将所有文件和目录所占用的磁盘空间大小累加就获得了存储库的体积,这和 du -sh 机制一致,特别的,我们这里说的存储库体积包含其附带的 wiki 存储库的目录,这也是为了避免个别用户使用 wiki 存储大文件。

GNK 目前会给大存储库推送提供三次机会,如果三次读没有减小存储库体积,则便无法继续修改远程存储库,以 Linux 内核 1.4 G 为例,如下所示:

第三次时如果存储库体积依然超出限制,则会告知用户,已经耗尽所有机会,无法重试。

无法尝试时,输出如下:

GNK 还会拦截用户推送的大文件,但已经存在于存储库的大文件,GNK 不会去检测。基于 Git 环境隔离机制实现的 GNK,拦截大文件不会像之前一样反复推送大文件失败导致存储库体积变大,环境隔离目录在 pre-receive 执行失败后会被删除。

存储库的精简方案

在开发的时候,我们可以使用包管理工具管理项目依赖,比如 dotnet core 使用 NuGet,Java 使用 Maven,完全没有必要将依赖二进制纳入版本控制。

如果不慎将大文件纳入了版本控制中,可以去访问 Gitee 帮助:仓库体积过大,如何减小?。在修改本地存储库历史记录后,通过 git push -f 的方式推送到 Gitee,然后在项目配置页面运行 Git GC 待 GC 运行后,通常能够发现存储库体积变小。注意:当修改本地存储库历史后强制推送到远程服务器,在运行 GC 之前,可以观察到存储库的体积显著增大,只有在运行 git gc 后,才可能会使存储库体积变小。

当然你还可以使用 git-sizer 查看存储库的占用细节,或者使用新的 git-filter-repo 去修改存储库历史记录。git-filter-repo 已经成为了 Git 的官方推荐。

如果项目使用 PR 机制参与协作开发,强制推送后运行 git gc 可能不会减小存储库的体积(这是因为存储库需要使用内部引用保持 PR 相应的 commit 的可用性,不被 GC),这个时候用户可以升级套餐,获得更大的存储库容量,或者在 Gitee 上新建一个空存储库,将修改历史记录的存储库推送到新的存储库。使用新的存储库即可。

一些大文件无法用版本控制可以将其使用 Git LFS 管理,用户需要使用 Git LFS 可以查看 Gitee LFS

对于一些用户由于疏忽已经用完重试次数则可以联系官方团队重置重试次数

最后

无论如何,给用户带来困扰,我们很抱歉,但 Gitee 也是需要不断改进,不断的完善。随着 GNK 迁移完成和前端切换,Gitee 的路由架构改造第一阶段也将完成,这使得用户改名,存储库改名,存储库忽略大小写,fork 能够更容易实现或者更加快速。

© 著作权归作者所有

Force武装卫队

Force武装卫队

粉丝 194
博文 41
码字总数 82115
作品 3
深圳
高级程序员
私信 提问
加载中

评论(20)

s
sugao
恩,很好的。马上就要换平台了,搞了一天
天绝弑杀
天绝弑杀
这就全球第二大了?
Skqing
Skqing
操作太慢了,还有别的办法吗?
Skqing
Skqing
Rewrite 02c9d741975ac5f529e93dc1d763953b55947fbf (419/1380) (2448 seconds passed, remaining 5614 predicted) 太慢了,能有别的办法吗?
Skqing
Skqing
执行命令还是不行提交不了 git filter-branch --tree-filter 'rm -f path/to/large/files' --tag-name-filter cat -- --all
唉,
Skqing
Skqing
Rewrite 3a016294da2f098adbbd82f35e71403f3cb26c25 (29/604) (247 seconds passed, remaining 4897 predicted)
一直这样,正常吗?
Skqing
Skqing
合情合理,不过要是能提前通知用户就更好了。
水平凡
水平凡
你们说的都很有道理,,,,我已经把个别项目从企业版切回gitlab本地版了。。。
久永
久永
多个不同人不同组织的库,物理上是存一份还是很多份?
红薯
红薯
看仓库的归属哦
霡霂
霡霂
“Gitee 存储库路由架构改造第一阶段已经到了收尾截断”的截断应该改为"阶段"
OSChina 开源周刊第37期 —— React Native 简单教程

每周技术抢先看,总有你想要的! 前端开发 【翻译】React Native 简单教程 【软件】AngularBeans —— Java EE 和 AngularJS 集成 服务端开发/管理 【软件】LeoFS —— 高可靠性的分布式对象...

OSC编辑部
2015/06/06
3.1K
1
LCPkg 0.2.1 发布,C/C++ 依赖管理工具

LCPkg 0.2.1 发布了,LCPkg 是一个用于管理 Windows C/C++ 项目依赖的命令行工具,它能够: 从 vcpkg 或 GitHub 安装依赖包 记录你项目的相关信息以及依赖库信息 将资源文件、头文件、库文件...

司徒永超
10/09
929
6
如何控制 Git 库的膨胀? GC 一步搞定!

相信每个公司都有自己的官网。小明公司也不例外,不过小明却发现公司的“猿”哥哥将许多视频放在了代码仓库里,导致原本只有代码的仓库从早期的几十MB,飙升至 1G以上,变得无比臃肿(或者是慢...

码云Gitee
2018/09/13
0
0
如何将 GitHub 项目导入码云?一步搞定!

码云(Gitee.com)是开源中国出品的 代码托管·协作开发 云平台,汇聚了国内众多优秀开源项目。历经 5 年打磨与沉淀,已有超过 200 万开发者选择码云,托管项目超过 300 万。我已经有了GitHu...

码云Gitee
2018/06/05
0
0
码云已经支持 Git Wire Protocol

前言 两个半月前,Google 开发者宣布了 Git Wire Protocol,即 Git v2 协议,Git Wire Protocol 协议改进了 Git 的传输过程,增加了可扩展性。关于协议的背景和细节介绍,大家可以去 《码云即...

Force武装卫队
2018/09/05
1K
9

没有更多内容

加载失败,请刷新页面

加载更多

Kafka实战(五) - 核心API及适用场景全面解析

1 四个核心API ● Producer API 允许一个应用程序发布一串流式的数据到一个或者多个Kafka topic。 ● Consumer API 允许一个应用程序订阅一个或多个topic ,并且对发布给他们的流式数据进行处...

JavaEdge
今天
11
0
实现线程的第三种方式——Callable & Future

Callable Runnable 封装一个异步运行的任务, 可以把它想象成为一个没有参数和返回值的异步方 法。Callable 与 Runnable 类似, 但是有返回值。Callable 接口是一个参数化的类型, 只有一 个...

ytuan996
今天
11
0
OSChina 周六乱弹 —— 不要摁F了!

Osc乱弹歌单(2019)请戳(这里) 【今日歌曲】 @巴拉迪维 : 朴树写的词曲都给人一种莫名的失落感,不过这首歌他自己却没有唱,换成赵传这种高音阶嘶喊的确很好,低沉但却有力,老男人的呐喊...

小小编辑
今天
20
0
Android Binder机制 - interface_cast和asBinder讲解

研究Android底层代码时,尤其是Binder跨进程通信时,经常会发现interface_cast和asBinder,很容易被这两个函数绕晕,下面来讲解一下: interface_cast 下面根据下述ICameraClient例子进行分析...

天王盖地虎626
昨天
13
0
计算机实现原理专题--存储器的实现(二)

计算机实现原理专题--存储器的实现(一)中描述了一种可以记住输入端变化的装置。现需要对其功能进行扩充,我们将上面的开关定义为置位,下面的开关定义为复位,然后需要增加一个保持位,当保...

FAT_mt
昨天
9
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部