the browser-facing portion of osu!
at master 3.1 kB view raw
1<?php 2 3// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0. 4// See the LICENCE file in the repository root for full licence text. 5 6namespace App\Http\Controllers\Passport; 7 8use Illuminate\Http\Request; 9use Laravel\Passport\ClientRepository; 10use Laravel\Passport\Exceptions\AuthenticationException; 11use Laravel\Passport\Http\Controllers\AuthorizationController as PassportAuthorizationController; 12use Laravel\Passport\Passport; 13use Laravel\Passport\TokenRepository; 14use Psr\Http\Message\ServerRequestInterface; 15 16/** 17 * Extension of Laravel\Passport\Http\Controllers\AuthorizationController 18 * to add support for scope normalization when requesting token scopes. 19 */ 20class AuthorizationController extends PassportAuthorizationController 21{ 22 /** 23 * Authorize a client to access the user's account. 24 * This overrides the default implementation to normalize scope requests 25 * and sort the scopes by key order. 26 * 27 * @param \Psr\Http\Message\ServerRequestInterface $psrRequest 28 * @param \Illuminate\Http\Request $request 29 * @param \Laravel\Passport\ClientRepository $clients 30 * @param \Laravel\Passport\TokenRepository $tokens 31 * @return \Illuminate\Http\Response 32 */ 33 public function authorize( 34 ServerRequestInterface $psrRequest, 35 Request $request, 36 ClientRepository $clients, 37 TokenRepository $tokens 38 ) { 39 try { 40 return parent::authorize($this->normalizeRequestScopes($psrRequest), $request, $clients, $tokens); 41 } catch (AuthenticationException $_e) { 42 $cancelUrl = $request->fullUrl(); 43 $cancelUrl .= strpos($cancelUrl, '?') === false ? '?' : '&'; 44 $cancelUrl .= 'prompt=none'; 45 46 return ext_view('sessions.create', [ 47 'cancelUrl' => $cancelUrl, 48 ]); 49 } 50 } 51 52 /** 53 * Normalizes the authorization request's scopes. 54 * 55 * @param ServerRequestInterface $request 56 * @return ServerRequestInterface 57 */ 58 private function normalizeRequestScopes(ServerRequestInterface $request): ServerRequestInterface 59 { 60 $params = $request->getQueryParams(); 61 $scopes = $this->normalizeScopes( 62 explode(' ', $params['scope'] ?? '') 63 ); 64 65 // temporary non-persisted token to validate with. 66 $token = Passport::token()->forceFill([ 67 'client_id' => $params['client_id'] ?? null, 68 'revoked' => false, 69 'scopes' => $scopes, 70 ]); 71 $token->user()->associate(auth()->user()); 72 $token->validate(); 73 74 $params['scope'] = implode(' ', $scopes); 75 76 return $request->withQueryParams($params); 77 } 78 79 /** 80 * Normalizes and sorts scopes. 81 * 82 * @param array $scopes 83 * @return array 84 */ 85 private function normalizeScopes(array $scopes): array 86 { 87 if (!in_array('identify', $scopes, true)) { 88 $scopes[] = 'identify'; 89 } 90 91 sort($scopes); 92 93 return $scopes; 94 } 95}