【问题标题】:Export all commits into ZIP files or directories将所有提交导出到 ZIP 文件或目录中
【发布时间】:2018-12-10 09:46:51
【问题描述】:

如何将所有提交导出到 ZIP 文件中(包含所有文件,而不仅仅是补丁/差异):

myproject-commit1-67d91ab.zip
myproject-commit2-9283acd.zip
myproject-commit3-c57daa6.zip
...

或进入目录:

myproject-commit1-67d91ab/
myproject-commit2-9283acd/
myproject-commit3-c57daa6/

?

我在考虑类似的命令:

git archive --format zip --output myproject-commit3.zip c57daa6

来自How do I export a specific commit with git-archive?,但是如何获得所有提交

注意事项:

  • 目标是导出每次提交的所有文件,这样即使机器上没有git 也可以访问它们 p>

  • 来自How can I export Git change sets from one repository to another via sneaker net (external files)? 的答案创建了一个.bundle 文件,但没有git 似乎无法访问它,所以这不是我要找的东西

  • 这几乎可以工作:

    for ((i = 0;; ++i)); do git checkout master~$i || break; tar czf ../myproject-commit$i.tgz .; done
    

    但它也会归档当前目录中不是的所有文件 git added to repo...如何避免这个问题?

【问题讨论】:

  • 试试git bundle。它创建了一个像只读存储库一样工作的包。见git-scm.com/docs/git-bundle
  • @phd 来自stackoverflow.com/questions/49101425/… 的答案创建了一个.bundle 文件,但没有git 似乎无法访问它,所以这不是我要找的。​​span>
  • 你没有解释你想要什么。你应该从一开始就这样做。嗯,git archive 似乎是答案,不,没有单一的命令。
  • @phd 谢谢你的评论,我认为说我想将每个提交导出到 zip 文件 myproject-commit3-67d91ab.zip 已经足够明确了,但现在我进行了编辑以添加更多细节。

标签: git export git-archive


【解决方案1】:

你不能,除非你已经在考虑的方法。

具体来说,要将 每个 提交转换为 zip 存档(每次提交一个单独的存档),只需迭代每个提交,将每个提交转换为 zip 存档。

您的迭代方法只需要遍历所有可能的提交,而不是仅遍历 master 分支的所有第一父级,并且您必须在每个此类提交上使用 git archive。因此:

git rev-list --all |
    while read hash; do git archive ...options... $hash
done

git rev-list --all 命令告诉 Git 按某种顺序打印出每个可访问的提交哈希 ID。要更改顺序,请使用git rev-listgit log 可用的各种排序选项(例如--author-date-order--topo-order)。

如果您想要每次提交(如果您只想要 master 的第一父母),您仍然可以使用 git rev-list

git rev-list --first-parent master | ...

这里,由于 Git 从master 标识的任何提交开始仅遍历第一父级,因此哈希 ID 将按照 Git 认为的前向顺序输出,即向后跨分支的第一父级:

...--o--o--o--o--o--o------o   <-- master
      \        \          /
       \        X--X--...X   <-- somebranch
        \         /
         X--X----X--X   <-- anotherbranch

不会出现任何X 提交,因为它们不在第一父系谱系中。 (没有--first-parent,因为somebranch 上的所有提交,以及anotherbranch 上除最后一个之外的所有提交,master 上,您将获得所有X 提交。 )

[Basj 添加了以下内容,由于$((i=i+1)):] 似乎是特定于 bash 的:] 编辑:这是一个随时可用的命令,如问题中所述:

git rev-list --all --reverse | while read hash; do git archive --format zip --output ../myproject-commit$((i=i+1))-$hash.zip $hash; done

[torek 觉得有必要补充一下 :-) :请注意,上面列举了顺序提交,即使这不是可逆映射。]

【讨论】:

  • 感谢您的详细回答@torek。我只是在最后附加了准备使用的命令。
【解决方案2】:

您可以使用 zip 文件下载具有特定提交的项目

https://host_url/{user_name}/{project_name}/archive/{commit_id}.zip

编辑

您可以使用命令行来执行此操作。

git archive -o commit_id.tar --remote=<repo_url> <commit_id>

【讨论】:

  • 在这种特定情况下,我不使用 github 或类似的东西。我只有一个本地仓库,我不认为网络解决方案可以在这里工作。
  • 谢谢@Shravan40,但你可以看到我已经在问题本身中提到了这一点,问题更多:如何获取所有提交的存档?
【解决方案3】:

@torek 我稍微改进了解决方案。
这一次导出提交,使用git log“通常可见”(所有提交都导出到文件夹zip):

mkdir zip && git log --format=%h --reverse |
    while read hash;
    do git archive --format zip --output zip/$((i=i+1))-project-$hash.zip $hash;
done

如果您还想要日期和时间(没有“项目”),请使用这个:

mkdir zip && git log --format="%h %ad" --date=format:"%d.%m.%Y-%H.%M" --reverse |
    while read hash date;
    do git archive --format zip --output zip/$((i=i+1))-$hash-$date.zip $hash;
done

或者,如果您想将所有提交导出到文件夹(而不是 zip 存档),请使用这个:

mkdir zip && git log --format="%h %ad" --date=format:"%d.%m.%Y-%H.%M" --reverse |
    while read hash date;
    do git archive --format zip --output zip/$((i=i+1))-$hash-$date.zip $hash;
done && find zip -name '*.zip' -exec sh -c 'unzip "$1" -d "${1%.*}"' _ {} \; && rm zip/*.zip

无论如何,如果您还想保持文件模式(chmod),请使用此模式。它使用 tar 存档而不是 zip 存档:

mkdir tar && git log --format="%h %ad" --date=format:"%d.%m.%Y-%H.%M" --reverse |
    while read hash date;
    do git archive --format tar --output tar/$((i=i+1))-$hash-$date.tar $hash;
done && find tar -name '*.tar' -exec sh -c 'mkdir ${1%.*} && tar -xvf "$1" -C "${1%.*}"' _ {} \; && rm tar/*.tar

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-09-18
    • 2012-06-15
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多