网站 - 在GitHub上,本教程深入了解Git Works如何运作,执行很多有时不寻常的步骤才能完成景点。您将不得不密切关注,或者您将在途中丢失。但不要绝望;您可以在您的计算机上运行Thistorial,以您想要的速度跳过您想要的速度,并始终调查inanother终端窗口的状态。实际上,您正在查看从该教程的输出生成的HTML文件。 (那个'为什么有那个" echo hi" upere:tutorial脚本只允许在命令后允许注释。:))教程代码在这里:github.com/ Bakkenbaeck / A-rantom-walk-toud-git - 克隆它并在您的机器上运行它!本教程不适用于绝对初学者,也不是&#34的accollection;烹饪谱"食谱不会帮助您展示广泛的画面,也不会让您迅速地播放。但是,通过实验和调查的一些更深层次的理解。所以让'开始。
首先,快速回顾基于Git相关的术语。树:文件集(文件名,perms,指针到子树/文件blob,而不是定时)提交:元数据(时间,作者,指针到树,可能指向父提交)head:下一个提交哈希/父级提交(仅限本地,由例如git checkout)索引/ staging / cache:head plus"要承诺的更改" (仅限本地,修改,例如,GIT添加/重置,存储在.git中)工作目录/ WIP:索引加"未添加用于提交的更改" (纯文件,仅限本地,修改,例如,Git Checkout / RESET - 哈达)确定?然后让' s init a git存储库......并查看.git /文件夹中的文件。
3#git init。 && git configal user.name" ijon tichy" && git config -local user.email" [email protected]" && rm -rf .git / hooks /&&找到.git -type f
4#echo"这不是一个自述文件" > Readme&& git添加Readme&& git commit -m"第一个提交"
现在有三个对象:提交,树,blob(文件)。什么文件类型做git对象文件使用?
所有内部斑点都被压缩。节省空间并保持Grep Clean。耶!稍后有关这些文件的更多详细信息。
这是对当前头部的指针(或者在&#34中的哈希;独立的头"状态)。
这是大师头的反射(CF. git Rhallog)。它不是回购的一部分,但仅供本地方便。我们稍后会看看它。
那个文件git用来跟踪当前索引(仅限本地)。它基本上是一个未提交的提交,而不是#39;树'一部分。这个文件是几个魔法的Git文件中的一个,主要是因为速度优化考虑因素:为了" git状态"要成为ABLETO,可以快速运行,一些数据附加到保存在实际的repohas中的数据。这就是为什么.git / index不仅仅是标准的TreeObject(它没有额外的元数据)。我们不会在这里详细介绍。进一步阅读:https://github.com/git/git/blob/master/documentation/technical/index-format.txt https://mirrors.edge.kernel.org/pub/software/scm/git/docs/技术/活泼,git.txt https://stackoverflow.com/questions/4084921/what-does-the-git-index-contain-exactly
[主6ecf002]第一次提交日期:星期三5月12日17时04分33秒2021 0200 1文件改变时,1个插入(+)创建模式100644自述
我们刚刚修改了最后一个提交,但实际上是改变任何东西:同样的提交消息,作者,树和时间。但提交哈希已经改变了。为什么?
提交6ECF00219D83579A35E3A1DAAE2615F753C0EC0FAUTHOR:IJONTICHY< [email protected]& GT; authordate:5月12日17:04:33 2021 + 0200Commit:[email protected]& gt; commitdate:星期三5月12日17:04:34 2021 +0200第一次提交
因为有' S比git的日志显示由default.There&#39更多的元数据; S作者日期和提交日期。修改承诺遵销作者日期,但更新提交日期。需要注意的是Git有单独的作者,提交者accountfor传统的Linux基于电子邮件的补丁workflow.Authors会通过邮件发送补丁,维护挑uppatches并提交(或拒绝)。
14#git_committer_date =" 1月1日12:00 2000 + 0000" git commit -amend --date =" 1月1日12:00 2000 + 0000" -m"第一个提交"
[Master C8D9B9C]首次提交日期:1月1日星期六12:00:00 2000 +0000 1文件已更改,1个插入(+)创建模式100644 Readme
15#git_committer_date =" 1月1日12:00 2000 + 0000" git commit -amend --date =" 1月1日12:00 2000 + 0000" -m"第一个提交"
[Master C8D9B9C]首次提交日期:1月1日星期六12:00:00 2000 +0000 1文件已更改,1个插入(+)创建模式100644 Readme
提交c8d9b9c01eea11fb1032903b0dd2bea3eeb46f48author:ijon tichy< [email protected]& gt; authordate:1月1日星期六12:00:00 2000 + 0000commit:ijon tichy< [email protected]& gt; commitdate:1月1日12:00:00 2000 +0000第一次提交
让我们修复日期,以便我们有确定性哈希。出于此目的,如果仅限该演示;不要在家里做这件事。
的.git /对象/ 40 / 33e22db3df6e826be2ba43f5db16ced4e3bc18:zlib的压缩data.git /对象/ 5B / 6c6cb672dc1c3e3f38da4cc819c07da510fb59:zlib的压缩data.git /对象/ 6E / cf00219d83579a35e3a1daae2615f753c0ec0f:zlib的压缩data.git /对象/ B3 / 5c99875f5758f64e9348c05dac14848a046f59:zlib的压缩data.git /对象/ C8 / D9B9C01E11FB1032903B0DD2BEA3EB46F48:ZLIB压缩数据
那一棵树(我们没有更改文件到目前为止),一个文件,三个提交(原始,哈希测试,固定时间)。
的.git /对象/ 40 / 33e22db3df6e826be2ba43f5db16ced4e3bc18:zlib的压缩data.git /对象/ 5B / 6c6cb672dc1c3e3f38da4cc819c07da510fb59:zlib的压缩data.git /对象/ 6E / cf00219d83579a35e3a1daae2615f753c0ec0f:zlib的压缩data.git /对象/ B3 / 5c99875f5758f64e9348c05dac14848a046f59:zlib的压缩data.git /对象/ C8 / D9B9C01E11FB1032903B0DD2BEA3EB46F48:ZLIB压缩数据
注意在树中找到文件元数据(文件模式位,文件名)在树中找到。他们的操作日期,例如,如果伪像归档是比sourcefile日期较大的,所以如果播出旧项目版本(用'正确'旧档案)不会触发重建,那么MakeOnly重建工件让'看看引用的blob。
00000000 62 6C 6C 62 20 32 35 00 54 68 69 73 20 69 73 20 | Blob 25.本发明是| 00000010 6E 6F 74 20 61 20 52 45 41 44 4D 45 20 79 65 74 |不是README + 00000020 0A | 。| 00000021.
00000000 74 72 65 65 20 33 34 00 31 30 30 34 344 20 52 |树34.100644 R | 00000010 45 41 44 4D 45 00 5B 6C 6C B6 72 DC 1C 3E 3F 38 | eADME。[LL.R .. ?8 | 00000020DA 4C C8 19 C0 7D A5 10 FB 59 | .L ...} ... y | 0000002a
树对象也是如此。 '垃圾'在ASCII表示中实际上是自述文件'在二进制中的Blob哈希。
让' s创建一个提交,只需使用git管道命令(git添加等)添加这个新文件。'瓷器')。
Hash-object计算文件的哈希(并且在-W中,将其添加到Git对象)。所以我们有Blob,但没有相应的树或提交。实际上,那些文件甚至没有上演......
在分支测试中致力于承诺:(使用" git restore --ssted<文件> ...""到unstage)新文件:test.txt
有效! test.txt是一个"新文件"。但是,我们仍然没有专用的树对象 - 它仍然在索引中仍然存在。
这占据了索引并从中创建了树对象。我们仍然需要提交对象。
树9240cdb2b8598f50cb8b66328b5c31d077d14470parent c8d9b9c01eea11fb1032903b0dd2b1032903b0dd2bea32903b0dd2bea32903b0dd2bea32903b0dd2bea32903b0dd2bea3eb46f48author ijon tichy< [email protected]& gt; 946728000 + 0000Committer Ijon Tichy< [email protected]& gt; 946728000 + 0000A提交,完成了艰难的方式
......但是新的提交并在日志中显示出来,因为我们的头脑仍然是之前的提交,而且.git / refs / head / master仍然需要更新。
提交5350fa43e7e3a6263c85e47d24b3351f84d24b3351f84be9a22author:ijon tichy< [email protected]& gt; authordate:1月1日星期六12:00:00 2000 + 0000commit:ijon tichy< [email protected]& gt; commitdate:1月1日12:00:00 2000 +0000提交,完成了硬度Waycommit C8D9B9C01EA11FB1032903B0DD2Bea3EeB46F48Author:Ijon tichy< [email protected]& gt; authordate:1月1日星期六12:00:00 2000 + 0000commit:ijon tichy< [email protected]& gt; commitdate:1月1日: 00:00 2000 +0000首次提交
伟大的!这结束了A'手动'使用Git管道命令提交。您可以看到“完整的手册”,即创建FilesSeeded以表示在.git /对象目录中的提交中的Jucking Echo等,也不会是一个大问题。但是,一旦它来改变,我们所看到的东西到目前为止我们所看到的效率低下?没有差异保存,每个文件版本都归因于新对象文件?那个'右,但是在Gitcalled&#39中的另一层物体存储层;包装'让' s创建一个新的空分支以进行测试。
47#在{1..10000}中为i; Do echo $ i>> mangryfile.txt; && tail -v mantringfile.txt&& git添加大型文件.txt&& git commit -m"一个大文件"
==> largefile.txt< == 99919992999399949995999699979998999910000 [packfile_demo(根提交)cec918b]大文件1的文件改变时,万个插入(+)创建模式100644 largefile.txt
注意我们只有少数文件Git DirectoryThat中的占用空间很少。让' s添加东西到一个大文件并提交更改;重复一百次。
49#{为我在{1..100}中; echo"添加更多... $ i" >> mangryfile.txt; git commit -m"添加到大键.txt,$ i" mangryfile.txt;完成} |尾巴15.
1文件已更改,1插入(+)[packfile_demo a5cd302]添加到sallyfile.txt,94 1文件已更改,1个插入(+)[packfile_demo 04265c8]添加到sallyfile.txt,95 1文件已更改,1插入(+)[ packfile_demo 2cb1a0d]添加到leandfile.txt,96 1文件已更改,1插入(+)[packfile_demo c80d763]添加到sallyfile.txt,97 1文件已更改,1个插入(+)[packfile_demo 245005d]添加到largefile.txt,98 1文件已更改,1个插入(+)[packfile_demo e9fa7d0]添加到leangfile.txt,99 1文件已更改,1个插入(+)[packfile_demo ddd7a4e]添加到leangfile.txt,100 1文件已更改,1插入(+)
50#echo -n"对象中的文件数:" &&查找.git /对象intepe f | WC -L&& du -h --max-depth = 0 .git /对象
那个存储膨胀了很多。修改和提交一个文件100次导致100/100 * 3(提交,树,blob)文件,我们现在有100near-idant(压缩)的大型文件对象存储副本。
垃圾收集(它是一个错误的错误,因为它包括repacking)将各个对象文件和重新包装到PackFiles中,仅存储对象Filesthat的差异是相似的。
类似于对象包文件格式,Git Maymanage以优化的方式引用。有些项目有数千个分支(和标签),并管理各个文件中的浪费。有关详细信息,请参阅git-pack-refs。做管道命令(猫文件等)还在吗?
树AAEE22C35FF84B15B28B1BAAA0EF121C9BB217B69Parent E9FA7D0E1AD0936501B478C962E84B8412CAC962E84B8412CAC82AUTHOR IJON TICHY< [email protected]& GT; 946728000 + 0000Committer Ijon Tichy< [email protected]& gt; 946728000 + 0000Adding到大型文件.txt,100
PackFile层对管道命令是透明的,例如,如果需要,Cat-File会像以前一样,访问PackFileSinstead,如有必要。如果您想了解更多关于Packfiles的信息:https://git-scm.com/book/en/v2/git-internals-packfiles最多可与完全不同的东西。有关GIT结账之间的差异的说明,Git Reset --soft,Git Reset( - 混合),Git Reset - Hard ...
结帐更新索引和工作目录。结账不会改变任何分支头(仅限.git / head)。结帐后,索引和工作目录(树)将与所选提交(树)相同(具有默认选项)。
注意:切换到' c8d9b9c01eea11fb1032903b0dd2bea3eeb46f48'。你在'独立的头部'状态。您可以环顾四周,使实验化和提交它们,您可以丢弃您在此处丢弃的任何提交,而不会通过切换回分支来影响任何分支。如果您想创建一个新的分支来保留您创建的提交,您可以(现在或更高版本)通过使用-c使用switch命令。示例:Git Switch -C
注意头现在只是一个哈希,而不是ref:... ...引用一些东西/ refs / heads / branch指针。你甚至可以提交东西......
59#echo"在独立的头部和#34中提交; > detached.txt&& git添加detached.txt&& git commit -m" detached.txt"
警告:您要留下1个提交,未连接您的分支机构:4BFFAD8 DECACHED.TIF您想要通过创建新分支来保持它,这可能是一个好的时间表所做的:git分支
......而Git将有助于向您移动时,在传动的情况下创建一个分支或标记指向最后的提交,它' s悬垂(a"松散的物体")。它'只能检索到禁止禁止,可能会在一段时间内通过垃圾收集删除(见GC.Pruneexpire,默认为两周)。
5350fa4 HEAD @ {0}:结帐:从4bffad870e307173ee175f4f3929bc39ba0fb772移动到test4bffad8 HEAD @ {1}:提交:detached.txtc8d9b9c HEAD @ {2}:结帐:从主移动到c8d9b9c01eea11fb1032903b0dd2bea3eeb46f48c8d9b9c HEAD @ {3}:结帐:从packfile_demo移动到Master6ECF002 Head @ {4}:提交(修改):First Commit4033E22 Head @ {5}:提交(初始):第一次提交
ReftoG是头指针和其他引用的本地日志。无论何时执行提交/结账/重置,将写入此日志。日志ISN' t部分实际的repo,不会被共享。 by" git push"等等。请注意,我们使用的乐趣与管道命令没有' t updatethe回流。它'如果你在任何时候丢失,或者用独立的头等丢失了。注意回流条目过期(请参阅GC.Reflogexpire,默认90天).Also,Remprog提供了诸如Master@“以aerone.week.ago”}等功能,该功能确实看着Rhallo(即,"什么在这台机器和#34;)上一周前掌握了一周前的尖端,而不是在提交日志。达到git重置......
62#git checkout test&& echo" ...加上更多文本" >> test.txt&& git添加test.txt&& git commit -m"更改test.txt" && git log --pretty = online
已经在'测试' [测试5395c9c]改变的test.txt 1个文件改变时,1个插入(+)5395c9ce4bd2ccb14dd3f7b847694fe87b2c2d94改变test.txt5350fa43e7e3a6263c85e47d24b3351f84be9a22提交,完成了艰难wayc8d9b9c01eea11fb1032903b0dd2bea3eeb46f48第一承诺
要回顾测试分支,我们开始了一个提交添加自述文件,然后一个提交添加test.txt,我们只是通信程序更改为test.txt。
在分支测试中致力于承诺:(使用" git restore --ssted<文件> ..."到unstage)修改:test.txt
重置--soft将当前分支的头部移动到SelectedTree / Commit。它确实*不是*触摸索引和工作目录。因此,在软复位后,Git状态将显示您的(不变)工作目录和分支元件的索引已重置的差异。这意味着如果软重置为任何提交,那么立即Git CommitAgain,新提交的生成树将替代到您的启动工作目录。您可以易于释放的一件事是在分支中挤压犯规,但是,rebase - 内部(我们将稍后查看)适合于此。如果要摆脱提交的更改,请重置 - 袜子不是您想要的。
重置后未置入的更改:M Test.TXTON分支TestChanges未分阶段暂存:(使用" git添加<文件> ..."更新将提交什么)(使用" git restore <文件> ..."要丢弃工作目录的变化)修改:test.txtno添加到提交到提交(使用" git添加"和/或" git commit -a&# 34;)
重置 - 混合(默认值)更改当前分支头*和* indexto所选树/提交。它不触摸工作目录。这个命令很好地重新加工提交,例如,已经意外地投入了一个提交的拆分化,但类似于重置--soft,可能是Rebase - InteractiveWill是更好的选择。再次,如果你想摆脱提交的变化,重置 - 贴现不是你想要的。
头现在处于5350FA4的提交,完成了硬盘分支试验到提交,工作树Clean ==> test.txt< ==艰难的方式
RESET - 拒绝覆盖具有索引的工作目录。工作目录的任何未提交更改将丢失。这是Go-to命令以完全摆脱,切换分支(例如,如果要切换MasterAnd Dev分支),或者摆脱任何本地更改(例如,Git Reset -Hard Origin / Master)。请注意,所有重置命令都可能移动返回厌氧(或某些提交,即使与以前状态也没有共同的祖先)。如果已完成,如果使用Hymote存储库,则需要能够强制推送。时间潜入远程存储库。
出于此演示的目的,我们使用预先初始化的本地裸机存储库作为遥控器。一个裸帐,只需介绍.git /文件夹,单身工作目录的内容。这突出显示了remotesare的一个关键方面:它们基本上只是指向一个单独的.git /目录的指针,无论它们是'重新达到的ssh,http还是通过文件系统访问直接。
只是假装这是Git Clone Git @ Someserver:git-playground.git克隆远程存储库基本上设置了一个localEmpty .git /存储库,并添加了远程名为'起源'使用默认值时,Git CloneThen连接到原点,获取其Git对象文件,为ThereMote的分支创建远程跟踪分支,然后创建本地主分支,设置其Headto Origin / Master并检查。请注意,如果连接到实际远程服务器,它将输出"枚举对象"等于内部内部的消息;那个' s远程服务器重新包装(仅限)完成操作所需的文件。我,任何"松散的物体"等等不传输,如果您使用带有git clone的 - depth或-single-branchoptions,则只需一分的远程' sobjects通常会传输。
[core] respositoryformatversion = 0 filemode = true = fallow logallrefupdates = true [远程" origin"] url = emply / semote fetch = + refs / head / *:refs / remotes / horiz / * [分支" master"] remote = liginer merge = refs / heads / master
.git / config用于跟踪thocal master分支正在跟踪远程repositorybranch的事实。
没有魔法:远程分支只是文本致命的提交引用引用,就像本地分支一样。没有.git / refs / remotes / russ / master虽然......?
记住引用可能会收集,而不是放入自己的文件。让' s返回上一个本地示例存储库并进行一些清理。
71#rm -rf git-playground&& git checkout master&& git branch -d packfile_demo&& git分支-d测试
没有必要从克隆开始; 您也可以为现有的本地存储库添加aremote。 git fetch后,我们看到远程分支.Fetch不变,更改本地分支,也不会更改indexnor工作目录。 请注意,遥控器/游乐场/ Maste ......