Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

pre commit Hook for blocking commit larger than 20MB

Tags:

svn

hook

IS it possible to write prcommit hook for SVN 1.8 to avoid commiting files larger than ~20MB. Any suggestions would be appreciated. Thanks ! I tried this but this is not working for binary files or other file extensions

filesize=$($SVNLOOK cat -t $TXN $REPOS $f|wc -c)
if [ "$filesize" -gt "$MAX_SIZE"]
then
    echo "File $f is too large(must <=$MAX_SIZE)" >&2
    exit 1
fi
like image 386
Kaku Avatar asked Dec 26 '22 00:12

Kaku


2 Answers

You need to do two things here:

  • First use svn -t$TXN changed to get the paths that were changed in the transaction. You need to filter out directories which would be any line returned by svn changed that ends with a /.
  • For each entry from svn changed, you need to run svn -t$TXN filesize file against it. Then, sum up the file changes.

Something like this. This isn't tested, but should give you an idea:

total=0
svnlook -t $TXN changed | while read status file
do
    [[ status == "D" ]] && continue  # Ignore deletions
    [[ $file == */ ]] && continue    # Skip directories
    size=$(svnlook -t $TXN filesize $REPOS $file)
    ((total+=size))
done
if [[ $total -gt $maxsize ]]
then
    echo "Commit is too big!" >&2
    exit 1
else
    exit 0
fi

However, I don't like using shell for hook scripts. Instead, you should use a true scripting language like Python or Perl. They're simply easier to work with and are more powerful and flexible.

Why are you having to filter out these big commits? Are you getting developers trying to commit the executable they've just built?


Lazy badger pointed out that you're not talking about total commit size, but just a single file being that large. If this is the case, you'd do a similar hook, but without totaling:

svnlook -t $TXN changed | while read status file
do
    [[ $status == "D" ]] && continue  # Skip Deletions
    [[ $file == */ ]] && continue     # Skip directories
    size=$(svnlook -t $TXN filesize $REPOS $file)
    if [ $size -gt $maxsize ]]
    then
        echo "File '$file' too large to commit" >&2
        exit 2
    fi
done
exit 0
like image 130
David W. Avatar answered Jan 10 '23 05:01

David W.


Read svnlook help

Use svnlook changed + svnlook filesize

Explanation for sluggards

$SVNLOOK filesize -t $TXN $REPOS $f will "... print the size (in bytes) of the file located at $f".

Sample for test-repo's HEAD state

>svnlook filesize Repo trunk/ADExplorer.exe
479096

If you want to check every file in transaction in pre-commit hook, you have to:

Get list of all objects in transaction (svnlook changed -t ...)

>svnlook changed Repo
A   trunk/ADExplorer.exe
A   trunk/Hlp/
A   trunk/Hlp/AdExplorer.chm

Skip all non-file entities from list, because

>svnlook filesize Repo trunk/Hlp/
svnlook: E160017: Path 'trunk/Hlp' is not a file

Pass every object of pure file-list to svnlook filesize and test returned number

like image 26
Lazy Badger Avatar answered Jan 10 '23 05:01

Lazy Badger