9f51371a55d630e1406ef0fbdfe7ed4dc66819c1
[lhc/web/wiklou.git] / tests / phpunit / unit / includes / Rest / RouterTest.php
1 <?php
2
3 namespace MediaWiki\Tests\Rest;
4
5 use GuzzleHttp\Psr7\Uri;
6 use MediaWiki\Rest\BasicAccess\StaticBasicAuthorizer;
7 use MediaWiki\Rest\Handler;
8 use MediaWiki\Rest\HttpException;
9 use MediaWiki\Rest\RequestData;
10 use MediaWiki\Rest\RequestInterface;
11 use MediaWiki\Rest\ResponseFactory;
12 use MediaWiki\Rest\Router;
13 use MediaWiki\Rest\Validator\Validator;
14 use Psr\Container\ContainerInterface;
15 use Wikimedia\ObjectFactory;
16 use User;
17
18 /**
19 * @covers \MediaWiki\Rest\Router
20 */
21 class RouterTest extends \MediaWikiUnitTestCase {
22 /** @return Router */
23 private function createRouter( RequestInterface $request, $authError = null ) {
24 $objectFactory = new ObjectFactory(
25 $this->getMockForAbstractClass( ContainerInterface::class )
26 );
27 return new Router(
28 [ __DIR__ . '/testRoutes.json' ],
29 [],
30 '/rest',
31 new \EmptyBagOStuff(),
32 new ResponseFactory( [] ),
33 new StaticBasicAuthorizer( $authError ),
34 $objectFactory,
35 new Validator( $objectFactory, $request, new User )
36 );
37 }
38
39 public function testPrefixMismatch() {
40 $request = new RequestData( [ 'uri' => new Uri( '/bogus' ) ] );
41 $router = $this->createRouter( $request );
42 $response = $router->execute( $request );
43 $this->assertSame( 404, $response->getStatusCode() );
44 }
45
46 public function testWrongMethod() {
47 $request = new RequestData( [
48 'uri' => new Uri( '/rest/user/joe/hello' ),
49 'method' => 'OPTIONS'
50 ] );
51 $router = $this->createRouter( $request );
52 $response = $router->execute( $request );
53 $this->assertSame( 405, $response->getStatusCode() );
54 $this->assertSame( 'Method Not Allowed', $response->getReasonPhrase() );
55 $this->assertSame( 'GET', $response->getHeaderLine( 'Allow' ) );
56 }
57
58 public function testNoMatch() {
59 $request = new RequestData( [ 'uri' => new Uri( '/rest/bogus' ) ] );
60 $router = $this->createRouter( $request );
61 $response = $router->execute( $request );
62 $this->assertSame( 404, $response->getStatusCode() );
63 // TODO: add more information to the response body and test for its presence here
64 }
65
66 public static function throwHandlerFactory() {
67 return new class extends Handler {
68 public function execute() {
69 throw new HttpException( 'Mock error', 555 );
70 }
71 };
72 }
73
74 public function testException() {
75 $request = new RequestData( [ 'uri' => new Uri( '/rest/mock/RouterTest/throw' ) ] );
76 $router = $this->createRouter( $request );
77 $response = $router->execute( $request );
78 $this->assertSame( 555, $response->getStatusCode() );
79 $body = $response->getBody();
80 $body->rewind();
81 $data = json_decode( $body->getContents(), true );
82 $this->assertSame( 'Mock error', $data['message'] );
83 }
84
85 public function testBasicAccess() {
86 // Using the throwing handler is a way to assert that the handler is not executed
87 $request = new RequestData( [ 'uri' => new Uri( '/rest/mock/RouterTest/throw' ) ] );
88 $router = $this->createRouter( $request, 'test-error' );
89 $response = $router->execute( $request );
90 $this->assertSame( 403, $response->getStatusCode() );
91 $body = $response->getBody();
92 $body->rewind();
93 $data = json_decode( $body->getContents(), true );
94 $this->assertSame( 'test-error', $data['error'] );
95 }
96 }