php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #53619 ASSERT_BAIL seems to interfer with custom error-handling
Submitted: 2010-12-28 10:27 UTC Modified: 2020-03-31 13:43 UTC
From: thijsputman at gmail dot com Assigned: cmb (profile)
Status: Closed Package: Scripting Engine problem
PHP Version: 5.3.4 OS: Windows 7
Private report: No CVE-ID: None
Welcome back! If you're the original bug submitter, here's where you can edit the bug or add additional notes.
If you forgot your password, you can retrieve your password here.
Password:
Status:
Package:
Bug Type:
Summary:
From: thijsputman at gmail dot com
New email:
PHP Version: OS:

 

 [2010-12-28 10:27 UTC] thijsputman at gmail dot com
Description:
------------
I seem to have encountered an unexpected interaction between my custom error-handling setup and enabling the ASSERT_BAIL option.

The (simplified) situation is as follows:

* A custom error_handler() is defined and it "converts" all non-fatal PHP errors into ErrorException's.
* A custom assert_handler() is defined to display all failed assertions.
* The script in question has ASSERT_BAIL enabled and error reporting set to "E_ALL".

See the reproduce code for an example.

An assertion containing an E_NOTICE type error is constructed. When executed under the above conditions, execution halts the moment error_handler() throws its ErrorException.
When ASSERT_BAIL is disabled, the custom error_handler() throws its ErrorException which is "caught" by PHP and results in a fatal error.

I would assume ASSERT_BAIL to only bail if/when the assertion gets the chance to be handled. When the custom error_handler() is modified to _not_ throw an exception, but only provide some output, execution continues to assert_handler() after which ASSERT_BAIL is respected.

The above behaviour is somewhat "killing" in situations where the actual error_handler() does nothing but throw an exception and expects a further custom exception-handler to pick up the pieces. The situation as sketched above then simply generates no output.

Test script:
---------------
function error_handler($severity, $message, $file, $line){

	echo "Error: $message" . PHP_EOL;
	throw new ErrorException($message);
}

function assert_handler($file, $line, $expression){

	echo "Assertion failed: $expression" . PHP_EOL;
}

set_error_handler('error_handler', E_ALL);

assert_options(ASSERT_CALLBACK, 'assert_handler');
assert_options(ASSERT_BAIL, true);

assert('$foo instanceof Bar');

echo '*Not executed*' . PHP_EOL;

Expected result:
----------------
Error: Undefined variable: foo

Fatal error: Uncaught exception 'ErrorException' with message 'Undefined variable: foo' in ...

Actual result:
--------------
Error: Undefined variable: foo


For further reference, here's what happens if error_handler() is modified to _not_ throw an exception:

ASSERT_BAIL enabled:

Error: Undefined variable: foo (<- error_handler())
Assertion failed: $foo instanceof Bar (<- assert_handler())
Error: assert(): Assertion "$foo instanceof Bar" failed (<- ASSERT_WARNING)

ASSERT_BAIL disabled:

Error: Undefined variable: foo (<- error_handler())
Assertion failed: $foo instanceof Bar (<- assert_handler())
Error: assert(): Assertion "$foo instanceof Bar" failed (<- ASSERT_WARNING)
*Not executed*  (<- ASSERT_BAIL)

Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2020-03-31 13:43 UTC] cmb@php.net
-Status: Open +Status: Closed -Assigned To: +Assigned To: cmb
 [2020-03-31 13:43 UTC] cmb@php.net
Traditional assertions are superseeded by expectations, and the
usage of assert_options() is therefore discouraged.
 
PHP Copyright © 2001-2025 The PHP Group
All rights reserved.
Last updated: Thu Jul 03 11:01:34 2025 UTC