#!/usr/bin/php <?php // // This is called by 'update' hook // Inspired by update.sample in git package // TODO: what we receive when a tag will be created? // error_reporting(E_ALL); ini_set("track_errors", "On"); $_start = microtime(TRUE); require_once("/etc/rocketgit/config.php"); $INC = $rg_scripts . "/inc"; require_once($INC . "/util.inc.php"); require_once($INC . "/log.inc.php"); require_once($INC . "/sql.inc.php"); require_once($INC . "/repo.inc.php"); rg_log_set_file("/var/log/rocketgit/hook_update.log"); $uid = @sprintf("%u", getenv("ROCKETGIT_UID")); $rights = getenv("ROCKETGIT_RIGHTS"); rg_log("Start uid=$uid, rights=[$rights]..."); rg_log("_SERVER: " . print_r($_SERVER, TRUE)); umask(0022); $refname = @rg_git_reference($_SERVER['argv'][1]); $old_rev = rg_git_rev(@$_SERVER['argv'][2]); $new_rev = rg_git_rev(@$_SERVER['argv'][3]); rg_log("refname=$refname old_rev=$old_rev new_rev=$new_rev."); if (empty($refname) || empty($old_rev) || empty($new_rev)) rg_fatal("Invalid parameters [$refname $old_rev $new_rev]!"); if (strcmp($new_rev, $rg_git_zero) == 0) $new_rev_type = "delete"; else $new_rev_type = rg_git_type($new_rev); rg_log("new_rev_type=$new_rev_type."); if (strcmp($new_rev_type, "commit") == 0) { rg_log("It's a commit..."); if (strcmp($old_rev, $rg_git_zero) != 0) { rg_log("This is a reference update..."); // check non fast-forward update if (!rg_rights_allow($rights, "O")) { $merge_base = rg_git_merge_base($old_rev, $new_rev); if ($merge_base === FALSE) { rg_log("Error: " . rg_git_error()); rg_fatal("Internal error! Try again later!"); } if (strcmp($merge_base, $old_rev) != 0) rg_fatal("Non fast-forward is not allowed for $refname!"); } } if (strncmp($refname, "refs/tags/", 10) == 0) { rg_log("Un-annotated tag..."); if (strcmp($old_rev, $rg_git_zero) == 0) { if (!rg_rights_allow($rights, "Y")) rg_fatal("No rights to create an un-annotated tag!"); } else { //change if (!rg_rights_allow($rights, "U")) rg_fatal("No rights to change an un-annotated tag!"); } } else if (strncmp($refname, "refs/heads/", 11) == 0) { if (strcmp($old_rev, $rg_git_zero) == 0) { rg_log("Creating a branch..."); if (!rg_rights_allow($rights, "C")) rg_fatal("You have no rights to create a branch!"); } else if (rg_git_rev_ok($new_rev . "^2")) { rg_log("Merge commit..."); if (!rg_rights_allow($rights, "M")) rg_fatal("You have no rights to push merge commits!"); } else { rg_log("Normal commit..."); if (!rg_rights_allow($rights, "W")) { if (!rg_git_whitespace_ok($old_rev, $new_rev)) rg_fatal("Bad whitespace is not allowed!"); } } } else { rg_fatal("Unknown refname provided!"); } // TODO: refs/remotes/* } else if (strcmp($new_rev_type, "delete") == 0) { rg_log("It's a delete..."); if (strncmp($refname, "refs/tags/", 10) == 0) { rg_log("Deleting an un-annotated tag..."); if (!rg_rights_allow($rights, "u")) rg_fatal("You have no rights to delete a tag!"); } else if (strncmp($refname, "refs/heads/", 11) == 0) { rg_log("Deleting a branch..."); if (!rg_rights_allow($rights, "D")) rg_fatal("You have no rights to delete a branch!"); } else if (strncmp($refname, "refs/remotes/", 13) == 0) { rg_log("Deleting a tracking branch..."); if (!rg_rights_allow($rights, "D")) rg_fatal("You have no rights to delete a tracking branch!"); } } else if (strcmp($new_rev_type, "tag") == 0) { rg_log("It's an annotated tag..."); if (strncmp($refname, "refs/tags/", 10) == 0) { rg_log("Modify tag..."); if (!rg_rights_allow($rights, "S")) rg_fatal("You have no rights to modify a tag!"); } } else { rg_log("Invalid new_rev type!"); rg_fatal("Internal error!"); } $diff = sprintf("%u", (microtime(TRUE) - $_start) * 1000); rg_log("Took " . $diff . "ms."); @file_put_contents($repo_path . "/rg/hook-update", "repo: " . $repo . " ($repo_path)" . "\nat: " . sprintf("%u", $_start) . "\nuid: " . $uid . "\npara: $refname $old_rev $new_rev" . "\nTook: " . $diff . "ms" . "\n_SERVER: " . print_r($_SERVER, TRUE)); ?>