UNPKG

pryv

Version:

Pryv JavaScript library

205 lines (181 loc) 6.23 kB
/** * @license * [BSD-3-Clause](https://github.com/pryv/lib-js/blob/master/LICENSE) */ const Cookies = require('./CookieUtils'); const AuthStates = require('../Auth/AuthStates'); const AuthController = require('../Auth/AuthController'); const Messages = require('../Auth/LoginMessages'); const utils = require('../utils'); /* global location, confirm */ /** * @memberof pryv.Browser */ class LoginButton { constructor (authSettings, service) { this.authSettings = authSettings; this.service = service; this.serviceInfo = service.infoSync(); } /** * setup button and load assets */ async init () { // initialize button visuals setupButton(this); this.languageCode = this.authSettings.authRequest.languageCode || 'en'; this.messages = Messages(this.languageCode); if (this.loginButtonText) { await loadAssets(this); } // set cookie key for authorization data this._cookieKey = 'pryv-libjs-' + this.authSettings.authRequest.requestingAppId; // initialize controller this.auth = new AuthController(this.authSettings, this.service, this); await this.auth.init(); return this.service; } onClick () { this.auth.handleClick(); } async onStateChange (state) { switch (state.status) { case AuthStates.LOADING: this.text = getLoadingMessage(this); break; case AuthStates.INITIALIZED: this.text = getInitializedMessage(this, this.serviceInfo.name); break; case AuthStates.NEED_SIGNIN: { const loginUrl = state.authUrl || state.url; // url is deprecated if (this.authSettings.authRequest.returnURL) { // open on same page (no Popup) location.href = loginUrl; return; } else { startLoginScreen(this, loginUrl); } break; } case AuthStates.AUTHORIZED: this.text = state.username; this.saveAuthorizationData({ apiEndpoint: state.apiEndpoint, username: state.username }); break; case AuthStates.SIGNOUT: { const message = this.messages.SIGNOUT_CONFIRM ? this.messages.SIGNOUT_CONFIRM : 'Logout ?'; if (confirm(message)) { this.deleteAuthorizationData(); this.auth.init(); } break; } case AuthStates.ERROR: this.text = getErrorMessage(this, state.message); break; default: console.log('WARNING Unhandled state for Login: ' + state.status); } if (this.loginButtonText) { this.loginButtonText.innerHTML = this.text; } } getAuthorizationData () { return Cookies.get(this._cookieKey); } saveAuthorizationData (authData) { Cookies.set(this._cookieKey, authData); } async deleteAuthorizationData () { Cookies.del(this._cookieKey); } /** * not mandatory to implement as non-browsers don't have this behaviour * @param {*} authController */ async finishAuthProcessAfterRedirection (authController) { // this step should be applied only for the browser if (!utils.isBrowser()) return; // 3. Check if there is a prYvkey as result of "out of page login" const url = window.location.href; const pollUrl = retrievePollUrl(url); if (pollUrl !== null) { try { const res = await utils.superagent.get(pollUrl); authController.state = res.body; } catch (e) { authController.state = { status: AuthStates.ERROR, message: 'Cannot fetch result', error: e }; } } function retrievePollUrl (url) { const params = utils.getQueryParamsFromURL(url); let pollUrl = null; if (params.prYvkey) { // deprecated method - To be removed pollUrl = authController.serviceInfo.access + params.prYvkey; } if (params.prYvpoll) { pollUrl = params.prYvpoll; } return pollUrl; } } } module.exports = LoginButton; async function startLoginScreen (loginButton, authUrl) { const screenX = typeof window.screenX !== 'undefined' ? window.screenX : window.screenLeft; const screenY = typeof window.screenY !== 'undefined' ? window.screenY : window.screenTop; const outerWidth = typeof window.outerWidth !== 'undefined' ? window.outerWidth : document.body.clientWidth; const outerHeight = typeof window.outerHeight !== 'undefined' ? window.outerHeight : (document.body.clientHeight - 22); const width = 400; const height = 620; const left = parseInt(screenX + ((outerWidth - width) / 2), 10); const top = parseInt(screenY + ((outerHeight - height) / 2.5), 10); const features = ( 'width=' + width + ',height=' + height + ',left=' + left + ',top=' + top + ',scrollbars=yes' ); loginButton.popup = window.open(authUrl, 'prYv Sign-in', features); if (!loginButton.popup) { // loginButton.auth.stopAuthRequest('FAILED_TO_OPEN_WINDOW'); console.log('Pop-up blocked. A second click should allow it.'); } else if (window.focus) { loginButton.popup.focus(); } } function setupButton (loginBtn) { loginBtn.loginButtonSpan = document.getElementById(loginBtn.authSettings.spanButtonID); if (!loginBtn.loginButtonSpan) { console.log('WARNING: pryv.Browser initialized with no spanButtonID'); } else { // up to the time the button is loaded use the Span to display eventual // error messages loginBtn.loginButtonText = loginBtn.loginButtonSpan; // bind actions dynamically to the button click loginBtn.loginButtonSpan.addEventListener('click', loginBtn.onClick.bind(loginBtn)); } } /** * Loads the style from the service info */ async function loadAssets (loginBtn) { const assets = await loginBtn.service.assets(); loginBtn.loginButtonSpan.innerHTML = await assets.loginButtonGetHTML(); loginBtn.loginButtonText = document.getElementById('pryv-access-btn-text'); } function getErrorMessage (loginButton, message) { return loginButton.messages.ERROR + ': ' + message; } function getLoadingMessage (loginButton) { return loginButton.messages.LOADING; } function getInitializedMessage (loginButton, serviceName) { return loginButton.messages.LOGIN + ': ' + serviceName; }