0

I have a large project that I'm working on as part of a team of 10 developers, and there are several configuration files and other settings-related files that need to be different for every one of us.

I know the obvious solution to this is to not source control those files at all, either by adding them to .gitignore files or by adding them to <project root dir>/.git/info/exclude.

The problems with those approaches are:

  1. The files are already in source control, which means .git/info/exclude won't work.
  2. My teammates refuse to introduce .gitignore files, for various reasons that I won't bore you with.

So after some research I came across the git update-index command and its --assume-unchanged option, which seemed perfect for my use case. I now have the troublesome files marked with that, and also have a post-checkout hook that copies my own local copies of the files from an external directory, into the correct places every time I checkout.

This mostly works, and has the following benefits:

  1. My settings are always correct for my local dev environment.
  2. The Git changes window in Visual Studio remains clear of those files, meaning that I can't accidentally forget to not stage them before a commit (I'm used to always staging and committing everything in one fell swoop).

The only problem is that sometimes, for some strange reason completely beyond my understanding, git seems to "forget" that I have explicitly told it to ignore those files, resulting in the following:

  1. Make some changes to files that I eventually want to commit.
  2. The boss comes along and says "this critical bug has just popped up, drop everything and fix it immediately!" so I git stash, git checkout master and attempt to git pull1.
  3. Git tells me error: Your local changes to the following files would be overwritten by merge: <list of files>.
  4. After swearing at and bashing the keyboard for 5 minutes, I realise that I need to git update-index --no-assume-unchanged <list of files>, then git checkout -- <list of files>, then git pull, then finally git checkout -b new-bugfix-branch1.

So why does this happen, and is there a better way to achieve the results mentioned above? MTIA :-)

1: Running these commands is not how I actually do things; as hinted at before I use the Git Changes window to do almost-everything Git-related, and only resort to full terminal commands when absolutely necessary. But the actions that I would take in said UI are equivalent to the commands given.

Kenny83
  • 769
  • 12
  • 38
  • Not seeing what this question has to do with C# or ASP.NET MVC. The fact that that's what your project is not inherently relevant if your question would be the same for a different project. Please remove any irrelevant tags or indicate in the question exactly how they are relevant. Otherwise, it seems like you're trying to trick people into viewing a question that isn't really relevant tot hem. – jmcilhinney Jun 28 '23 at 08:36
  • Just curious.... when that happens, are there changes coming for the files that are assumed to be unchanged? – eftshift0 Jun 28 '23 at 08:43
  • Maybe because you must have used `skip-worktree` instead of `assume-unchaged` See https://stackoverflow.com/a/13631525/717372 – Philippe Jun 28 '23 at 09:03
  • 1
    Sorry @jmcilhinney, removed those tags as requested :-) I just want to say that I wasn't trying to trick anyone though, just thought there would be no harm in adding some more context, although I realised you were right as soon as I read your comment. – Kenny83 Jun 28 '23 at 22:07
  • @eftshift0 Those files usually don't change...sometimes but very rarely. The only "changes" are between my versions and the source controlled versions. – Kenny83 Jun 28 '23 at 22:08
  • @Philippe Do you mean that I *should* use `skip-worktree`? Because it sounds like you're suggesting that I *have* used that command instead of `update-index`, which is not the case. I did see some talk on SO and other places about the two different commands and when to use which one, but I really feel that `update-index --assume-unchanged` should work better in my use case. – Kenny83 Jun 28 '23 at 22:19
  • @Kenny83 the 2 are very similar and a pain to use. Normally we try to find another way to fix this problem. I just say that you use a feature that is not for that (it's for perf) whereas there is another command for your exact use case so it advice you to use it instead. – Philippe Jun 28 '23 at 22:51
  • @Phillipe "...very similar and a pain to use" LOL yeah I feel you, it is a very convoluted solution that I have set up and every time I noticed another settings file that needed to be ignored it took me like 5 mins to set up the `post-checkout` hook and the `assume-unchanged` bit again. That doesn't sound like a lot but when you're individually making those changes for many files, it becomes tedious and annoying pretty quickly! Anyway thanks for your comments :-) If you want to write up a proper answer I'll gladly accept it. – Kenny83 Jun 28 '23 at 23:33
  • "My teammates refuse to introduce `.gitignore` files, for various reasons that I won't bore you with."—"How can I change gears without using the clutch or ever damaging the gearbox?" "How can I throw a fastball if I cut off my index and middle fingers?" "Of what use is a phone call if you are unable to speak?"—your teammates are actively attempting to sabotage Git. – jthill Jul 21 '23 at 23:14
  • @jthill LOL I don't know about "sabotaging Git"...they're just head strong (show me a programmer who isn't and I'll eat my hat lol :-P) and like to do things "their way". Which is kinda arrogant, I know, but I also think that it would be arrogant of the Git devs to expect every user to explicitly obey every single "rule". If something is not possible due to the way Git is designed, fair enough, just say so. But you don't need to insult my colleagues, or insinuate that they're doing something horrible. – Kenny83 Jul 31 '23 at 05:57
  • They're trying to make Git stop and refusing to use the brake. Make of it what you will. – jthill Jul 31 '23 at 06:07

2 Answers2

1

just use this command for remove ignored file from cache

git rm --cached -r  FilePath

or you can remove all cache with this code next commit again

git rm --cached -r .

Warning

In second way other developer loss their files in pulling

First way is safer and better

mamad2559
  • 158
  • 2
  • 15
1

Git doesn't support ignoring tracked files. The Git FAQ says this:

Git doesn't provide a way to do this. The reason is that if Git needs to overwrite this file, such as during a checkout, it doesn’t know whether the changes to the file are precious and should be kept, or whether they are irrelevant and can safely be destroyed. Therefore, it has to take the safe route and always preserve them.

This is the problem you're seeing. The FAQ continues:

It's tempting to try to use certain features of git update-index, namely the assume-unchanged and skip-worktree bits, but these don't work properly for this purpose and shouldn't be used this way.

However, it goes on to provide an example of what to do:

If your goal is to modify a configuration file, it can often be helpful to have a file checked into the repository which is a template or set of defaults which can then be copied alongside and modified as appropriate. This second, modified file is usually ignored to prevent accidentally committing it.

bk2204
  • 64,793
  • 6
  • 84
  • 100
  • Thanks for the info and the suggestion, but this still doesn't save me from having to change my colleagues' opinions about `.gitignore` files :-( It sucks that there's no way to say "hey guess what Git? You don't always know what's best for everybody, and I'm telling you right here, right now, **it is always safe** to ignore these already-tracked files, even though my colleagues don't think so". I totally agree that this is the best solution available though. – Kenny83 Jun 29 '23 at 04:13