从现有的子目录创建一个新的存储库,只包含相关的文件和提交

时间:2018-04-26 17:12:50

标签: git bfg-repo-cleaner monorepo

我有一个monorepo,其中有许多不同的packages。我想拿一个包并为它创建一个新的回购。我想保留与项目文件夹中的文件有关的提交。

我尝试将git filter-branch--subdirectory-filter一起使用,git filter-branch --subdirectory-filter ./src/project git log --pretty=oneline dc1fd15e212c2e916591d931f81d0f94b0312067 (HEAD -> master) j a68625cffd59e0bc6efda226042b81979985f77c a1 612e28ee9a2a7e59e8da0dff2c0109f0c03fa216 a2 04335730f1e4ecfbd7882fcdc16d5f2402261b3f a3 3e76c4deecd9b019302bcdf667523dbc866479bd a4 01ca27e1801b1f80d7480110c2861d798b0e6893 a5 可以使用指定文件夹中的文件创建分支。

log

然而,使用--all命令和git log --pretty=oneline --all f96e38e502b6bcab013f4505f40b0060fcafc461 a 06d7edc961690a9e2ec406d64dcee57443441926 b 06723ca315e8f2aad83d4d7e3bfcb095456329c6 c f7f3ff04c873ba573602e8ed24b88394284d1e7a d 9d355e1802fdb6a44199d7f798d4dfc59ab73244 e 00d3e0d524d7f44bd41ea0e12583e234b7db941c f 97a245266a28d75baffa43cc8fc19a8adcf89fe3 g faa1c96d7789db06b216be5d989f8d809d626a32 h a5e892fcb2eb4f05c5cb4f7f0adbf3dfe5bd29b5 i dc1fd15e212c2e916591d931f81d0f94b0312067 (HEAD -> master) j 68583660582d9184f2ea29e9c74da00793775245 k a68625cffd59e0bc6efda226042b81979985f77c l 8a224dcebdfc18b13001c600113104f20ea0334e m 4c1606853902e1e3711892e5515e51fee45dcfa2 n 4ecd26965d13266a51f807af3ea88382d5cf8ba8 o 612e28ee9a2a7e59e8da0dff2c0109f0c03fa216 p 31cf0b36a977fa7d2d16fb66465fd59f8a9e274a q dcc685af381a520795bfafe8df667aeb2cf087e6 r a2d39ff1e21541e0a638b39877ab19fee2c162d0 s 9a5775e3bc3194bb021a0687140f976f6751cee1 t 2b9535729525537811745456f8917e200effb44f u f4813470ee84b740e398ed09a68121982f6d171e v 4d46ecbe227d191fc7be0260ff6ddb7c2bd6d759 w aeb866d98e78fed9aef3e9cc721b21b9d051438c x e1ac5f9505f75290833a28c6b27cff659f734b24 y 9b3db9df98df1a20da1b8dda1200c2d09603ee2d z def782319c775c68698666eb5f3fe828a70bf7a6 h 006d44e9f1abb7bba7cb9bdc1dcba09b41a3297d i 1e7eb9b30a6402914344c5ef038076a26bdd4a65 j 2e55da67d626db00043eeddbe1204afd3e7e5790 k 65e868a89ff22412f939ffc71fea8c6cef016683 l aadc31aa541da8fe0f25af5aec9a967f6c5172f1 m ed865f5499640eac12cd0b0048a54224898cf998 n 7c51acdc3e57f3c28fdcc9ea5c3c368b29991d9b o 06770a789e66dddc1e87257a4f64ca42e9fed6cf p 8148c5cdaa920900eac1750c2453ead6446b2d08 q 标志,您可以看到在主分支中有更多提交。

subdirectory

这些提交中的每一个都有与所需bfg无关的文件和数据。

如何删除这些文件?这就是-p的用武之地。

使用--protect-blobs-frommaster)标记,我可以传递bfg -D '*' -p "`git rev-list master | tr '\n' ','`" 中的所有引用。

master

这将从整个存储库历史记录中删除不在git log --all分支中的所有文件

然而!如果你./src/project,你仍然会看到所有额外的提交,而提交中没有文件。

我正在寻找一种方法来为命令提供目录(例如filter-branch),并且拥有一个仅包含与该目录中文件有关的文件提交的repo。 / p>

如何在没有文件更改的情况下删除这些提交?

There is a PR for bfg for a --prune-empty command.这可能有所帮助,但在它合并之前不是一个可行的解决方案,而且我似乎仍然需要同时使用bfgclone

我也试过refs这个分支。理想情况下,有一种方法可以使用master filter-branch来创建一个全新的存储库。

更新

我已经延长了@ BlythMeister的帖子,the article中的subdirectory-filter命令存在一个问题,subdirectory会将DIR=./src/project git filter-branch --index-filter 'git rm --cached -qr --ignore-unmatch -- . && git reset -q $GIT_COMMIT -- $DIR' --prune-empty -- --all git filter-branch --subdirectory-filter $DIR 的内容移到头部。所以我必须在之后运行它。

{{1}}

2 个答案:

答案 0 :(得分:0)

前段时间我有这个确切的问题,我想把一个回购完整的历史记录拆分成2个。

我没有找到一个好的指南,但找到了如何做到这一点,并在我的博客上写了我自己的指南:https://www.blyth.me.uk/2017/06/07/migrating-multiple-folders-between-git-repositories/

我希望这有帮助!

答案 1 :(得分:0)

这是我放在一起非常快的方法。它使用--subdirectory-filter然后一个克隆/合并来移动只获取给定分支的内容和提交而不是整个提交历史。

#!/usr/bin/env bash
# clone the original monorepo
git clone $REPO example
# change directory into monorepo
cd example
# remove origin for safety reasons
git remote remove origin
# filter the package / dir you want to be the new submodule / repo
git filter-branch --subdirectory-filter $SUBDIR
# change directory up one 
cd ../
# create a new directory
mkdir example-subdir
# change directory into the new directory
cd example-subdir
# git initialize
git init
# add the filtered monorepo as a remote 
git remote add source ../example
# fetch the source repo
git fetch source
# merge the master branch into this master branch
git merge source/master

现在你有一个只有来自该特定目录的更改/提交的repo。