【问题标题】:How to list the change history of the directory tree in git如何在git中列出目录树的更改历史
【发布时间】:2014-02-20 20:47:12
【问题描述】:

Git 不会像这样跟踪目录。它只跟踪存在于某个目录中的文件。 (见How can I add an empty directory to a Git repository?

但是,如果我有一定的提交历史,我隐含地也有目录树的更改历史。

那么我该如何回答这样的问题:

  1. foo/bar 目录是何时创建的(在 git 术语中:该目录中的第一个文件是何时创建的)。如果 foo/bar 已经存在,则可能有多个合格的提交 在历史上删除了一段时间,后来又重新创建了。
  2. 目录 foo/bar 何时被删除(在 git 术语中:最后一个文件何时从该目录中删除)。如上所述,可能有多个符合条件的提交。
  3. 历史上任何时间点存在的 foo/bar 的子目录是什么

我能想到的最接近的是伪代码:

loop over all commits (git rev-list --all)
  start from repo root directory
  do recursively on the directory tree rebuilt so far
    call git ls-tree and grep the tree lines
    rebuild next level of directory tree
  end
end

显然,这可以用您最喜欢的脚本语言编写。

然后我有了所有目录树,我仍然需要以一种聪明的方式搜索它们,以便回答类型 1 - 3 的问题。同样,可行但可能不会在几分钟内完成。

问题是:

  1. 有没有更简单的方法?
  2. 如果不是:网络上已有的脚本是否合适? (我的谷歌搜索没有发现任何内容,但我也没有找到完美的搜索词)

【问题讨论】:

    标签: git


    【解决方案1】:

    对于问题 1 和 2,这很简单:

    • 目录 foo/bar 何时创建?
      git log --oneline -- foo/bar | tail -n 1

    • foo/bar 目录何时被删除?
      git log --oneline -- foo/bar | head -n 1

    但是,第三部分有点棘手,我无法完全回答。

    上面的两个命令给你$FIRST_REV(创建)和$LAST_REV(删除)。

    以下 sn-p 为您提供修改树的所有提交:

    for rev in $(git rev-list FIRST_REV..LAST_REV)
    do
      git ls-tree -r -t $rev | grep tree | cut -f 2
    done
    

    然后,您有一个存在的目录列表。但仍有重复。将该列表传递给sort -u,您就完成了:

    #!/bin/sh
    for r in $(git rev-list FIRST_REV..LAST_REV) 
    do 
        git ls-tree -r -t $r | grep tree | cut -f 2
    done | sort -u
    

    但是,您会丢失这些目录受到影响的提交的信息。这就是缺点。

    而且,这假设 foo/bar 仅创建一次并且不再存在。

    【讨论】:

    • +1 - 你比我更早建议使用git log。如果可以的话,我会把我的答案留在那里一会儿,看看 OP 对我的建议 3 的反应是什么。
    • 您打算将 * 传递给 shell 还是 git?我认为两者都行不通。对于 shell,它仅在您运行命令时首先添加/最后删除的内容在您的工作区域中时才有效。 git log 似乎不喜欢 *.不管怎样,我认为它不起作用。
    • @Uwe:改变了答案。使用测试存储库进行了尝试,如果 foo/bar 已被删除,上面的代码也可以工作。
    • @Eckes:确实很有趣!不知道/期望 git log 会接受目录名称。是否有任何替代建议出现,我仍然会等待一段时间。
    • 现在只评论你的前 2 个命令。它们仅在 foo/bar 已创建并可能在历史记录中删除一次时才起作用。我已经编辑了我的问题,以便更清楚地表明我需要多个提交(如果适用)。对不起,不打扰你,我这里的历史是很多来回的,添加和删除......仍然需要在现实生活中测试你的循环,但需要现在运行......
    【解决方案2】:

    gitk foo/bar 为您提供了一个用户界面,用于浏览 git 历史记录,仅限于触及 foo/bar 的提交。

    【讨论】:

    • 是的,和 git log foo/bar 一样
    猜你喜欢
    • 2010-12-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-09-03
    • 2017-12-08
    • 2013-07-13
    • 1970-01-01
    相关资源
    最近更新 更多