预推

适用于 Git 1.8.2 及更高版本。

Version >= 1.8

可以使用预推钩来防止推动。这有用的原因包括:阻止意外手动推送到特定分支,或者如果已建立的检查失败则阻止推送(单元测试,语法)。

只需在 .git/hooks/下创建一个名为 pre-push 的文件和(gotcha alert ) 创建一个预推钩,确保该文件是可执行的:chmod +x ./git/hooks/pre-push

以下是汉娜·沃尔夫Hannah Wolfe)阻止推动掌握的一个例子 :

#!/bin/bash

protected_branch='master'  
current_branch=$(git symbolic-ref HEAD | sed -e 's,.*/\(.*\),\1,')

if [ $protected_branch = $current_branch ]  
then  
    read -p "You're about to push master, is that what you intended? [y|n] " -n 1 -r < /dev/tty
    echo
    if echo $REPLY | grep -E '^[Yy]$' > /dev/null
    then
        exit 0 # push will execute
    fi
    exit 1 # push will not execute
else  
    exit 0 # push will execute
fi  

这是 Volkan Unsal 的一个例子,它确保 RSpec 测试在允许推送之前通过:

#!/usr/bin/env ruby
require 'pty'
html_path = "rspec_results.html"
begin
  PTY.spawn( "rspec spec --format h > rspec_results.html" ) do |stdin, stdout, pid|
  begin
    stdin.each { |line| print line }
  rescue Errno::EIO
  end
end
rescue PTY::ChildExited
  puts "Child process exit!"
end

# find out if there were any errors  
html = open(html_path).read
examples = html.match(/(\d+) examples/)[0].to_i rescue 0
errors = html.match(/(\d+) errors/)[0].to_i rescue 0
if errors == 0 then
  errors = html.match(/(\d+) failure/)[0].to_i rescue 0
end
pending = html.match(/(\d+) pending/)[0].to_i rescue 0

if errors.zero?
  puts "0 failed! #{examples} run, #{pending} pending"
  # HTML Output when tests ran successfully:
  # puts "View spec results at #{File.expand_path(html_path)}"
  sleep 1
  exit 0
else
  puts "\aCOMMIT FAILED!!"
  puts "View your rspec results at #{File.expand_path(html_path)}"
  puts
  puts "#{errors} failed! #{examples} run, #{pending} pending"
  # Open HTML Ooutput when tests failed
  # `open #{html_path}`
  exit 1
end

正如你所看到的,有很多可能性,但核心部分是如果好事发生的话,那就是发生了坏事。任何时候你都可以防止推送,你的代码将处于运行 git push... 之前的状态。

使用客户端挂钩时,请记住,用户可以通过在推送时使用选项“–no-verify”来跳过所有客户端挂钩。如果你依赖钩子来强制执行流程,那么你可能会被烧毁。

文档: https//git-scm.com/docs/githooks#_pre_push
官方样本: https//github.com/git/git/blob/87c86dd14abe8db7d00b0df5661ef8cf147a72a3/templates/hooks–pre-push.sample