Remove a directory from all previous commits

前端 未结 2 1705
忘掉有多难
忘掉有多难 2021-01-30 23:56

Git Repo, there is a folder ABC with three files, all having spaces in the name file - 1.ext, file - 2.ext, and file - 3.ext.

相关标签:
2条回答
  • 2021-01-31 00:33

    Instead of using --index-filter, try with --tree-filter:

    --tree-filter <command>
        This is the filter for rewriting the tree and its contents. The argument is
        evaluated in shell with the working directory set to the root of the
        checked out tree. The new tree is then used as-is
        (new files are auto-added, disappeared files are auto-removed -
        neither .gitignore files nor any other ignore rules HAVE ANY EFFECT!).
    

    The commandline:

    git filter-branch --tree-filter 'rm -rf path/to/ABC' \
      --prune-empty --tag-name-filter cat -- --all
    
    0 讨论(0)
  • 2021-01-31 00:46

    Say you begin with a history of

    $ git lola --name-status
    * e709131 (HEAD, master) bar
    | A     bar
    * 61493ac ABC/file - 3.ext
    | A     ABC/file - 3.ext
    * 34cce9e ABC/file - 2.ext
    | A     ABC/file - 2.ext
    * 115e6d5 ABC/file - 1.ext
    | A     ABC/file - 1.ext
    * 5ea5b42 foo
      A     foo

    Note: git lola is a non-standard but highly useful alias.

    git rm supports an option for removing subtrees.

    -r
    Allow recursive removal when a leading directory name is given.

    After running

    $ git filter-branch --index-filter 'git rm --cached -r --ignore-unmatch ABC' \
      --prune-empty --tag-name-filter cat -- --all

    you will see output that resembles

    Rewrite 115e6d5cd06565ca08f1e5c98c4b91246cf59fa1 (2/5)rm 'ABC/file - 1.ext'
    Rewrite 34cce9e90f832460137e620ebacc8a73a99e64ce (3/5)rm 'ABC/file - 1.ext'
    rm 'ABC/file - 2.ext'
    Rewrite 61493ac3211808f34f616dbc33d51d193b3f45a3 (4/5)rm 'ABC/file - 1.ext'
    rm 'ABC/file - 2.ext'
    rm 'ABC/file - 3.ext'
    Rewrite e709131f1fe6103adf37616c9fa500994aeb30d0 (5/5)rm 'ABC/file - 1.ext'
    rm 'ABC/file - 2.ext'
    rm 'ABC/file - 3.ext'
    
    Ref 'refs/heads/master' was rewritten

    If you are happy with the result, delete the old master with

    $ git update-ref -d refs/original/refs/heads/master

    and now you have a history of

    $ git lola --name-status
    * 19680d4 (HEAD, master) bar
    | A     bar
    * 5ea5b42 foo
      A     foo

    To answer your second question, say you wanted to delete ABC/file - 2.ext only. Remember that you will need two layers of quoting: one layer for the whole command and another to escape spaces in an argument to that command, the name of the file to remove.

    One way to do that is

    $ git filter-branch --index-filter \
      'git rm --cached --ignore-unmatch "ABC/file - 2.ext"' --prune-empty \
      --tag-name-filter cat -- --all

    Note the double quotes inside the single quotes.

    If you had run this command instead, your history would have become

    $ git lola
    * a8d1b0d (HEAD, master) bar
    * cff0c4e ABC/file - 3.ext
    * 115e6d5 ABC/file - 1.ext
    * 5ea5b42 foo
    0 讨论(0)
提交回复
热议问题