Reject Large Files in Git Repositories while Pushing to Atlassian Stash Using the File Hooks Plugin

Git is a great tool for versioning and storing code but has its limitations with large files. Furthermore, large files increase clone and fetch times for all users of the repository.

In this post I would like to show some techniques how to deal with large files and how they can play together.

.gitignore file

The first solution is to add a .gitignore file. In short a .gitignore file allows you to specify which files and directories in your working directory are ignored by Git. Setting up a .gitignore file is highly recommended (https://www.gitignore.io/ is a nice little tool to generate a .gitignore file) and covers already many use cases. E.g. you can configure a .gitignore file which contains patterns for files which are known to be large, e.g. music, video files, etc. But there are use cases and situations where a .gitignore file is not enough and has its limitations such as

– There is no .gitignore configured
– A new file is added but not configured in the .gitignore
– The file in question is temporarily removed from the file
– It is a all or nothing approach, either you allow or ignore the file by its extension or not

– Users changes the file extension to bypass the .gitignore file

Git pre-receive hook

A second solution is to setup a Git pre-receive hook which checks the file size before the files are committed and rejects them if they exceed the configured size limit. This approach addresses some of the shortcomings of the first approach. E.g. it also works if there is no .gitignore file or if there is no pattern confgured. The problem which remains with this approach is that you developer needs to configure the pre-receive hook and can easily bypass it be temporarily remove the hook.

Server-Side Hook for Atlassian Stash

The first two techniques both rely on that they are configured properly by the developer on the local machine. If you are a user of Atlassian Stash you can configure server-side hooks for the Git repositories managed with Stash. Server-side hooks provide a mean for central management of rules and workflows for your development team.

As there was no plugin available for Stash I decided to developed the File Hook Plugin which provides a pre-receive hook that allows you to specify a file name pattern and size limit.

If commits in a push to Stash contain files which are larger then the specified file size the push is rejected.
The plugin is free and can be found at the Atlassian Marketplace.

Removing Large Files From Commits

In order to remove large from commits, checkout the following two articles

Conclusion

All mentioned techniques can be used in isolation or together. With .gitignore you can already address many use case. With having a local Git hook you can further control which files are added to your Git repository. If you need server-side control, e.g. in enterprises with central Git repositories then the File Hook Plugin for Atlassian Stash might be of interest for you.
Advertisements