简体   繁体   English

从Github Webhooks和.git /确定分支点

[英]Determine branch point from Github Webhooks & .git/

I'm trying to track the history of a repo on Github as it's created. 我正在尝试跟踪Github创建时的回购历史。 Tracking a linear history is simple enough with the PushEvent , but I'd also like to track branches, merges, etc. 使用PushEvent跟踪线性历史记录非常简单,但是我也想跟踪分支,合并等。

From playing around with it so far, it seems like a PushEvent 's before field only gives you the previous commit on the ref that was pushed, so if you create a branch called test and push to it, the previous commit is 000000 since there was no previous commit on test . 从到目前为止的操作来看,似乎PushEventbefore字段只为您提供了被推送的ref上的前一次提交,因此,如果您创建一个名为test的分支并将其推送到该分支, PushEvent那里开始,前一次提交为000000以前没有提交过test The CreateEvent only tells you that a branch was created, but it doesn't seem to tell you what the branch point was. CreateEvent仅告诉您已创建分支,但似乎没有告诉您分支点是什么。

From what I can tell, the only way to get around this is to pull the repo and crawl .git/ to reconstruct the full history DAG. 据我所知,解决此问题的唯一方法是拉出仓库并抓取.git/来重建完整的历史DAG。 Is that correct, or is there another kind of event that I should be looking into? 那是正确的,还是我应该研究的另一种事件?

Also, if I'm trying to recreate the history from .git/ , logs/refs/head/{branch name} only gives you something like this: 另外,如果我尝试从.git/重新创建历史记录,则logs/refs/head/{branch name}只会为您提供以下信息:

3e0bad... 3e6422... {Author} 1458238937 -0700 merge test : Merge made by the 'recursive' strategy. 3e0bad... 3e6422... {Author} 1458238937 -0700合并test :“递归”策略进行的合并。

This doesn't tell you which commit was merged with 3e0bad... to create the merge commit. 这不会告诉您哪个提交已与3e0bad...合并以创建合并提交。 Is the only way to do it to go to logs/refs/head/test and look at the latest commit before the timestamp 1458238937 , or is there somewhere else that the parent commits are stored explicitly? 是这样做的唯一方法是去logs/refs/head/test并查看时间戳1458238937之前的最新提交,还是在其他地方显式存储了父提交?

Thanks in advance! 提前致谢!

The information really isn't available. 该信息确实不可用。

Consider, for instance, the following sequence of commands: 例如,考虑以下命令序列:

$ git clone <url> repo
$ cd repo
$ git checkout -b b1 master
Switched to a new branch 'b1'
$ echo stuff >> file; git add file; git commit -m add-stuff
[b1 b100000] add-stuff
...
$ git checkout -b b2
Switched to a new branch 'b2'
$ echo more stuff >> file; git add file; git commit -m more-stuff
[b2 b200000] more stuff
...
$ git push origin b2

Note that I'm not pushing b1 here. 请注意,我这里不推b1

At this point, origin (whether github or any other site) receives, from us: 此时, origin (无论是github还是任何其他站点)都从我们这里收到:

  • commit b100000... (this hash is made up of course; the name starting with b1 is meant to tell us that b1 was created "from" master using branch b1 ); 提交b100000... (此哈希当然是组成的;以b1开头的名称是要告诉我们 b1是使用分支b1从“ master”创建的);
  • commit b200000... ; 提交b200000... ;
  • any trees and/or file blobs needed for those two commits (presumably updated trees and blobs for file file , although it's possible, however unlikely, that the required tree and file blobs are already present due to the new trees and files matching some existing trees and files); 这两次提交所需的任何树和/或文件Blob(可能是文件file更新的树和Blob,尽管由于新的树和与某些现有树匹配的文件而可能存在(但不太可能)所需的树和文件Blob已经存在和文件); and
  • a request to set refs/heads/b2 to b200000... . refs/heads/b2b200000...的请求。

The new commits have the usual metadata: commit b100000... has whatever master pointed-to as its parent, and b200000... has b100000... as its parent. 新的提交具有通常的元数据:提交b100000...具有指向其master ,而b200000...具有b100000...作为其父b100000... Let's assume that master has not moved since the clone, and call its commit a000000... . 假设master自克隆以来没有移动过,然后将其提交a000000...

Presumably neither b1 nor b2 exist on the server. 大概服务器上既不存在b1也不存在b2 The server's hook therefore gets an update that creates refs/heads/b2 pointing to b200000... , ie, the "old" SHA-1 is the null hash. 因此,服务器的挂钩获得了更新,该更新创建了指向b200000... refs/heads/b2 ,即,“旧” SHA-1是空哈希。

If, on the server, we accept this push, and then look at the resulting commit graph, we'll see b2 pointing to b200000... , which points to b100000... , which points to a000000... , which is on an existing branch, master . 如果在服务器上我们接受此推送,然后查看生成的提交图,我们将看到b2指向b200000... ,它指向b100000... ,它指向a000000... ,即在现有分支上, master We will then conclude that branch b2 was created directly from master. 然后我们将得出结论,分支b2是直接从master创建的。

But it wasn't! 但这不是!

If I now git push origin b1 , I will send no objects ( origin already has everything needed) and a request to set refs/heads/b1 to b100000... . 如果现在使用git push origin b1 ,则将不发送任何对象( origin已经具有所需的一切),并且不会发送请求将refs/heads/b1b100000... This will be another branch creation in the hook, but this time b1 is being created pointing to a commit that's already on branch b2 . 这将是该挂钩中的另一个分支创建,但是这次创建的b1指向分支b2上已经存在的提交。 Where shall we now decide that b1 was created from? 我们现在应该从哪里确定b1是从哪里创建的?

Also, if I'm trying to recreate the history from [a reflog, and I encounter a merge ...] 另外,如果我尝试通过[reflog重新创建历史记录,并且遇到合并...]

The commit that was current before the merge occurred is always the first parent of the merge commit itself. 合并发生之前的当前提交始终是合并提交本身的第一个父级。 The merged-in commit is, in the graph, identified by the 2nd (or in the case of an octopus merge, 3rd, 4th, etc) parent of the merge. 在图中,合并的提交由合并的第二个(或在章鱼合并的情况下为第三,第四等)标识。 As you have seen, the text in the reflog contains the argument presented to git merge , which may be a branch name, or a tag name, or indeed anything acceptable to git rev-parse (see the gitrevisions documentation ). 如您所见,reflog中的文本包含提供给git merge的参数,该参数可以是分支名称或标记名称,或者甚至是git rev-parse可接受的任何内容(请参见gitrevisions文档 )。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM