1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131
|
<?php
/**
* Slim Framework (https://slimframework.com)
*
* @license https://github.com/slimphp/Slim/blob/3.x/LICENSE.md (MIT License)
*/
namespace Slim\Tests\Handlers;
use Exception;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit_Framework_MockObject_MockObject;
use PHPUnit;
use ReflectionClass;
use RuntimeException;
use Slim\Handlers\Error;
use Slim\Http\Request;
use Slim\Http\Response;
use UnexpectedValueException;
class ErrorTest extends PHPUnit\Framework\TestCase
{
public static function errorProvider()
{
return [
['application/json', 'application/json', '{'],
['application/vnd.api+json', 'application/json', '{'],
['application/xml', 'application/xml', '<error>'],
['application/hal+xml', 'application/xml', '<error>'],
['text/xml', 'text/xml', '<error>'],
['text/html', 'text/html', '<html>'],
];
}
/**
* Test invalid method returns the correct code and content type
*/
#[DataProvider('errorProvider')]
public function testError($acceptHeader, $contentType, $startOfBody)
{
$error = new Error();
$e = new Exception("Oops", 1, new Exception('Previous oops'));
/** @var Response $res */
$res = $error->__invoke($this->getRequest('GET', $acceptHeader), new Response(), $e);
$this->assertSame(500, $res->getStatusCode());
$this->assertSame($contentType, $res->getHeaderLine('Content-Type'));
$this->assertEquals(0, strpos((string)$res->getBody(), $startOfBody));
}
/**
* Test invalid method returns the correct code and content type with details
*/
#[DataProvider('errorProvider')]
public function testErrorDisplayDetails($acceptHeader, $contentType, $startOfBody)
{
$error = new Error(true);
$e = new Exception('Oops', 1, new Exception('Opps before'));
/** @var Response $res */
$res = $error->__invoke($this->getRequest('GET', $acceptHeader), new Response(), $e);
$this->assertSame(500, $res->getStatusCode());
$this->assertSame($contentType, $res->getHeaderLine('Content-Type'));
$this->assertEquals(0, strpos((string)$res->getBody(), $startOfBody));
}
public function testNotFoundContentType()
{
$this->expectException('UnexpectedValueException');
$errorMock = $this->getMockBuilder(Error::class)->onlyMethods(['determineContentType'])->getMock();
$errorMock->method('determineContentType')
->willReturn('unknown/type');
$e = new Exception("Oops");
$req = $this->getMockBuilder('Slim\Http\Request')->disableOriginalConstructor()->getMock();
$errorMock->__invoke($req, new Response(), $e);
}
/**
* Test that an exception with a previous exception provides correct output
* to the error log
*/
public function testPreviousException()
{
$error = $this->getMockBuilder('\Slim\Handlers\Error')->onlyMethods(['logError'])->getMock();
$error->expects($this->once())->method('logError')->with(
$this->logicalAnd(
$this->stringContains("Type: Exception" . PHP_EOL . "Message: Second Oops"),
$this->stringContains("Previous Error:" . PHP_EOL . "Type: Exception" . PHP_EOL . "Message: First Oops")
)
);
$first = new Exception("First Oops");
$second = new Exception("Second Oops", 0, $first);
$error->__invoke($this->getRequest('GET', 'application/json'), new Response(), $second);
}
/**
* If someone extends the Error handler and calls renderHtmlExceptionOrError with
* a parameter that isn't an Exception or Error, then we thrown an Exception.
*/
public function testRenderHtmlExceptionOrErrorTypeChecksParameter()
{
$class = new ReflectionClass(Error::class);
$renderHtmlExceptionorError = $class->getMethod('renderHtmlExceptionOrError');
$renderHtmlExceptionorError->setAccessible(true);
$this->expectException(RuntimeException::class);
$error = new Error();
$renderHtmlExceptionorError->invokeArgs($error, ['foo']);
}
/**
* @param string $method
*
* @return PHPUnit_Framework_MockObject_MockObject|Request
*/
protected function getRequest($method, $acceptHeader)
{
$req = $this->getMockBuilder('Slim\Http\Request')->disableOriginalConstructor()->getMock();
$req->expects($this->once())->method('getHeaderLine')->willReturn($acceptHeader);
return $req;
}
}
|