• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 3040
  • Last Modified:

Why do I get the error: post-commit hook failed (exit code 255) with no output.

I am getting the following error when I commit to a repository:

post-commit hook failed (exit code 255) with no output.

Open in new window


The post commit code is as follows:

@echo off

setlocal enableextensions

set REPOS=%1
set REV=%2
set TEMPFILE=C:\TEMP\%REV%.txt
set LOGFILE=D:\svn\logs\mysite\post_commit.log

set MANTIS_PATH="D:\home\mantis"

"C:\Program Files\SlikSvn\bin\svnlook" author %REPOS% -r %REV% >> %TEMPFILE% 2>>C:\TEMP\err.txt
"C:\Program Files\SlikSvn\bin\svnlook" date %REPOS% -r %REV% >> %TEMPFILE% 2>>C:\TEMP\err.txt
"C:\Program Files\SlikSvn\bin\svnlook" changed %REPOS% -r %REV% >> %TEMPFILE% 2>>C:\TEMP\err.txt
echo revision:[%REV%] >> %TEMPFILE% 2>>C:\TEMP\err.txt
"C:\Program Files\SlikSvn\bin\svnlook" log %REPOS% -r %REV% >> %TEMPFILE% 2>>C:\TEMP\err.txt

date /T >> %LOGFILE% 2>>C:\TEMP\err.txt
time /T >> %LOGFILE% 2>>C:\TEMP\err.txt
D:\wamp\bin\php\php5.3.0\php.exe %MANTIS_PATH%\scripts\checkin.php < %TEMPFILE% >> %LOGFILE% 2>>C:\TEMP\err.txt

Open in new window


- As you can see there is extensive error logging, but the error log never gets populated
- Both dev and live environments are Windows
- The line that seems to case the error is the final one - where PHP is called. When I take this out the commit works without issue

As you've probably made out, this is hooking up my SVN checkins with Mantis bug tracker. The interesting thing is that the PHP script is being executed, i.e. the notes are being added to bugs and the auto-closing of issues is working. It just seems to erroring for some reason. Mantis' checkin.php looks like this (some general comments removed for readability):

#!/usr/bin/php -q
<?php

global $g_bypass_headers;
$g_bypass_headers = 1;
require_once( dirname( dirname( __FILE__ ) ) . DIRECTORY_SEPARATOR . 'core.php' );

# Make sure this script doesn't run via the webserver
if( php_sapi_name() != 'cli' ) {
	echo "checkin.php is not allowed to run through the webserver.\n";
	exit( 1 );
}

# Check that the username is set and exists
$t_username = config_get( 'source_control_account' );
if( is_blank( $t_username ) || ( user_get_id_by_name( $t_username ) === false ) ) {
	echo "Invalid source control account ('$t_username').\n";
	exit( 1 );
}

if( !defined( "STDIN" ) ) {
	define( "STDIN", fopen( 'php://stdin', 'r' ) );
}

# Detect references to issues + concat all lines to have the comment log.
$t_commit_regexp = config_get( 'source_control_regexp' );
$t_commit_fixed_regexp = config_get( 'source_control_fixed_regexp' );

$t_comment = '';
$t_issues = array();
$t_fixed_issues = array();
while(( $t_line = fgets( STDIN, 1024 ) ) ) {
	$t_comment .= $t_line;
	if( preg_match_all( $t_commit_regexp, $t_line, $t_matches ) ) {
		$t_count = count( $t_matches[0] );
		for( $i = 0;$i < $t_count;++$i ) {
			$t_issues[] = $t_matches[1][$i];
		}
	}

	if( preg_match_all( $t_commit_fixed_regexp, $t_line, $t_matches ) ) {
		$t_count = count( $t_matches[0] );
		for( $i = 0;$i < $t_count;++$i ) {
			$t_fixed_issues[] = $t_matches[1][$i];
		}
	}
}

# If no issues found, then no work to do.
if(( count( $t_issues ) == 0 ) && ( count( $t_fixed_issues ) == 0 ) ) {
	echo "Comment does not reference any issues.\n";
	exit( 0 );
}

# Login as source control user
if( !auth_attempt_script_login( $t_username ) ) {
	echo "Unable to login\n";
	exit( 1 );
}

# history parameters are reserved for future use.
$t_history_old_value = '';
$t_history_new_value = '';

# add note to each bug only once
$t_issues = array_unique( $t_issues );
$t_fixed_issues = array_unique( $t_fixed_issues );

# Call the custom function to register the checkin on each issue.

foreach( $t_issues as $t_issue_id ) {
	if( !in_array( $t_issue_id, $t_fixed_issues ) ) {
		helper_call_custom_function( 'checkin', array( $t_issue_id, $t_comment, $t_history_old_value, $t_history_new_value, false ) );
	}
}

foreach( $t_fixed_issues as $t_issue_id ) {
	helper_call_custom_function( 'checkin', array( $t_issue_id, $t_comment, $t_history_old_value, $t_history_new_value, true ) );
}

exit( 0 );

Open in new window

0
LeonardChallis
Asked:
LeonardChallis
  • 4
  • 3
1 Solution
 
Brian UtterbackPrinciple Software EngineerCommented:
So to be clear, you get an error when you do a commit, and do not get the error if the call to php is removed, right? And with the call in place, the php
program seems to run okay, but you get the error, right? Are you sure that the php program runs to the end and does not get an error at some
point in the middle? If I recall correctly, SVN expects that if there is an error, the error message will be written to the stderr (standard error) output, not to
the stdout (standard output) file. In the php program, your errors are going to stdout, not stderr, so you may not see them.

0
 
LeonardChallisAuthor Commented:
@blu Thanks for that. I added this line to the top of my PHP file:

ini_set('display_errors', 'stderr');

Open in new window


Which did in fact show up an error (one of the included files was trying to use zlib compression, which wasn't enabled on that particular server), which I fixed, and now there are no PHP errors at all, but the problem still remains - I still get the hook error. Any more ideas?
0
 
Brian UtterbackPrinciple Software EngineerCommented:
Two things come to mind here. Either the php program is exiting with a non-zero return code (implying that the for loop exits pre-maturely). Or the windows batch program is not picking up the php return code and passing it on.

Add a line in the php script to output something to stderr between the for loop and the exit call. Then add a exit 0
call after the php program in the windows batch script.
0
What does it mean to be "Always On"?

Is your cloud always on? With an Always On cloud you won't have to worry about downtime for maintenance or software application code updates, ensuring that your bottom line isn't affected.

 
LeonardChallisAuthor Commented:
I instructed PHP to output to stderr instead (with the previously mentioned ini_set call. When I put
exit 0;

Open in new window

in the script, even before any other line of code (apart from the ini_set call) it still gives me the same, original error.
0
 
Brian UtterbackPrinciple Software EngineerCommented:
What I said was to add the exit 0 to the batch script, not the php script. It would appear that php is returning something other than 0 and the batch script is passing the return code up. Since it doesn't appear that you can easily get the php script to return 0, my thought was to override the php return code.
0
 
LeonardChallisAuthor Commented:
I was about to reply that it hadn't worked, when I tried one more thing. Very odd... maybe you can help?

When I added
EXIT 0

Open in new window

to the end, I still got the error. But when I added this:

echo "RAN." >> %LOGFILE% 2>>C:\TEMP\err.txt
EXIT 0

Open in new window


It works without error! No idea why! If you could explain why that'd be fantastic, but I will award you the points nevertheless. Thanks :)
0
 
Brian UtterbackPrinciple Software EngineerCommented:
I suspect that the echo command sets the error level, while the exit does not. I think that for the exit to work as you and I expected, you need to add the /B flag to it. Just guessing though.
0

Featured Post

Vote for the Most Valuable Expert

It’s time to recognize experts that go above and beyond with helpful solutions and engagement on site. Choose from the top experts in the Hall of Fame or on the right rail of your favorite topic page. Look for the blue “Nominate” button on their profile to vote.

  • 4
  • 3
Tackle projects and never again get stuck behind a technical roadblock.
Join Now