Sometimes you have scripts in your repository that you need to mark as an executable so that they can be run in a docker container somewhere. Git tracks these file permission changes differently than typical file systems. It primarily pays attention to the executable bit; other bits (read/write for group/others) are not stored. Files are assigned modes such as 644 (read/write for owner, read-only for group and others) or 755 (executable by owner and readable/executable by group and others) (Git – git-config Documentation).
Managing the Executable Bit
To mark a file as executable in Git, you can use either your operating system’s chmod command or Git’s own index update. For example, git update-index --chmod=+x <file> adds the executable bit, while git update-index --chmod=-x <file> removes it. After changing the permissions, stage and commit the file so that the change is tracked.
Ignoring Permission Changes
Sometimes permission changes can clutter your diffs, particularly when collaborating across different operating systems. Git has a configuration option core.fileMode that tells Git whether to consider file mode changes when determining if a file has been modified. Setting this option to false globally will ignore permission changes for all repositories:
git config --global core.fileMode false
Alternatively, you can set it per repository:
git config core.fileMode false
This option instructs Git to ignore differences in file modes when comparing revisions (How Do I Make Git Ignore File Mode (Chmod) Changes?). Be careful: ignoring modes might hide meaningful permission changes in projects where the executable bit matters. Document the configuration in your project’s README and consider enabling it only for specific repositories.
My Git Tool is Ignoring Permission Only Changes
Your situation maybe such that the configuration mentioned above is set in such a way that it is ignoring permission changes. And any git tools that you are using (e.g., GitHub Desktop) maybe looking at that configuration and not staging your files accordingly. You can manually force the staging of your file:
git add --chmox=+x .\my-executable-script.sh
Best Practices
- Use the OS-level
chmodcommand to set the correct permissions before adding files to Git. - Use
git update-index --chmodto ensure the executable bit is tracked correctly across clones. - Use
git ls-files -s <file>to inspect a file’s mode in the index. - Be cautious with
core.fileMode=false; avoid using it if your project relies on executable scripts.
Conclusion
Handling file permissions in Git boils down to managing the executable bit and knowing when to ignore changes. By understanding how Git tracks file modes and using configuration options wisely, you can avoid common pitfalls and keep your repository history clean.
