2

我正在尝试编写一个提交后挂钩,我在映射驱动器 (V:) 上有一个 Git 存储库,msysgit 安装在 C:\Git 中,Python 安装在 C:\Python26 中。

我在 Windows 7 64 位上运行 TortoiseGit。

脚本是:

#!C:/Python26/python

import sys
from subprocess import Popen, PIPE, call

GIT_PATH = 'C:\Git\bin\git.exe'
BRANCHES = ['master']
TRAC_ENV = 'C:\TRAC_ENV'
REPO_NAME = 'core'

def call_git(command, args):
    return Popen([GIT_PATH, command] + args, stdout=PIPE).communicate()[0]

def handle_ref(old, new, ref):
    # If something else than the master branch (or whatever is contained by the
    # constant BRANCHES) was pushed, skip this ref.
    if not ref.startswith('refs/heads/') or ref[11:] not in BRANCHES:
        return

    # Get the list of hashs for commits in the changeset.
    args = (old == '0' * 40) and [new] or [new, '^' + old]
    pending_commits = call_git('rev-list', args).splitlines()[::-1]

    call(["trac-admin", TRAC_ENV, "changeset", "added", REPO_NAME] + pending_commits)

if __name__ == '__main__':
    for line in sys.stdin:
        handle_ref(*line.split())

如果我从命令行运行“git commit ...”命令,它似乎根本没有运行钩子脚本。

4

1 回答 1

2

根据githooks 手册页

[提交后挂钩] 由 git-commit 调用。它不带参数,并在提交后调用。

它不带任何参数。在 Python 中,这意味着 sys.argv[1:] 将是一个空列表。手册页没有说明将什么(如果有的话)发送到标准输入,但大概什么也没有。让我们检查一下。

我创建了一个小 git 目录并将其放在 .git/hooks/post-commit 中:

#!/usr/bin/env python 
import sys
def handle_ref(old, new, ref):
    with open('/tmp/out','w') as f:
        f.write(old,new,ref)
if __name__ == '__main__':
    with open('/tmp/out','w') as f:
        f.write('post-commit running')
    for line in sys.stdin:
        handle_ref(*line.split())
        with open('/tmp/out','w') as f:
            f.write('Got here')

并使其可执行。

当我提交时,我看到 /tmp/out 文件已创建,但它的唯一内容是

post-commit running

所以脚本运行了,但for line in sys.stdin:循环什么也不做,因为没有任何东西发送到 sys.stdin。

您将需要以handle_ref其他方式生成要发送到的参数,可能是通过对某个 git 命令的子进程调用。

于 2010-11-13T00:21:59.953 回答