main.js revision 5d1f7b1de12d16ceb2c938c56701a3e8bfa558f7
15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)/**
6d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) * Authenticator class wraps the communications between Gaia and its host.
7d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) */
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)function Authenticator() {
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)/**
124e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) * Gaia auth extension url origin.
134e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) * @type {string}
144e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) */
154e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)Authenticator.THIS_EXTENSION_ORIGIN =
164e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    'chrome-extension://mfffpogegjflfpflabcdkioaeobkgjik';
174e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)
184e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)/**
19c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) * Singleton getter of Authenticator.
20c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) * @return {Object} The singleton instance of Authenticator.
21c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) */
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Authenticator.getInstance = function() {
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!Authenticator.instance_) {
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Authenticator.instance_ = new Authenticator();
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return Authenticator.instance_;
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Authenticator.prototype = {
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  email_: null,
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_: null,
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  attemptToken_: null,
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Input params from extension initialization URL.
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  inputLang_: undefined,
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  intputEmail_: undefined,
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
385d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  isSAMLFlow_: false,
395d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  isSAMLEnabled_: false,
405d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  supportChannel_: null,
41d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
4290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  GAIA_URL: 'https://accounts.google.com/',
438bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  GAIA_PAGE_PATH: 'ServiceLogin?skipvpage=true&sarp=1&rm=hide',
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PARENT_PAGE: 'chrome://oobe/',
458bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  SERVICE_ID: 'chromeoslogin',
464e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  CONTINUE_URL: Authenticator.THIS_EXTENSION_ORIGIN + '/success.html',
475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  CONSTRAINED_FLOW_SOURCE: 'chrome',
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  initialize: function() {
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    var params = getUrlSearchParams(location.search);
514e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    this.parentPage_ = params.parentPage || this.PARENT_PAGE;
524e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    this.gaiaUrl_ = params.gaiaUrl || this.GAIA_URL;
53f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    this.gaiaPath_ = params.gaiaPath || this.GAIA_PAGE_PATH;
544e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    this.inputLang_ = params.hl;
554e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    this.inputEmail_ = params.email;
568bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)    this.service_ = params.service || this.SERVICE_ID;
574e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    this.continueUrl_ = params.continueUrl || this.CONTINUE_URL;
585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.desktopMode_ = params.desktopMode == '1';
595d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.isConstrainedWindow_ = params.constrained == '1';
60a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    this.initialFrameUrl_ = params.frameUrl || this.constructInitialFrameUrl_();
61a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    this.initialFrameUrlWithoutParams_ = stripParams(this.initialFrameUrl_);
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (this.desktopMode_) {
645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_ = new Channel();
655d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_.connect('authMain');
665d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_.send({
685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        name: 'initDesktopFlow',
695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        gaiaUrl: this.gaiaUrl_,
705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        continueUrl: stripParams(this.continueUrl_),
715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        isConstrainedWindow: this.isConstrainedWindow_
725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      });
735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_.registerMessage(
755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        'switchToFullTab', this.switchToFullTab_.bind(this));
765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_.registerMessage(
775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        'completeLogin', this.completeLogin_.bind(this));
785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    }
795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    document.addEventListener('DOMContentLoaded', this.onPageLoad_.bind(this));
81d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    document.addEventListener('enableSAML', this.onEnableSAML_.bind(this));
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  },
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  isGaiaMessage_: function(msg) {
8590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    // Not quite right, but good enough.
8690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    return this.gaiaUrl_.indexOf(msg.origin) == 0 ||
8790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)           this.GAIA_URL.indexOf(msg.origin) == 0;
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  },
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  isInternalMessage_: function(msg) {
914e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    return msg.origin == Authenticator.THIS_EXTENSION_ORIGIN;
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  },
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
94d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  isParentMessage_: function(msg) {
95d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    return msg.origin == this.parentPage_;
96d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  },
97d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
98a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  constructInitialFrameUrl_: function() {
99f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    var url = this.gaiaUrl_ + this.gaiaPath_;
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
101f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    url = appendParam(url, 'service', this.service_);
102f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    url = appendParam(url, 'continue', this.continueUrl_);
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (this.inputLang_)
104f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)      url = appendParam(url, 'hl', this.inputLang_);
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (this.inputEmail_)
106f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)      url = appendParam(url, 'Email', this.inputEmail_);
1075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (this.isConstrainedWindow_)
1085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      url = appendParam(url, 'source', this.CONSTRAINED_FLOW_SOURCE);
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return url;
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  },
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  onPageLoad_: function() {
1135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    window.addEventListener('message', this.onMessage.bind(this), false);
1145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.loadFrame_();
1155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  },
116a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)
1175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  loadFrame_: function() {
1185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    var gaiaFrame = $('gaia-frame');
1195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    gaiaFrame.src = this.initialFrameUrl_;
1205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (this.desktopMode_) {
1215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      var handler = function() {
1225d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        this.onLoginUILoaded_();
1235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        gaiaFrame.removeEventListener('load', handler);
1245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      }.bind(this);
1255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      gaiaFrame.addEventListener('load', handler);
1264e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)    }
1274e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)  },
1284e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)
1291e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  /**
1305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * Invoked when the login UI is initialized or reset.
131a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)   */
1325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  onLoginUILoaded_: function() {
133a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    var msg = {
1345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'method': 'loginUILoaded'
135a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    };
136a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    window.parent.postMessage(msg, this.parentPage_);
137a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  },
138a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)
1395d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  /**
1405d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * Invoked when the background script sends a message to indicate that the
1415d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * current content does not fit in a constrained window.
1425d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * @param {Object=} opt_extraMsg Optional extra info to send.
1435d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   */
1445d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  switchToFullTab_: function(msg) {
1455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    var parentMsg = {
1465d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'method': 'switchToFullTab',
1475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'url': msg.url
1485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    };
1495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    window.parent.postMessage(parentMsg, this.parentPage_);
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  },
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  /**
1535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * Invoked when the signin flow is complete.
1545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * @param {Object=} opt_extraMsg Optional extra info to send.
1555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   */
1565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  completeLogin_: function(opt_extraMsg) {
157d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    var msg = {
158d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      'method': 'completeLogin',
1595d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'email': (opt_extraMsg && opt_extraMsg.email) || this.email_,
1605d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'password': this.password_,
1615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'usingSAML': this.isSAMLFlow_,
1625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'chooseWhatToSync': this.chooseWhatToSync_ || false,
1635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'skipForNow': opt_extraMsg && opt_extraMsg.skipForNow,
1645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'sessionIndex': opt_extraMsg && opt_extraMsg.sessionIndex
165d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    };
166d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    window.parent.postMessage(msg, this.parentPage_);
1675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (this.isSAMLEnabled_)
1685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_.send({name: 'resetAuth'});
1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  },
1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
171d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  /**
172d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)   * Invoked when 'enableSAML' event is received to initialize SAML support.
173d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)   */
174d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  onEnableSAML_: function() {
1755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.isSAMLEnabled_ = true;
1765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.isSAMLFlow_ = false;
1775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
1785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (!this.supportChannel_) {
1795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_ = new Channel();
1805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_.connect('authMain');
1815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    }
182d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
1835d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.supportChannel_.registerMessage(
184d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)        'onAuthPageLoaded', this.onAuthPageLoaded_.bind(this));
1855d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.supportChannel_.registerMessage(
1865d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        'apiCall', this.onAPICall_.bind(this));
1875d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.supportChannel_.send({
188d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      name: 'setGaiaUrl',
189d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      gaiaUrl: this.gaiaUrl_
190d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    });
191d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  },
192d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
193d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  /**
194d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)   * Invoked when the background page sends 'onHostedPageLoaded' message.
195d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)   * @param {!Object} msg Details sent with the message.
196d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)   */
197d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  onAuthPageLoaded_: function(msg) {
1985d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    var isSAMLPage = msg.url.indexOf(this.gaiaUrl_) != 0;
1995d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2005d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (isSAMLPage && !this.isSAMLFlow_) {
2015d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      // GAIA redirected to a SAML login page. The credentials provided to this
2025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      // page will determine what user gets logged in. The credentials obtained
2035d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      // from the GAIA login from are no longer relevant and can be discarded.
2045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.isSAMLFlow_ = true;
2055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.email_ = null;
2065d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.password_ = null;
2075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    }
2085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
209d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    window.parent.postMessage({
210d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      'method': 'authPageLoaded',
2115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'isSAML': this.isSAMLFlow_,
2125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      'domain': extractDomain(msg.url)
213d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    }, this.parentPage_);
214d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  },
215d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
2165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  /**
2175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * Invoked when one of the credential passing API methods is called by a SAML
2185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * provider.
2195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   * @param {!Object} msg Details of the API call.
2205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)   */
2215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  onAPICall_: function(msg) {
2225d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    var call = msg.call;
2235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (call.method == 'add') {
2245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.apiToken_ = call.token;
2255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.email_ = call.user;
2265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.password_ = call.password;
2275d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    } else if (call.method == 'confirm') {
2285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      if (call.token != this.apiToken_)
2295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        console.error('Authenticator.onAPICall_: token mismatch');
2305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    } else {
2315d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      console.error('Authenticator.onAPICall_: unknown message');
232a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    }
2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  },
2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
235d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  onConfirmLogin_: function() {
2365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (!this.isSAMLFlow_) {
2375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.completeLogin_();
238d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      return;
239d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    }
240d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
2415d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    var apiUsed = !!this.password_;
2425d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2435d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    // Retrieve the e-mail address of the user who just authenticated from GAIA.
2445d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    window.parent.postMessage({method: 'retrieveAuthenticatedUserEmail',
2455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                               attemptToken: this.attemptToken_,
2465d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                               apiUsed: apiUsed},
2475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                              this.parentPage_);
2485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (!apiUsed) {
2505d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.supportChannel_.sendWithCallback(
2515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)          {name: 'getScrapedPasswords'},
2525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)          function(passwords) {
2535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)            if (passwords.length == 0) {
2545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)              window.parent.postMessage(
2555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                  {method: 'noPassword', email: this.email_},
2565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                  this.parentPage_);
2575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)            } else {
2585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)              window.parent.postMessage({method: 'confirmPassword',
2595d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                                         email: this.email_,
2605d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                                         passwordCount: passwords.length},
2615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                                        this.parentPage_);
2625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)            }
2635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)          }.bind(this));
2645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    }
2655d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  },
2665d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  maybeCompleteSAMLLogin_: function() {
2685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    // SAML login is complete when the user's e-mail address has been retrieved
2695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    // from GAIA and the user has successfully confirmed the password.
2705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    if (this.email_ !== null && this.password_ !== null)
2715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.completeLogin_();
272d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  },
273d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
274d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  onVerifyConfirmedPassword_: function(password) {
2755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    this.supportChannel_.sendWithCallback(
276d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)        {name: 'getScrapedPasswords'},
277d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)        function(passwords) {
278d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)          for (var i = 0; i < passwords.length; ++i) {
279d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)            if (passwords[i] == password) {
2805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)              this.password_ = passwords[i];
2815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)              this.maybeCompleteSAMLLogin_();
282d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)              return;
283d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)            }
284d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)          }
285a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)          window.parent.postMessage(
286a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)              {method: 'confirmPassword', email: this.email_},
287a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)              this.parentPage_);
288d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)        }.bind(this));
289d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  },
290d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)
2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  onMessage: function(e) {
2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    var msg = e.data;
2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (msg.method == 'attemptLogin' && this.isGaiaMessage_(e)) {
2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this.email_ = msg.email;
2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this.password_ = msg.password;
2965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this.attemptToken_ = msg.attemptToken;
2975d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.chooseWhatToSync_ = msg.chooseWhatToSync;
2985d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.isSAMLFlow_ = false;
2995d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      if (this.isSAMLEnabled_)
3005d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        this.supportChannel_.send({name: 'startAuth'});
3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else if (msg.method == 'clearOldAttempts' && this.isGaiaMessage_(e)) {
3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this.email_ = null;
3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this.password_ = null;
3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this.attemptToken_ = null;
3055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.isSAMLFlow_ = false;
3065d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      this.onLoginUILoaded_();
3075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      if (this.isSAMLEnabled_)
3085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        this.supportChannel_.send({name: 'resetAuth'});
3095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    } else if (msg.method == 'setAuthenticatedUserEmail' &&
3105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)               this.isParentMessage_(e)) {
3115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      if (this.attemptToken_ == msg.attemptToken) {
3125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        this.email_ = msg.email;
3135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        this.maybeCompleteSAMLLogin_();
3145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      }
3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else if (msg.method == 'confirmLogin' && this.isInternalMessage_(e)) {
316d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      if (this.attemptToken_ == msg.attemptToken)
317d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)        this.onConfirmLogin_();
318d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      else
319d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)        console.error('Authenticator.onMessage: unexpected attemptToken!?');
320d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    } else if (msg.method == 'verifyConfirmedPassword' &&
321d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)               this.isParentMessage_(e)) {
322d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)      this.onVerifyConfirmedPassword_(msg.password);
3231e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    } else if (msg.method == 'navigate' &&
3241e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)               this.isParentMessage_(e)) {
3255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      $('gaia-frame').src = msg.src;
3265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    } else if (msg.method == 'redirectToSignin' &&
3275d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)               this.isParentMessage_(e)) {
3285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      $('gaia-frame').src = this.constructInitialFrameUrl_();
3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
3305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)       console.error('Authenticator.onMessage: unknown message + origin!?');
3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Authenticator.getInstance().initialize();
336