将一些文件从git存储库移动到新存储库

将一些文件从git存储库移动到新存储库,git,Git,我有一个git存储库,它本质上包含两个相关的项目,我现在想拆分它们。我想将与一个项目相关的文件移动到一个新的存储库中,以保留更改的历史记录。具体来说,让我们假设原始git存储库包含: file1.c file2.c subdir/file2_extra.c 另外,原始的git存储库包含几个分支。我只想保留其中的一些,那些与我想分离的文件相关的 如何创建一个新的git存储库,该存储库仅包含file2.c和subdir/file2\u extra.c以及提交给它们的历史记录 请注意,我要分离的文件

我有一个
git
存储库,它本质上包含两个相关的项目,我现在想拆分它们。我想将与一个项目相关的文件移动到一个新的存储库中,以保留更改的历史记录。具体来说,让我们假设原始git存储库包含:

file1.c
file2.c
subdir/file2_extra.c
另外,原始的
git
存储库包含几个分支。我只想保留其中的一些,那些与我想分离的文件相关的

如何创建一个新的
git
存储库,该存储库仅包含
file2.c
subdir/file2\u extra.c
以及提交给它们的历史记录

请注意,我要分离的文件在单独的目录中找不到。否则,我认为可以使用
git子树

我尝试使用
git过滤器分支
,但没有成功。让我们假设原始存储库是git_original,我尝试的是

$ git clone git_original/ git_new
Cloning into 'git_new'...
done.
$ cd git_new
$ git rm file1.c
rm 'file1.c'
$ git filter-branch --prune-empty -- --all
Cannot rewrite branches: Your index contains uncommitted changes.
但是,如果我承诺删除
file1.c
,那么
git filter branch
就不会做任何事情。

基于(感谢@marekful提供此功能),我设计了此解决方案。其主要思想是将存储库克隆到一个新的存储库中,并在每次提交时消除不需要的文件。我假设有一个远程存储库,每个本地分支跟踪相应的远程分支

将旧存储库克隆到新存储库中

$ git clone git_original/ git_new
进入新的存储库

$ cd git_new
$ git remote rm origin
$ git remote add origin remote_origin_address
为新存储库中的每个所需分支设置一个分支

$ git branch -t branch_name origin/branch_name
删除新存储库中所有不需要的文件。例如,在问题的示例中,我想删除文件file1.c

$ git filter-branch -f --index-filter 'git rm --cached --ignore-unmatch file1.c' \
      --prune-empty -- --all
如果删除多个文件,则必须使用选项
-f
,因为它会强制覆盖“旧”引用

通过对新存储库的所有分支执行
git签出
,您可以检查不需要的文件是否确实已被删除

清理一下

$ git reflog expire --expire=now --all
$ git gc --prune=now --aggressive
现在,删除旧的源并与新的远程存储库关联

$ cd git_new
$ git remote rm origin
$ git remote add origin remote_origin_address
最后把所有东西都推到新的遥控器上

$ git push -u origin --all
$ git push -u origin --tags

您需要在
过滤器分支之前提交
git rm
@marekful请检查问题的最后一行。如果我提交了
gitrm
,那么我只会得到一个带有额外提交的存储库。我想去掉
file1.c
及其提交历史。
filter branch
仍将仅对提交到分支中的更改进行操作,因此,使用未提交的本地更改调用它是没有意义的,而且它无论如何都不允许这样做。您需要微调调用过滤器分支的方式。您可以在“运行筛选器分支”和“按名称删除文件”部分找到一些提示。@marekful非常感谢您提供的链接!据我所见,一个人在其他地方克隆了存储库,然后遍历所有需要的分支,删除不需要的文件。