createMock(Response::class); /** @var SessionInterface|MockObject $session */ /** @var UrlGeneratorInterface|MockObject $url */ /** @var Config $config */ /** @var Authenticator|MockObject $auth */ list(, $session, $url, $config, $auth) = $this->getMocks(); $session->expects($this->atLeastOnce()) ->method('get') ->willReturnCallback(function ($type) { return $type == 'errors' ? ['foo' => 'bar'] : []; }); $response->expects($this->once()) ->method('withView') ->with('pages/login') ->willReturn($response); $controller = new AuthController($response, $session, $url, $config, $auth); $controller->login(); } /** * @covers \Engelsystem\Controllers\AuthController::postLogin */ public function testPostLogin() { $this->initDatabase(); $request = new Request(); /** @var Response|MockObject $response */ $response = $this->createMock(Response::class); /** @var UrlGeneratorInterface|MockObject $url */ /** @var Config $config */ /** @var Authenticator|MockObject $auth */ list(, , $url, $config, $auth) = $this->getMocks(); $session = new Session(new MockArraySessionStorage()); /** @var Validator|MockObject $validator */ $validator = new Validator(); $session->set('errors', [['bar' => 'some.bar.error']]); $this->app->instance('session', $session); $user = new User([ 'name' => 'foo', 'password' => '', 'email' => '', 'api_key' => '', 'last_login_at' => null, ]); $user->forceFill(['id' => 42]); $user->save(); $settings = new Settings(['language' => 'de_DE', 'theme' => '']); $settings->user() ->associate($user) ->save(); $auth->expects($this->exactly(2)) ->method('authenticate') ->with('foo', 'bar') ->willReturnOnConsecutiveCalls(null, $user); $response->expects($this->once()) ->method('withView') ->willReturnCallback(function ($view, $data = []) use ($response) { $this->assertEquals('pages/login', $view); $this->assertArraySubset(['errors' => collect(['some.bar.error', 'auth.not-found'])], $data); return $response; }); $response->expects($this->once()) ->method('redirectTo') ->with('news') ->willReturn($response); // No credentials $controller = new AuthController($response, $session, $url, $config, $auth); $controller->setValidator($validator); try { $controller->postLogin($request); $this->fail('Login without credentials possible'); } catch (ValidationException $e) { } // Missing password $request = new Request([], ['login' => 'foo']); try { $controller->postLogin($request); $this->fail('Login without password possible'); } catch (ValidationException $e) { } // No user found $request = new Request([], ['login' => 'foo', 'password' => 'bar']); $controller->postLogin($request); $this->assertEquals([], $session->all()); // Authenticated user $controller->postLogin($request); $this->assertNotNull($user->last_login_at); $this->assertEquals(['user_id' => 42, 'locale' => 'de_DE'], $session->all()); } /** * @covers \Engelsystem\Controllers\AuthController::logout */ public function testLogout() { /** @var Response $response */ /** @var SessionInterface|MockObject $session */ /** @var UrlGeneratorInterface|MockObject $url */ /** @var Config $config */ /** @var Authenticator|MockObject $auth */ list($response, $session, $url, $config, $auth) = $this->getMocks(); $session->expects($this->once()) ->method('invalidate'); $url->expects($this->once()) ->method('to') ->with('/') ->willReturn('https://foo.bar/'); $controller = new AuthController($response, $session, $url, $config, $auth); $return = $controller->logout(); $this->assertEquals(['https://foo.bar/'], $return->getHeader('location')); } /** * @return array */ protected function getMocks() { $response = new Response(); /** @var SessionInterface|MockObject $session */ $session = $this->getMockForAbstractClass(SessionInterface::class); /** @var UrlGeneratorInterface|MockObject $url */ $url = $this->getMockForAbstractClass(UrlGeneratorInterface::class); $config = new Config(['home_site' => 'news']); /** @var Authenticator|MockObject $auth */ $auth = $this->createMock(Authenticator::class); $this->app->instance('session', $session); return [$response, $session, $url, $config, $auth]; } }