首页 文章

使用GitHub时,防止将大文本文件添加到提交中

提问于
浏览
2

我们想要阻止:

  • 非常大的文本文件(每个文件大于50MB)被提交到 git 而不是 git-lfs ,因为它们会膨胀git历史记录 .

  • 问题是,其中99%<1MB,应该承诺更好地进行差异化 .

  • 大小不一致的原因:这些是YAML文件,它们通过base64编码支持二进制序列化 .

  • 我们无法可靠地防止二进制序列化的原因:这是一个Unity项目,由于各种原因需要二进制序列化 .

鉴于:

  • GitHub托管缺乏预接收挂钩支持 .

  • git-lfs缺少文件大小属性支持 .

问题:

  • 如何可靠地防止大文件被添加到提交?

  • 这可以通过repo中的配置文件完成,这样所有用户都可以优雅地遵循此规则吗?

  • 如果没有,可以通过bash命令别名来完成这一点,这样可信用户在意外 git add 一个大文件并且 git-lfs 不处理时会看到警告消息?

(我们的环境是macOS . 我已经看了很多解决方案,到目前为止还没有满足我们的需求)

2 回答

  • 0

    好吧,在CodeWizard和this SO answer的帮助下,我设法自己创建了一个很好的指南:

    首先,设置你的repo core.hooksPath

    git config core.hooksPath .githooks
    

    其次,在 .githooks 文件夹中创建这个 pre-commit 文件,这样就可以跟踪它(gist link),然后记得用 chmod +x 赋予它执行权限 .

    #!/bin/sh
    #
    # An example hook script to verify what is about to be committed.
    # Called by "git commit" with no arguments. The hook should
    # exit with non-zero status after issuing an appropriate message if
    # it wants to stop the commit.
    #
    # To enable this hook, rename this file to "pre-commit".
    
    # Redirect output to stderr.
    exec 1>&2
    
    FILE_SIZE_LIMIT_KB=1024
    CURRENT_DIR="$(pwd)"
    COLOR='\033[01;33m'
    NOCOLOR='\033[0m'
    HAS_ERROR=""
    COUNTER=0
    
    # generate file extension filter from gitattributes for git-lfs tracked files
    filter=$(cat .gitattributes | grep filter=lfs | awk '{printf "-e .%s$ ", $1}')
    
    # before git commit, check non git-lfs tracked files to limit size
    files=$(git diff --cached --name-only | sort | uniq | grep -v $filter)
    while read -r file; do
        if [ "$file" = "" ]; then
            continue
        fi
        file_path=$CURRENT_DIR/$file
        file_size=$(ls -l "$file_path" | awk '{print $5}')
        file_size_kb=$((file_size / 1024))
        if [ "$file_size_kb" -ge "$FILE_SIZE_LIMIT_KB" ]; then
            echo "${COLOR}${file}${NOCOLOR} has size ${file_size_kb}KB, over commit limit ${FILE_SIZE_LIMIT_KB}KB."
            HAS_ERROR="YES"
            ((COUNTER++))
        fi
    done <<< "$files"
    
    # exit with error if any non-lfs tracked files are over file size limit
    if [ "$HAS_ERROR" != "" ]; then
        echo "$COUNTER files are larger than permitted, please fix them before commit" >&2
        exit 1
    fi
    
    exit 0
    

    现在,假设您正确设置 .gitattributesgit-lfs ,当您尝试 git commit 并确保git-lfs未跟踪的所有暂存文件(在 .gitattributes 中指定)时,此预提交挂钩将运行,将满足指定的文件大小限制 .

    您的仓库的任何新用户都需要自己设置 core.hooksPath ,但除此之外,事情应该可行 .

    希望这有助于其他Unity开发人员与不断增长的git repo大小抗争!

  • 1

    我们如何可靠地防止大文件被添加到提交?这可以通过repo中的配置文件来完成,这样所有用户都可以优雅地遵循此规则吗?由于GitHub不支持服务器端挂钩,因此可以使用客户端挂钩 . 正如您可能知道的那样,这些挂钩可以通过并且没有问题地被禁用,但是,这仍然是一种很好的方法 .


    core.hooksPath

    Git v2.9 添加了在远程文件夹上设置客户端挂钩的功能 . 在此之前,钩子必须放在 .git 文件夹中 .

    这将允许您编写脚本并将它们放在任何地方 . 我假设你知道什么是钩子,但如果没有随意问 .


    怎么做?

    通常,您将钩子放在repo(或任何其他常见文件夹)中 .

    # set the hooks path. for git config, the default location is --local
    # so this configuration is locally per project
    git config core.hooksPath .githooks
    

相关问题