【问题标题】:How to get push notifications from a remote git repository in real time?如何实时从远程 git 存储库获取推送通知?
【发布时间】:2015-11-12 23:41:28
【问题描述】:

我有一个远程存储库 (bitbucket)、一个服务器存储库 (linux) 和许多本地存储库(开发人员)。

如果某些开发人员更改了远程分支,我希望服务器能够收到通知。

到目前为止,我尝试在服务器中使用 cron 中声明的 bash 脚本,但最小分辨率为 1 分钟,因此使其实时适应似乎非常棘手。但是,我的做法是这样的:

path=/some/dir/

# something new in remote
if git fetch origin && [ `git rev-list HEAD...origin/master --count` != 0 ]
then
    echo 'Remote repository has changed. Pull needed' &>>$path/git-backup.log
    echo $d >> $path/git-backup.log
    git merge origin/master &>>$path/git-backup.log
fi

【问题讨论】:

  • 您是否可以为您的 bitbucket 遥控器添加结帐后挂钩? git-scm.com/docs/githooks#_post_checkout
  • rev-list 测试之后,你有一个流浪的&&。此外,四个字 git fetch 通常不是很有用,因为它不会更新任何本地引用。如果您只想知道远程 ref 是否已更改,那么 git fetch origingit rev-list --count master..origin/master 应该会告诉您。 git diff --exit-code master origin/master 也应该可以工作,并且可以在没有 [ ... ] 包装的情况下使用。你也可以总是获取、合并和记录,不是吗?
  • 你是对的 goatshepard,解决方案是 git hooks (atlassian.com/git/tutorials/git-hooks/conceptual-overview)。在 bitbucket 中,这可以通过具有管理员权限的“Webhooks”来控制。就我而言,我正在服务器端安装一个应用程序来监听特定端口以便收到通知。完成后我会发布代码。

标签: bash cron bitbucket githooks


【解决方案1】:

终于解决了

在 bitbucket 端

您只需要声明一个指向服务器的 Webhook。

在服务器端

您需要一种始终监听某个端口的机制。这是一直在运行的 celery_listengit.py 的内容:

import subprocess
import threading
from tasks import git_pull
from flask import *

app = Flask(__name__)


@app.route("/", methods=['GET', 'POST'])
def listen_git4pull():

    # Range of bitbucket IP Addresses that we know.
    trusted = ['131.103.20', '165.254.145', '04.192.143']

    incoming = '.'.join(str(request.remote_addr).split('.')[:-1])
    if incoming in trusted:
        git_pull.delay()
        # OK
        resp = Response(status=200, mimetype='application/json')
    else:
        # HTTP not authorized
        resp = Response(status=403, mimetype='application/json')

    return resp


class CeleryThread(threading.Thread):
    def run(self):
        error_message = ('Something went wrong when trying to '
                         'start celery. Make sure it is '
                         'accessible to this script')
        command = ['celery',
                   '-A',
                   'tasks',
                   'worker',
                   '--loglevel=info']
        try:
            _ = subprocess.check_output(command)
        except Exception:
            raise Exception(error_message)


if __name__ == '__main__':
    celery_thread = CeleryThread()
    celery_thread.start()
    app.run(host='0.0.0.0')

这是任务的内容,其中声明了 git_pull() 函数。这必须延迟,因为 git.pull() 可能需要很长时间,所以它必须在服务器响应 HTPP OK 状态后运行:

from git import *
from celery.app.base import Celery


app = Celery('tasks',
             backend='amqp://guest@localhost//',
             broker='amqp://guest@localhost//')

app.conf.update(
    CELERY_ACCEPT_CONTENT=['json'],
    CELERY_TASK_SERIALIZER='json',
    CELERY_RESULT_SERIALIZER='json',)

@app.task
def git_pull():
    repo = Repo('.')
    o = repo.remotes.origin
    o.fetch()
    o.pull()

【讨论】:

    猜你喜欢
    • 2011-05-05
    • 2019-07-03
    • 2018-06-24
    • 2010-10-25
    • 1970-01-01
    • 2011-12-27
    • 2014-01-25
    • 1970-01-01
    相关资源
    最近更新 更多