@@ -18,8 +18,10 @@ limitations under the License.
1818*/
1919
2020import Matrix from 'matrix-js-sdk' ;
21+ import { InvalidStoreError } from "matrix-js-sdk/src/errors" ;
22+ import { MatrixClient } from "matrix-js-sdk/src/client" ;
2123
22- import { MatrixClientPeg } from './MatrixClientPeg' ;
24+ import { IMatrixClientCreds , MatrixClientPeg } from './MatrixClientPeg' ;
2325import EventIndexPeg from './indexing/EventIndexPeg' ;
2426import createMatrixClient from './utils/createMatrixClient' ;
2527import Analytics from './Analytics' ;
@@ -47,44 +49,46 @@ import ThreepidInviteStore from "./stores/ThreepidInviteStore";
4749const HOMESERVER_URL_KEY = "mx_hs_url" ;
4850const ID_SERVER_URL_KEY = "mx_is_url" ;
4951
52+ interface ILoadSessionOpts {
53+ enableGuest ?: boolean ;
54+ guestHsUrl ?: string ;
55+ guestIsUrl ?: string ;
56+ ignoreGuest ?: boolean ;
57+ defaultDeviceDisplayName ?: string ;
58+ fragmentQueryParams ?: Record < string , string > ;
59+ }
60+
5061/**
5162 * Called at startup, to attempt to build a logged-in Matrix session. It tries
5263 * a number of things:
5364 *
54- *
5565 * 1. if we have a guest access token in the fragment query params, it uses
5666 * that.
57- *
5867 * 2. if an access token is stored in local storage (from a previous session),
5968 * it uses that.
60- *
6169 * 3. it attempts to auto-register as a guest user.
6270 *
6371 * If any of steps 1-4 are successful, it will call {_doSetLoggedIn}, which in
6472 * turn will raise on_logged_in and will_start_client events.
6573 *
66- * @param {object } opts
67- *
68- * @param {object } opts.fragmentQueryParams: string->string map of the
74+ * @param {object } [opts]
75+ * @param {object } [opts.fragmentQueryParams]: string->string map of the
6976 * query-parameters extracted from the #-fragment of the starting URI.
70- *
71- * @param {boolean } opts.enableGuest: set to true to enable guest access tokens
72- * and auto-guest registrations.
73- *
74- * @params {string} opts.guestHsUrl: homeserver URL. Only used if enableGuest is
75- * true; defines the HS to register against.
76- *
77- * @params {string} opts.guestIsUrl: homeserver URL. Only used if enableGuest is
78- * true; defines the IS to use.
79- *
80- * @params {bool} opts.ignoreGuest: If the stored session is a guest account, ignore
81- * it and don't load it.
82- *
77+ * @param {boolean } [opts.enableGuest]: set to true to enable guest access
78+ * tokens and auto-guest registrations.
79+ * @param {string } [opts.guestHsUrl]: homeserver URL. Only used if enableGuest
80+ * is true; defines the HS to register against.
81+ * @param {string } [opts.guestIsUrl]: homeserver URL. Only used if enableGuest
82+ * is true; defines the IS to use.
83+ * @param {bool } [opts.ignoreGuest]: If the stored session is a guest account,
84+ * ignore it and don't load it.
85+ * @param {string } [opts.defaultDeviceDisplayName]: Default display name to use
86+ * when registering as a guest.
8387 * @returns {Promise } a promise which resolves when the above process completes.
8488 * Resolves to `true` if we ended up starting a session, or `false` if we
8589 * failed.
8690 */
87- export async function loadSession ( opts ) {
91+ export async function loadSession ( opts : ILoadSessionOpts = { } ) : Promise < boolean > {
8892 try {
8993 let enableGuest = opts . enableGuest || false ;
9094 const guestHsUrl = opts . guestHsUrl ;
@@ -97,10 +101,11 @@ export async function loadSession(opts) {
97101 enableGuest = false ;
98102 }
99103
100- if ( enableGuest &&
104+ if (
105+ enableGuest &&
101106 fragmentQueryParams . guest_user_id &&
102107 fragmentQueryParams . guest_access_token
103- ) {
108+ ) {
104109 console . log ( "Using guest access credentials" ) ;
105110 return _doSetLoggedIn ( {
106111 userId : fragmentQueryParams . guest_user_id ,
@@ -139,7 +144,7 @@ export async function loadSession(opts) {
139144 * is associated with them. The session is not loaded.
140145 * @returns {String } The persisted session's owner, if an owner exists. Null otherwise.
141146 */
142- export function getStoredSessionOwner ( ) {
147+ export function getStoredSessionOwner ( ) : string {
143148 const { hsUrl, userId, accessToken} = getLocalStorageSessionVars ( ) ;
144149 return hsUrl && userId && accessToken ? userId : null ;
145150}
@@ -148,7 +153,7 @@ export function getStoredSessionOwner() {
148153 * @returns {bool } True if the stored session is for a guest user or false if it is
149154 * for a real user. If there is no stored session, return null.
150155 */
151- export function getStoredSessionIsGuest ( ) {
156+ export function getStoredSessionIsGuest ( ) : boolean {
152157 const sessVars = getLocalStorageSessionVars ( ) ;
153158 return sessVars . hsUrl && sessVars . userId && sessVars . accessToken ? sessVars . isGuest : null ;
154159}
@@ -163,7 +168,10 @@ export function getStoredSessionIsGuest() {
163168 * @returns {Promise } promise which resolves to true if we completed the token
164169 * login, else false
165170 */
166- export function attemptTokenLogin ( queryParams , defaultDeviceDisplayName ) {
171+ export function attemptTokenLogin (
172+ queryParams : Record < string , string > ,
173+ defaultDeviceDisplayName ?: string ,
174+ ) : Promise < boolean > {
167175 if ( ! queryParams . loginToken ) {
168176 return Promise . resolve ( false ) ;
169177 }
@@ -187,7 +195,7 @@ export function attemptTokenLogin(queryParams, defaultDeviceDisplayName) {
187195 return _clearStorage ( ) . then ( ( ) => {
188196 _persistCredentialsToLocalStorage ( creds ) ;
189197 // remember that we just logged in
190- sessionStorage . setItem ( "mx_fresh_login" , true ) ;
198+ sessionStorage . setItem ( "mx_fresh_login" , String ( true ) ) ;
191199 return true ;
192200 } ) ;
193201 } ) . catch ( ( err ) => {
@@ -197,8 +205,8 @@ export function attemptTokenLogin(queryParams, defaultDeviceDisplayName) {
197205 } ) ;
198206}
199207
200- export function handleInvalidStoreError ( e ) {
201- if ( e . reason === Matrix . InvalidStoreError . TOGGLED_LAZY_LOADING ) {
208+ export function handleInvalidStoreError ( e : InvalidStoreError ) : Promise < void > {
209+ if ( e . reason === InvalidStoreError . TOGGLED_LAZY_LOADING ) {
202210 return Promise . resolve ( ) . then ( ( ) => {
203211 const lazyLoadEnabled = e . value ;
204212 if ( lazyLoadEnabled ) {
@@ -231,7 +239,11 @@ export function handleInvalidStoreError(e) {
231239 }
232240}
233241
234- function _registerAsGuest ( hsUrl , isUrl , defaultDeviceDisplayName ) {
242+ function _registerAsGuest (
243+ hsUrl : string ,
244+ isUrl : string ,
245+ defaultDeviceDisplayName : string ,
246+ ) : Promise < boolean > {
235247 console . log ( `Doing guest login on ${ hsUrl } ` ) ;
236248
237249 // create a temporary MatrixClient to do the login
@@ -259,12 +271,21 @@ function _registerAsGuest(hsUrl, isUrl, defaultDeviceDisplayName) {
259271 } ) ;
260272}
261273
274+ export interface ILocalStorageSession {
275+ hsUrl : string ;
276+ isUrl : string ;
277+ accessToken : string ;
278+ userId : string ;
279+ deviceId : string ;
280+ isGuest : boolean ;
281+ }
282+
262283/**
263284 * Retrieves information about the stored session in localstorage. The session
264285 * may not be valid, as it is not tested for consistency here.
265286 * @returns {Object } Information about the session - see implementation for variables.
266287 */
267- export function getLocalStorageSessionVars ( ) {
288+ export function getLocalStorageSessionVars ( ) : ILocalStorageSession {
268289 const hsUrl = localStorage . getItem ( HOMESERVER_URL_KEY ) ;
269290 const isUrl = localStorage . getItem ( ID_SERVER_URL_KEY ) ;
270291 const accessToken = localStorage . getItem ( "mx_access_token" ) ;
@@ -292,8 +313,8 @@ export function getLocalStorageSessionVars() {
292313// The plan is to gradually move the localStorage access done here into
293314// SessionStore to avoid bugs where the view becomes out-of-sync with
294315// localStorage (e.g. isGuest etc.)
295- async function _restoreFromLocalStorage ( opts ) {
296- const ignoreGuest = opts . ignoreGuest ;
316+ async function _restoreFromLocalStorage ( opts ?: { ignoreGuest ?: boolean } ) : Promise < boolean > {
317+ const ignoreGuest = opts ? .ignoreGuest ;
297318
298319 if ( ! localStorage ) {
299320 return false ;
@@ -314,7 +335,7 @@ async function _restoreFromLocalStorage(opts) {
314335 console . log ( "No pickle key available" ) ;
315336 }
316337
317- const freshLogin = sessionStorage . getItem ( "mx_fresh_login" ) ;
338+ const freshLogin = sessionStorage . getItem ( "mx_fresh_login" ) === "true" ;
318339 sessionStorage . removeItem ( "mx_fresh_login" ) ;
319340
320341 console . log ( `Restoring session for ${ userId } ` ) ;
@@ -335,7 +356,7 @@ async function _restoreFromLocalStorage(opts) {
335356 }
336357}
337358
338- async function _handleLoadSessionFailure ( e ) {
359+ async function _handleLoadSessionFailure ( e : Error ) : Promise < boolean > {
339360 console . error ( "Unable to load session" , e ) ;
340361
341362 const SessionRestoreErrorDialog =
@@ -369,12 +390,12 @@ async function _handleLoadSessionFailure(e) {
369390 *
370391 * @returns {Promise } promise which resolves to the new MatrixClient once it has been started
371392 */
372- export async function setLoggedIn ( credentials ) {
393+ export async function setLoggedIn ( credentials : IMatrixClientCreds ) : Promise < MatrixClient > {
373394 credentials . freshLogin = true ;
374395 stopMatrixClient ( ) ;
375396 const pickleKey = credentials . userId && credentials . deviceId
376- ? await PlatformPeg . get ( ) . createPickleKey ( credentials . userId , credentials . deviceId )
377- : null ;
397+ ? await PlatformPeg . get ( ) . createPickleKey ( credentials . userId , credentials . deviceId )
398+ : null ;
378399
379400 if ( pickleKey ) {
380401 console . log ( "Created pickle key" ) ;
@@ -400,7 +421,7 @@ export async function setLoggedIn(credentials) {
400421 *
401422 * @returns {Promise } promise which resolves to the new MatrixClient once it has been started
402423 */
403- export function hydrateSession ( credentials ) {
424+ export function hydrateSession ( credentials : IMatrixClientCreds ) : Promise < MatrixClient > {
404425 const oldUserId = MatrixClientPeg . get ( ) . getUserId ( ) ;
405426 const oldDeviceId = MatrixClientPeg . get ( ) . getDeviceId ( ) ;
406427
@@ -425,7 +446,10 @@ export function hydrateSession(credentials) {
425446 *
426447 * @returns {Promise } promise which resolves to the new MatrixClient once it has been started
427448 */
428- async function _doSetLoggedIn ( credentials , clearStorage ) {
449+ async function _doSetLoggedIn (
450+ credentials : IMatrixClientCreds ,
451+ clearStorage : boolean ,
452+ ) : Promise < MatrixClient > {
429453 credentials . guest = Boolean ( credentials . guest ) ;
430454
431455 const softLogout = isSoftLogout ( ) ;
@@ -514,7 +538,7 @@ async function _doSetLoggedIn(credentials, clearStorage) {
514538 return client ;
515539}
516540
517- function _showStorageEvictedDialog ( ) {
541+ function _showStorageEvictedDialog ( ) : Promise < boolean > {
518542 const StorageEvictedDialog = sdk . getComponent ( 'views.dialogs.StorageEvictedDialog' ) ;
519543 return new Promise ( resolve => {
520544 Modal . createTrackedDialog ( 'Storage evicted' , '' , StorageEvictedDialog , {
@@ -527,7 +551,7 @@ function _showStorageEvictedDialog() {
527551// `instanceof`. Babel 7 supports this natively in their class handling.
528552class AbortLoginAndRebuildStorage extends Error { }
529553
530- function _persistCredentialsToLocalStorage ( credentials ) {
554+ function _persistCredentialsToLocalStorage ( credentials : IMatrixClientCreds ) : void {
531555 localStorage . setItem ( HOMESERVER_URL_KEY , credentials . homeserverUrl ) ;
532556 if ( credentials . identityServerUrl ) {
533557 localStorage . setItem ( ID_SERVER_URL_KEY , credentials . identityServerUrl ) ;
@@ -537,7 +561,7 @@ function _persistCredentialsToLocalStorage(credentials) {
537561 localStorage . setItem ( "mx_is_guest" , JSON . stringify ( credentials . guest ) ) ;
538562
539563 if ( credentials . pickleKey ) {
540- localStorage . setItem ( "mx_has_pickle_key" , true ) ;
564+ localStorage . setItem ( "mx_has_pickle_key" , String ( true ) ) ;
541565 } else {
542566 if ( localStorage . getItem ( "mx_has_pickle_key" ) ) {
543567 console . error ( "Expected a pickle key, but none provided. Encryption may not work." ) ;
@@ -561,7 +585,7 @@ let _isLoggingOut = false;
561585/**
562586 * Logs the current session out and transitions to the logged-out state
563587 */
564- export function logout ( ) {
588+ export function logout ( ) : void {
565589 if ( ! MatrixClientPeg . get ( ) ) return ;
566590
567591 if ( MatrixClientPeg . get ( ) . isGuest ( ) ) {
@@ -590,7 +614,7 @@ export function logout() {
590614 ) ;
591615}
592616
593- export function softLogout ( ) {
617+ export function softLogout ( ) : void {
594618 if ( ! MatrixClientPeg . get ( ) ) return ;
595619
596620 // Track that we've detected and trapped a soft logout. This helps prevent other
@@ -611,11 +635,11 @@ export function softLogout() {
611635 // DO NOT CALL LOGOUT. A soft logout preserves data, logout does not.
612636}
613637
614- export function isSoftLogout ( ) {
638+ export function isSoftLogout ( ) : boolean {
615639 return localStorage . getItem ( "mx_soft_logout" ) === "true" ;
616640}
617641
618- export function isLoggingOut ( ) {
642+ export function isLoggingOut ( ) : boolean {
619643 return _isLoggingOut ;
620644}
621645
@@ -625,7 +649,7 @@ export function isLoggingOut() {
625649 * @param {boolean } startSyncing True (default) to actually start
626650 * syncing the client.
627651 */
628- async function startMatrixClient ( startSyncing = true ) {
652+ async function startMatrixClient ( startSyncing = true ) : Promise < void > {
629653 console . log ( `Lifecycle: Starting MatrixClient` ) ;
630654
631655 // dispatch this before starting the matrix client: it's used
@@ -684,7 +708,7 @@ async function startMatrixClient(startSyncing=true) {
684708 * Stops a running client and all related services, and clears persistent
685709 * storage. Used after a session has been logged out.
686710 */
687- export async function onLoggedOut ( ) {
711+ export async function onLoggedOut ( ) : Promise < void > {
688712 _isLoggingOut = false ;
689713 // Ensure that we dispatch a view change **before** stopping the client so
690714 // so that React components unmount first. This avoids React soft crashes
@@ -698,7 +722,7 @@ export async function onLoggedOut() {
698722 * @param {object } opts Options for how to clear storage.
699723 * @returns {Promise } promise which resolves once the stores have been cleared
700724 */
701- async function _clearStorage ( opts : { deleteEverything : boolean } ) {
725+ async function _clearStorage ( opts ? : { deleteEverything ? : boolean } ) : Promise < void > {
702726 Analytics . disable ( ) ;
703727
704728 if ( window . localStorage ) {
@@ -736,7 +760,7 @@ async function _clearStorage(opts: {deleteEverything: boolean}) {
736760 * @param {boolean } unsetClient True (default) to abandon the client
737761 * on MatrixClientPeg after stopping.
738762 */
739- export function stopMatrixClient ( unsetClient = true ) {
763+ export function stopMatrixClient ( unsetClient = true ) : void {
740764 Notifier . stop ( ) ;
741765 UserActivity . sharedInstance ( ) . stop ( ) ;
742766 TypingStore . sharedInstance ( ) . reset ( ) ;
0 commit comments