UNPKG

@delewis13/appauth

Version:

A general purpose OAuth client. Vendored awaiting PR merge

198 lines (177 loc) 7.02 kB
/* * Copyright 2017 Google Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except * in compliance with the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software distributed under the * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either * express or implied. See the License for the specific language governing permissions and * limitations under the License. */ // Represents the test web app that uses the AppAuthJS library. import {AuthorizationRequest} from '../authorization_request'; import {AuthorizationNotifier, AuthorizationRequestHandler} from '../authorization_request_handler'; import {AuthorizationServiceConfiguration} from '../authorization_service_configuration'; import {log} from '../logger'; import {RedirectRequestHandler} from '../redirect_based_handler'; import {GRANT_TYPE_AUTHORIZATION_CODE, GRANT_TYPE_REFRESH_TOKEN, TokenRequest} from '../token_request'; import {BaseTokenRequestHandler, TokenRequestHandler} from '../token_request_handler'; import {TokenResponse} from '../token_response'; import { AuthorizationResponse } from '../authorization_response'; import { StringMap } from '../types'; /* Some interface declarations for Material design lite. */ /** * Snackbar options. */ declare interface SnackBarOptions { message: string; timeout?: number; } /** * Interface that defines the MDL Material Snack Bar API. */ declare interface MaterialSnackBar { showSnackbar: (options: SnackBarOptions) => void; } /* an example open id connect provider */ const openIdConnectUrl = 'https://accounts.google.com'; /* example client configuration */ const clientId = '674027045299-a31g2q39v6qgngqvh8psi99km931rn8f.apps.googleusercontent.com'; const clientSecret = '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'; const redirectUri = 'http://localhost:8000/app/redirect.html'; const scope = 'openid profile email'; /** * The Test application. */ export class App { private notifier: AuthorizationNotifier; private authorizationHandler: AuthorizationRequestHandler; private tokenHandler: TokenRequestHandler; // state private configuration: AuthorizationServiceConfiguration|undefined; private request: AuthorizationRequest|undefined; private response: AuthorizationResponse|undefined; private code: string|undefined; private tokenResponse: TokenResponse|undefined; constructor(public snackbar: Element) { this.notifier = new AuthorizationNotifier(); this.authorizationHandler = new RedirectRequestHandler(); this.tokenHandler = new BaseTokenRequestHandler(); // set notifier to deliver responses this.authorizationHandler.setAuthorizationNotifier(this.notifier); // set a listener to listen for authorization responses this.notifier.setAuthorizationListener((request, response, error) => { log('Authorization request complete ', request, response, error); if (response) { this.request = request; this.response = response; this.code = response.code; this.showMessage(`Authorization Code ${response.code}`); } }); } showMessage(message: string) { const snackbar = (this.snackbar as any)['MaterialSnackbar'] as MaterialSnackBar; snackbar.showSnackbar({message: message}); } fetchServiceConfiguration() { AuthorizationServiceConfiguration.fetchFromIssuer(openIdConnectUrl) .then(response => { log('Fetched service configuration', response); this.configuration = response; this.showMessage('Completed fetching configuration'); }) .catch(error => { log('Something bad happened', error); this.showMessage(`Something bad happened ${error}`) }); } makeAuthorizationRequest() { // create a request let request = new AuthorizationRequest({ client_id: clientId, redirect_uri: redirectUri, scope: scope, response_type: AuthorizationRequest.RESPONSE_TYPE_CODE, state: undefined, extras: {'prompt': 'consent', 'access_type': 'offline'} }); if (this.configuration) { this.authorizationHandler.performAuthorizationRequest(this.configuration, request); } else { this.showMessage( 'Fetch Authorization Service configuration, before you make the authorization request.'); } } makeTokenRequest() { if (!this.configuration) { this.showMessage('Please fetch service configuration.'); return; } let request: TokenRequest|null = null; if (this.code) { let extras: StringMap|undefined = undefined; if (this.request && this.request.internal) { extras = {}; extras['code_verifier'] = this.request.internal['code_verifier']; } // use the code to make the token request. request = new TokenRequest({ client_id: clientId, client_secret: clientSecret, redirect_uri: redirectUri, grant_type: GRANT_TYPE_AUTHORIZATION_CODE, code: this.code, refresh_token: undefined, extras: extras }); } else if (this.tokenResponse) { // use the token response to make a request for an access token request = new TokenRequest({ client_id: clientId, client_secret: clientSecret, redirect_uri: redirectUri, grant_type: GRANT_TYPE_REFRESH_TOKEN, code: undefined, refresh_token: this.tokenResponse.refreshToken, extras: undefined }); } if (request) { this.tokenHandler.performTokenRequest(this.configuration, request) .then(response => { let isFirstRequest = false; if (this.tokenResponse) { // copy over new fields this.tokenResponse.accessToken = response.accessToken; this.tokenResponse.issuedAt = response.issuedAt; this.tokenResponse.expiresIn = response.expiresIn; this.tokenResponse.tokenType = response.tokenType; this.tokenResponse.scope = response.scope; } else { isFirstRequest = true; this.tokenResponse = response; } // unset code, so we can do refresh token exchanges subsequently this.code = undefined; if (isFirstRequest) { this.showMessage(`Obtained a refresh token ${response.refreshToken}`); } else { this.showMessage(`Obtained an access token ${response.accessToken}.`); } }) .catch(error => { log('Something bad happened', error); this.showMessage(`Something bad happened ${error}`) }); } } checkForAuthorizationResponse() { this.authorizationHandler.completeAuthorizationRequestIfPossible(); } } // export App (window as any)['App'] = App;