request = $this->createMock(IRequest::class); $this->urlGenerator = $this->createMock(IURLGenerator::class); $this->clientMapper = $this->createMock(ClientMapper::class); $this->session = $this->createMock(ISession::class); $this->l = $this->createMock(IL10N::class); $this->random = $this->createMock(ISecureRandom::class); $this->appConfig = $this->createMock(IAppConfig::class); $this->config = $this->createMock(IConfig::class); $this->loginRedirectorController = new LoginRedirectorController( 'oauth2', $this->request, $this->urlGenerator, $this->clientMapper, $this->session, $this->l, $this->random, $this->appConfig, $this->config, ); } public function testAuthorize(): void { $client = new Client(); $client->setClientIdentifier('MyClientIdentifier'); $this->clientMapper ->expects($this->once()) ->method('getByIdentifier') ->with('MyClientId') ->willReturn($client); $this->session ->expects($this->once()) ->method('set') ->with('oauth.state', 'MyState'); $this->urlGenerator ->expects($this->once()) ->method('linkToRouteAbsolute') ->with( 'core.ClientFlowLogin.showAuthPickerPage', [ 'clientIdentifier' => 'MyClientIdentifier', 'providedRedirectUri' => '', ] ) ->willReturn('https://example.com/?clientIdentifier=foo'); $this->config ->expects($this->once()) ->method('getSystemValueBool') ->with('oauth2.enable_oc_clients', false) ->willReturn(false); $expected = new RedirectResponse('https://example.com/?clientIdentifier=foo'); $this->assertEquals($expected, $this->loginRedirectorController->authorize('MyClientId', 'MyState', 'code')); } public function testAuthorizeSkipPicker(): void { $client = new Client(); $client->setName('MyClientName'); $client->setClientIdentifier('MyClientIdentifier'); $this->clientMapper ->expects($this->once()) ->method('getByIdentifier') ->with('MyClientId') ->willReturn($client); $this->session ->expects(static::exactly(2)) ->method('set') ->willReturnCallback(function (string $key, string $value): void { switch ([$key, $value]) { case ['oauth.state', 'MyState']: case [ClientFlowLoginController::STATE_NAME, 'MyStateToken']: /* Expected */ break; default: throw new LogicException(); } }); $this->appConfig ->expects(static::once()) ->method('getValueArray') ->with('oauth2', 'skipAuthPickerApplications', []) ->willReturn(['MyClientName']); $this->random ->expects(static::once()) ->method('generate') ->willReturn('MyStateToken'); $this->urlGenerator ->expects($this->once()) ->method('linkToRouteAbsolute') ->with( 'core.ClientFlowLogin.grantPage', [ 'stateToken' => 'MyStateToken', 'clientIdentifier' => 'MyClientIdentifier', 'providedRedirectUri' => '', ] ) ->willReturn('https://example.com/?clientIdentifier=foo'); $this->config ->expects($this->once()) ->method('getSystemValueBool') ->with('oauth2.enable_oc_clients', false) ->willReturn(false); $expected = new RedirectResponse('https://example.com/?clientIdentifier=foo'); $this->assertEquals($expected, $this->loginRedirectorController->authorize('MyClientId', 'MyState', 'code')); } public function testAuthorizeWrongResponseType(): void { $client = new Client(); $client->setClientIdentifier('MyClientIdentifier'); $client->setRedirectUri('http://foo.bar'); $this->clientMapper ->expects($this->once()) ->method('getByIdentifier') ->with('MyClientId') ->willReturn($client); $this->session ->expects($this->never()) ->method('set'); $expected = new RedirectResponse('http://foo.bar?error=unsupported_response_type&state=MyState'); $this->assertEquals($expected, $this->loginRedirectorController->authorize('MyClientId', 'MyState', 'wrongcode')); } public function testAuthorizeWithLegacyOcClient(): void { $client = new Client(); $client->setClientIdentifier('MyClientIdentifier'); $client->setRedirectUri('http://localhost:*'); $this->clientMapper ->expects($this->once()) ->method('getByIdentifier') ->with('MyClientId') ->willReturn($client); $this->session ->expects($this->once()) ->method('set') ->with('oauth.state', 'MyState'); $this->urlGenerator ->expects($this->once()) ->method('linkToRouteAbsolute') ->with( 'core.ClientFlowLogin.showAuthPickerPage', [ 'clientIdentifier' => 'MyClientIdentifier', 'providedRedirectUri' => 'http://localhost:30000', ] ) ->willReturn('https://example.com/?clientIdentifier=foo&providedRedirectUri=http://localhost:30000'); $this->config ->expects($this->once()) ->method('getSystemValueBool') ->with('oauth2.enable_oc_clients', false) ->willReturn(true); $expected = new RedirectResponse('https://example.com/?clientIdentifier=foo&providedRedirectUri=http://localhost:30000'); $this->assertEquals($expected, $this->loginRedirectorController->authorize('MyClientId', 'MyState', 'code', 'http://localhost:30000')); } public function testAuthorizeNotForwardingUntrustedURIs(): void { $client = new Client(); $client->setClientIdentifier('MyClientIdentifier'); $this->clientMapper ->expects($this->once()) ->method('getByIdentifier') ->with('MyClientId') ->willReturn($client); $this->session ->expects($this->once()) ->method('set') ->with('oauth.state', 'MyState'); $this->urlGenerator ->expects($this->once()) ->method('linkToRouteAbsolute') ->with( 'core.ClientFlowLogin.showAuthPickerPage', [ 'clientIdentifier' => 'MyClientIdentifier', 'providedRedirectUri' => '', ] ) ->willReturn('https://example.com/?clientIdentifier=foo'); $this->config ->expects($this->once()) ->method('getSystemValueBool') ->with('oauth2.enable_oc_clients', false) ->willReturn(false); $expected = new RedirectResponse('https://example.com/?clientIdentifier=foo'); $this->assertEquals($expected, $this->loginRedirectorController->authorize('MyClientId', 'MyState', 'code', 'http://untrusted-uri.com')); } public function testClientNotFound(): void { $clientNotFound = new ClientNotFoundException('could not find client test123', 0); $this->clientMapper ->expects($this->once()) ->method('getByIdentifier') ->willThrowException($clientNotFound); $this->session ->expects($this->never()) ->method('set'); $response = $this->loginRedirectorController->authorize('MyClientId', 'MyState', 'wrongcode'); $this->assertInstanceOf(TemplateResponse::class, $response); /** @var TemplateResponse $response */ $this->assertEquals('404', $response->getTemplateName()); $this->assertEquals('guest', $response->getRenderAs()); } }