2011-03-05 19:23:35 +00:00
< ? php
/*
* This file is part of the Symfony package .
*
2011-03-06 11:40:06 +00:00
* ( c ) Fabien Potencier < fabien @ symfony . com >
2011-03-05 19:23:35 +00:00
*
* For the full copyright and license information , please view the LICENSE
* file that was distributed with this source code .
*/
2013-03-20 17:09:46 +00:00
namespace Symfony\Component\Debug\Tests ;
2011-03-05 19:23:35 +00:00
2013-03-20 17:09:46 +00:00
use Symfony\Component\Debug\ErrorHandler ;
2014-04-17 08:44:42 +01:00
use Symfony\Component\Debug\Exception\HandledErrorException ;
2011-03-05 19:23:35 +00:00
/**
* ErrorHandlerTest
*
* @ author Robert Schönthal < seroscho @ googlemail . com >
*/
class ErrorHandlerTest extends \PHPUnit_Framework_TestCase
{
2013-11-05 20:12:21 +00:00
/**
* @ var int Error reporting level before running tests .
*/
protected $errorReporting ;
/**
* @ var string Display errors setting before running tests .
*/
protected $displayErrors ;
2013-12-12 16:08:59 +00:00
public function setUp ()
{
2013-11-05 20:12:21 +00:00
$this -> errorReporting = error_reporting ( E_ALL | E_STRICT );
$this -> displayErrors = ini_get ( 'display_errors' );
ini_set ( 'display_errors' , '1' );
}
2013-12-12 16:08:59 +00:00
public function tearDown ()
{
2013-11-05 20:12:21 +00:00
ini_set ( 'display_errors' , $this -> displayErrors );
error_reporting ( $this -> errorReporting );
}
public function testNotice ()
{
$exceptionHandler = $this -> getMock ( 'Symfony\Component\Debug\ExceptionHandler' , array ( 'handle' ));
set_exception_handler ( array ( $exceptionHandler , 'handle' ));
$that = $this ;
2013-12-28 07:46:05 +00:00
$exceptionCheck = function ( $exception ) use ( $that ) {
2014-04-17 08:44:42 +01:00
$that -> assertInstanceOf ( 'Symfony\Component\Debug\Exception\HandledErrorException' , $exception );
2013-11-05 20:12:21 +00:00
$that -> assertEquals ( E_NOTICE , $exception -> getSeverity ());
$that -> assertEquals ( __FILE__ , $exception -> getFile ());
$that -> assertRegexp ( '/^Notice: Undefined variable: (foo|bar)/' , $exception -> getMessage ());
$that -> assertArrayHasKey ( 'foobar' , $exception -> getContext ());
$trace = $exception -> getTrace ();
$that -> assertEquals ( __FILE__ , $trace [ 0 ][ 'file' ]);
$that -> assertEquals ( 'Symfony\Component\Debug\ErrorHandler' , $trace [ 0 ][ 'class' ]);
$that -> assertEquals ( 'handle' , $trace [ 0 ][ 'function' ]);
$that -> assertEquals ( '->' , $trace [ 0 ][ 'type' ]);
$that -> assertEquals ( __FILE__ , $trace [ 1 ][ 'file' ]);
$that -> assertEquals ( __CLASS__ , $trace [ 1 ][ 'class' ]);
$that -> assertEquals ( 'triggerNotice' , $trace [ 1 ][ 'function' ]);
$that -> assertEquals ( '::' , $trace [ 1 ][ 'type' ]);
$that -> assertEquals ( __CLASS__ , $trace [ 2 ][ 'class' ]);
$that -> assertEquals ( 'testNotice' , $trace [ 2 ][ 'function' ]);
$that -> assertEquals ( '->' , $trace [ 2 ][ 'type' ]);
};
2013-11-28 16:41:31 +00:00
$exceptionHandler -> expects ( $this -> once ())
2013-11-05 20:12:21 +00:00
-> method ( 'handle' )
-> will ( $this -> returnCallback ( $exceptionCheck ));
ErrorHandler :: register ();
2013-11-28 16:41:31 +00:00
try {
self :: triggerNotice ( $this );
2014-04-17 08:44:42 +01:00
} catch ( HandledErrorException $e ) {
2013-11-28 16:41:31 +00:00
// if an exception is thrown, the test passed
2013-12-11 15:16:31 +00:00
} catch ( \Exception $e ) {
restore_error_handler ();
throw $e ;
2013-11-28 16:41:31 +00:00
}
2013-08-07 14:15:14 +01:00
restore_error_handler ();
}
2011-04-15 20:12:02 +01:00
2013-11-05 20:12:21 +00:00
// dummy function to test trace in error handler.
2013-11-28 10:16:43 +00:00
private static function triggerNotice ( $that )
{
2013-11-05 20:12:21 +00:00
// dummy variable to check for in error handler.
$foobar = 123 ;
2013-11-28 10:16:43 +00:00
$that -> assertSame ( '' , $foo . $foo . $bar );
2013-08-07 14:15:14 +01:00
}
2011-04-15 20:12:02 +01:00
2011-03-05 19:23:35 +00:00
public function testConstruct ()
{
2013-12-11 15:16:31 +00:00
try {
$handler = ErrorHandler :: register ( 3 );
2011-04-15 20:12:02 +01:00
2013-12-11 15:16:31 +00:00
$level = new \ReflectionProperty ( $handler , 'level' );
$level -> setAccessible ( true );
2011-04-15 20:12:02 +01:00
2013-12-11 15:16:31 +00:00
$this -> assertEquals ( 3 , $level -> getValue ( $handler ));
2011-04-15 20:12:02 +01:00
2013-12-11 15:16:31 +00:00
restore_error_handler ();
} catch ( \Exception $e ) {
restore_error_handler ();
throw $e ;
}
2011-03-05 19:23:35 +00:00
}
public function testHandle ()
{
2013-12-11 15:16:31 +00:00
try {
$handler = ErrorHandler :: register ( 0 );
$this -> assertFalse ( $handler -> handle ( 0 , 'foo' , 'foo.php' , 12 , 'foo' ));
2011-05-05 07:46:20 +01:00
2013-12-11 15:16:31 +00:00
restore_error_handler ();
2011-05-05 07:46:20 +01:00
2013-12-11 15:16:31 +00:00
$handler = ErrorHandler :: register ( 3 );
$this -> assertFalse ( $handler -> handle ( 4 , 'foo' , 'foo.php' , 12 , 'foo' ));
2011-04-15 20:12:02 +01:00
2013-12-11 15:16:31 +00:00
restore_error_handler ();
2011-04-15 20:12:02 +01:00
2013-12-11 15:16:31 +00:00
$handler = ErrorHandler :: register ( 3 );
try {
$handler -> handle ( 111 , 'foo' , 'foo.php' , 12 , 'foo' );
} catch ( \ErrorException $e ) {
$this -> assertSame ( '111: foo in foo.php line 12' , $e -> getMessage ());
$this -> assertSame ( 111 , $e -> getSeverity ());
$this -> assertSame ( 'foo.php' , $e -> getFile ());
$this -> assertSame ( 12 , $e -> getLine ());
}
2011-03-05 19:23:35 +00:00
2013-12-11 15:16:31 +00:00
restore_error_handler ();
2012-12-01 11:25:00 +00:00
2013-12-11 15:16:31 +00:00
$handler = ErrorHandler :: register ( E_USER_DEPRECATED );
$this -> assertTrue ( $handler -> handle ( E_USER_DEPRECATED , 'foo' , 'foo.php' , 12 , 'foo' ));
2012-12-01 11:25:00 +00:00
2013-12-11 15:16:31 +00:00
restore_error_handler ();
2012-12-01 11:25:00 +00:00
2013-12-11 15:16:31 +00:00
$handler = ErrorHandler :: register ( E_DEPRECATED );
$this -> assertTrue ( $handler -> handle ( E_DEPRECATED , 'foo' , 'foo.php' , 12 , 'foo' ));
2012-12-01 11:25:00 +00:00
2013-12-11 15:16:31 +00:00
restore_error_handler ();
2012-12-01 11:25:00 +00:00
2013-12-11 15:16:31 +00:00
$logger = $this -> getMock ( 'Psr\Log\LoggerInterface' );
2012-12-07 11:47:14 +00:00
2013-12-11 15:16:31 +00:00
$that = $this ;
2013-12-28 08:12:03 +00:00
$warnArgCheck = function ( $message , $context ) use ( $that ) {
2013-12-11 15:16:31 +00:00
$that -> assertEquals ( 'foo' , $message );
$that -> assertArrayHasKey ( 'type' , $context );
$that -> assertEquals ( $context [ 'type' ], ErrorHandler :: TYPE_DEPRECATION );
$that -> assertArrayHasKey ( 'stack' , $context );
$that -> assertInternalType ( 'array' , $context [ 'stack' ]);
};
2012-12-07 11:47:14 +00:00
2013-12-11 15:16:31 +00:00
$logger
-> expects ( $this -> once ())
-> method ( 'warning' )
-> will ( $this -> returnCallback ( $warnArgCheck ))
;
2012-12-01 11:25:00 +00:00
2013-12-11 15:16:31 +00:00
$handler = ErrorHandler :: register ( E_USER_DEPRECATED );
$handler -> setLogger ( $logger );
$handler -> handle ( E_USER_DEPRECATED , 'foo' , 'foo.php' , 12 , 'foo' );
2012-12-01 11:25:00 +00:00
2013-12-11 15:16:31 +00:00
restore_error_handler ();
2014-02-04 20:08:27 +00:00
$logger = $this -> getMock ( 'Psr\Log\LoggerInterface' );
$that = $this ;
$logArgCheck = function ( $level , $message , $context ) use ( $that ) {
$that -> assertEquals ( 'Undefined variable: undefVar' , $message );
$that -> assertArrayHasKey ( 'type' , $context );
$that -> assertEquals ( $context [ 'type' ], E_NOTICE );
};
$logger
-> expects ( $this -> once ())
-> method ( 'log' )
-> will ( $this -> returnCallback ( $logArgCheck ))
;
$handler = ErrorHandler :: register ( E_NOTICE );
$handler -> setLogger ( $logger , 'scream' );
unset ( $undefVar );
@ $undefVar ++ ;
restore_error_handler ();
2013-12-11 15:16:31 +00:00
} catch ( \Exception $e ) {
restore_error_handler ();
throw $e ;
}
2011-05-05 07:46:20 +01:00
}
2013-05-28 18:12:41 +01:00
/**
2013-07-24 05:59:37 +01:00
* @ dataProvider provideFatalErrorHandlersData
2013-05-28 18:12:41 +01:00
*/
2013-07-24 05:59:37 +01:00
public function testFatalErrorHandlers ( $error , $class , $translatedMessage )
2013-05-28 18:12:41 +01:00
{
2013-07-24 05:59:37 +01:00
$handler = new ErrorHandler ();
$exceptionHandler = new MockExceptionHandler ();
2013-07-23 19:05:03 +01:00
$m = new \ReflectionMethod ( $handler , 'handleFatalError' );
$m -> setAccessible ( true );
2014-04-17 08:44:42 +01:00
$m -> invoke ( $handler , array ( $exceptionHandler , 'handle' ), $error );
2013-05-28 18:12:41 +01:00
2013-07-24 05:59:37 +01:00
$this -> assertInstanceof ( $class , $exceptionHandler -> e );
2014-02-03 10:14:27 +00:00
// class names are case insensitive and PHP/HHVM do not return the same
$this -> assertSame ( strtolower ( $translatedMessage ), strtolower ( $exceptionHandler -> e -> getMessage ()));
2013-05-28 18:12:41 +01:00
$this -> assertSame ( $error [ 'type' ], $exceptionHandler -> e -> getSeverity ());
$this -> assertSame ( $error [ 'file' ], $exceptionHandler -> e -> getFile ());
$this -> assertSame ( $error [ 'line' ], $exceptionHandler -> e -> getLine ());
}
2013-07-24 05:59:37 +01:00
public function provideFatalErrorHandlersData ()
2013-05-28 18:12:41 +01:00
{
return array (
2013-07-24 05:59:37 +01:00
// undefined function
2013-05-28 18:12:41 +01:00
array (
array (
'type' => 1 ,
'line' => 12 ,
'file' => 'foo.php' ,
2013-12-12 16:06:35 +00:00
'message' => 'Call to undefined function test_namespaced_function_again()' ,
2013-05-28 18:12:41 +01:00
),
2013-07-24 05:59:37 +01:00
'Symfony\Component\Debug\Exception\UndefinedFunctionException' ,
2013-12-12 16:06:35 +00:00
'Attempted to call function "test_namespaced_function_again" from the global namespace in foo.php line 12. Did you mean to call: "\\symfony\\component\\debug\\tests\\test_namespaced_function_again"?' ,
2013-05-28 18:12:41 +01:00
),
2013-07-24 05:59:37 +01:00
// class not found
2013-05-28 18:12:41 +01:00
array (
array (
'type' => 1 ,
'line' => 12 ,
'file' => 'foo.php' ,
2013-08-30 12:26:06 +01:00
'message' => 'Class \'WhizBangFactory\' not found' ,
2013-05-28 18:12:41 +01:00
),
2013-07-24 05:59:37 +01:00
'Symfony\Component\Debug\Exception\ClassNotFoundException' ,
'Attempted to load class "WhizBangFactory" from the global namespace in foo.php line 12. Did you forget a use statement for this class?' ,
2013-05-28 18:12:41 +01:00
),
);
}
2011-03-05 19:23:35 +00:00
}
2013-12-12 16:06:35 +00:00
function test_namespaced_function_again ()
{
}