4

我正在尝试调试 Mercurial 扩展。此扩展添加了一些在执行 a 时应执行的代码pull。原作者通过更改存储库对象的类来设置此挂钩。

以下是相关代码(实际上是有效的 Mercurial 扩展):

def reposetup(ui, repo):
    class myrepo(repo.__class__):
        def pull(self, remote, heads=None, force=False):
            print "pull called"
            return super(myrepo, self).pull(remote, heads, force)

    print "reposetup called"
    if repo.local():
        print "repo is local"
        repo.__class__ = myrepo

当我在hg pull启用此扩展程序的情况下执行时,输出如下:

# hg pull
reposetup called
repo is local
pulling from ssh://hgbox/myrepo
reposetup called
searching for changes
no changes found

这是在pull命令中注入扩展代码的合理方式吗?为什么从未达到“拉动”声明?

我在 Windows 7 上使用 Mercurial 3.4.1 和 python 2.7.5。

4

1 回答 1

5

根据代码(mercurial/extensions.py),这是扩展存储库对象的唯一合理方法(https://www.mercurial-scm.org/repo/hg/file/ff5172c83002/mercurial/extensions.py#l227)。

但是,我查看了代码,此时localrepo对象似乎没有pull方法,所以我怀疑这就是为什么你的“拉调用”打印语句从未出现的原因——没有任何调用它,因为它不应该存在!

根据您要完成的工作,有更好的方法可以将代码注入到 pull 中。例如,如果您只想在发出 pull 时运行某些东西,则更喜欢包装 exchange.pull 函数:

extensions.wrapfunction(exchange, 'pull', my_pull_function)

对于您的特定用例,我建议使用以下代码创建一个方法:

def expull(orig, repo, remote, *args, **kwargs):
    transferprojrc(repo.ui, repo, remote)
    return orig(repo, remote, *args, **kwargs)

在 extsetup 方法中,添加如下一行:

extensions.wrapfunction(exchange, 'pull', expull)

最后,在 reposetup 方法中,您可以完全删除 projrcrepo 类的东西。希望这会让你得到你正在寻找的行为。

于 2015-06-24T19:01:10.833 回答