简体   繁体   中英

How to remove a file named .css from all branches in git

I am working with a git repository that somehow has a file named .css in it. This causes an error when checking out in Windows (but in Linux it works fine).

How do I remove this file from all branches in git , without accidentally removing all css files from all branches?

Here's how you can do it for a single branch, since "all branches" is rather ambiguous, I left the automation/iteration part over all branches for you to do how you prefer (I suggest doing it manually if you don't have too many branches that have this problematic file)

# First checkout the branch - WARNING - Note I use
# --force here to make sure `git status` is clean. 
# I'm relying on it later when doing `git add -A`.
# The --force flag will delete any uncommited local changes,
# so make sure you don't have any of those before running
# the following command
git checkout --force my_branch

# Now delete the `*.css` file. Note the single quotes, they
# are crucial to prevent the shell from doing expansion on the asterisk:
rm -- '*.css'

# Add "all" the changes (The deletion of the file should be the only change):
git add -A

# Now commit
git commit -m 'Removed evil *.css file'

# And push
git push origin my_branch

I didn't use git rm (which combines deletion and git add in one command) on purpose because I couldn't get it to ignore the * as a character, it tried to get smart and delete all .css files in the project. EDIT: See torek's answer for a way to specify literal asterisks in git commands

How do I remove this file from all branches in git, without accidentally removing all css files from all branches?

Omer's answer shows one way; here is another.

Note: you aren't removing the file from branches . You are making new commits that lack the file , which each new commit made on some particular branch. This is an important distinction because the existing commits continue to exist, and continue to have the file. No existing commit can ever be altered! You simply stop using those commits. But as long as you still have those earlier commits, any attempt to extract one of them on Windows will give you the same sort of heartburn. 1

To make a new commit on a branch, we will (of course) use git commit as usual. To get on some particular branch, we will use git checkout or git switch as usual. As in Omer's answer, it's important to be sure that you are starting from a clean setup, though I won't show any particular method for guaranteeing that here.

Given a list of branches that do have the file whose name is literally *.css , we now want a loop, written in whatever scripting language you prefer. Since Git includes sh (or bash) and that's a nice powerful scripting language, that's the one I would use here:

for name in br1 br2 br3 master; do
    git checkout $name &&
    git rm -f -- ":(literal)*.css" &&
    git commit -m "remove file named *.css" ||
    echo "failed to update branch $name"
done

The :(literal) prefix is part of a pathspec and prevents git rm from expanding *.css to match all the .css files. This is documented in the gitglossary , albeit rather well-hidden. (The -f flag here allows the git rm even on Windows, though on Windows the git checkout step would probably fail so you'd have to modify the && chain. If you are doing this on a Linux system you don't need the -f flag here.)

You can follow this up with a single git push of all the branches in question:

git push origin br1 br2 br3 master

for instance.


1 It is possible to "rewrite history" in a Git repository so as to not merely stop using a commit, but also stop keeping it in the repository at all. The downside to doing this is that every subsequent commit's commit-number (hash-ID) also changes, such that the new repository can never be mixed with the original repository: if it is mixed together, all the old commits come right back. This is sometimes, but not all that often, worth the pain it takes to achieve. The amount of pain depends on the number and importance of copies of the repository that exist and have the original commits, pre-rewrite.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM