Klemart3D
Klemart3D

Reputation: 338

How can I add to Git only files with new mode?

Git can track the mode of files (like 755 or 644). I did a global update of chmod of all my working files but only some of them had a bad chmod. Now I have a mix of updated files : some with new code I updated before and others with only a new mode. How can I add to Git only files that have a new mode?

In the Git documentation I have found a chmod option but I'm not sure if it useful in my case.

Upvotes: 1

Views: 234

Answers (2)

torek
torek

Reputation: 487725

The easy answer, except on some Windows systems, is just to use git add . from the top level of the work-tree, or git add -u. Re-adding an already added file is harmless; re-adding an existing file also picks up its new mode setting.

More about the index / staging-area

As an exercise, run the command:

git ls-files --stage

on an existing repository that has a bunch of files checked out. (This prints a lot of output in a big repository, and does not use a pager by default, so you might want to add | page or | less or whatever you do for paging.)

The result of this listing tells you all the files that will be in the next commit you make. If you run git commit right after this git ls-files command, you'll get a new commit containing exactly the set of files listed by git ls-files, with the mode information being that shown by --stage (as the first column).

Compare the output to that from git status:

$ git ls-files --stage | wc -l
    3606

There are more than three thousand six hundred files staged for commit! But:

$ git status
On branch master
Your branch is up to date with 'origin/master'.

nothing to commit, working tree clean

Why are these different? Why does git status report that there is nothing staged, when git ls-files reports 3606 staged files?

The answer is that the current commit—the tip of master—has the same 3606 files:

$ git ls-tree -r HEAD | wc -l
    3606

Moreover, the 3606 files in the HEAD commit are the same—mode, size, and bytes-of-data—as the 3606 files in the index / staging-area. So git status, which compares these two, says that none of them are different and there is nothing to commit.

If you change one file in the index / staging-area—by changing the copy that's in the work-tree, or even by just changing the mode—there will still be 3606 files in the staging area, but this time, one will be different. The git ls-files command will list all 3606; the git status command will list the different files. Which of these is more useful in every-day work?

The index / staging-area holds a copy of every file, ready to go into the next commit. This is where the mode—always 100755 or 100644—comes from, too. Whatever is in the index / staging-area, that's what gets committed when you run git commit. The reason you have to run git add is to tell Git: Update the index copy from the work-tree copy.

Upvotes: 0

A. M.
A. M.

Reputation: 394

You could change the mode of all your files, and do a git add . Since git tracks only what's changed, it will only add those files whose mode has changed.

Note that this works on filesystems that correctly track the executable bit (the only mode tracked by git). On windows you might need to use the --chmod option you linked.

Upvotes: 1

Related Questions