Merge pull request #3610 from matrix-org/jryans/alias-cache
Improve room switching performance with alias cache
This commit is contained in:
commit
c9ca8b9869
3 changed files with 81 additions and 29 deletions
35
src/RoomAliasCache.js
Normal file
35
src/RoomAliasCache.js
Normal file
|
@ -0,0 +1,35 @@
|
||||||
|
/*
|
||||||
|
Copyright 2019 The Matrix.org Foundation C.I.C.
|
||||||
|
|
||||||
|
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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This is meant to be a cache of room alias to room ID so that moving between
|
||||||
|
* rooms happens smoothly (for example using browser back / forward buttons).
|
||||||
|
*
|
||||||
|
* For the moment, it's in memory only and so only applies for the current
|
||||||
|
* session for simplicity, but could be extended further in the future.
|
||||||
|
*
|
||||||
|
* A similar thing could also be achieved via `pushState` with a state object,
|
||||||
|
* but keeping it separate like this seems easier in case we do want to extend.
|
||||||
|
*/
|
||||||
|
const aliasToIDMap = new Map();
|
||||||
|
|
||||||
|
export function storeRoomAliasInCache(alias, id) {
|
||||||
|
aliasToIDMap.set(alias, id);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getCachedRoomIDForAlias(alias) {
|
||||||
|
return aliasToIDMap.get(alias);
|
||||||
|
}
|
|
@ -60,6 +60,7 @@ import AutoDiscoveryUtils from "../../utils/AutoDiscoveryUtils";
|
||||||
import DMRoomMap from '../../utils/DMRoomMap';
|
import DMRoomMap from '../../utils/DMRoomMap';
|
||||||
import { countRoomsWithNotif } from '../../RoomNotifs';
|
import { countRoomsWithNotif } from '../../RoomNotifs';
|
||||||
import { setTheme } from "../../theme";
|
import { setTheme } from "../../theme";
|
||||||
|
import { storeRoomAliasInCache } from '../../RoomAliasCache';
|
||||||
|
|
||||||
// Disable warnings for now: we use deprecated bluebird functions
|
// Disable warnings for now: we use deprecated bluebird functions
|
||||||
// and need to migrate, but they spam the console with warnings.
|
// and need to migrate, but they spam the console with warnings.
|
||||||
|
@ -866,7 +867,12 @@ export default createReactClass({
|
||||||
const room = MatrixClientPeg.get().getRoom(roomInfo.room_id);
|
const room = MatrixClientPeg.get().getRoom(roomInfo.room_id);
|
||||||
if (room) {
|
if (room) {
|
||||||
const theAlias = Rooms.getDisplayAliasForRoom(room);
|
const theAlias = Rooms.getDisplayAliasForRoom(room);
|
||||||
if (theAlias) presentedId = theAlias;
|
if (theAlias) {
|
||||||
|
presentedId = theAlias;
|
||||||
|
// Store display alias of the presented room in cache to speed future
|
||||||
|
// navigation.
|
||||||
|
storeRoomAliasInCache(theAlias, room.roomId);
|
||||||
|
}
|
||||||
|
|
||||||
// Store this as the ID of the last room accessed. This is so that we can
|
// Store this as the ID of the last room accessed. This is so that we can
|
||||||
// persist which room is being stored across refreshes and browser quits.
|
// persist which room is being stored across refreshes and browser quits.
|
||||||
|
|
|
@ -20,6 +20,7 @@ import MatrixClientPeg from '../MatrixClientPeg';
|
||||||
import sdk from '../index';
|
import sdk from '../index';
|
||||||
import Modal from '../Modal';
|
import Modal from '../Modal';
|
||||||
import { _t } from '../languageHandler';
|
import { _t } from '../languageHandler';
|
||||||
|
import { getCachedRoomIDForAlias, storeRoomAliasInCache } from '../RoomAliasCache';
|
||||||
|
|
||||||
const INITIAL_STATE = {
|
const INITIAL_STATE = {
|
||||||
// Whether we're joining the currently viewed room (see isJoining())
|
// Whether we're joining the currently viewed room (see isJoining())
|
||||||
|
@ -137,7 +138,7 @@ class RoomViewStore extends Store {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
_viewRoom(payload) {
|
async _viewRoom(payload) {
|
||||||
if (payload.room_id) {
|
if (payload.room_id) {
|
||||||
const newState = {
|
const newState = {
|
||||||
roomId: payload.room_id,
|
roomId: payload.room_id,
|
||||||
|
@ -176,34 +177,44 @@ class RoomViewStore extends Store {
|
||||||
this._joinRoom(payload);
|
this._joinRoom(payload);
|
||||||
}
|
}
|
||||||
} else if (payload.room_alias) {
|
} else if (payload.room_alias) {
|
||||||
// Resolve the alias and then do a second dispatch with the room ID acquired
|
// Try the room alias to room ID navigation cache first to avoid
|
||||||
this._setState({
|
// blocking room navigation on the homeserver.
|
||||||
roomId: null,
|
let roomId = getCachedRoomIDForAlias(payload.room_alias);
|
||||||
initialEventId: null,
|
if (!roomId) {
|
||||||
initialEventPixelOffset: null,
|
// Room alias cache miss, so let's ask the homeserver. Resolve the alias
|
||||||
isInitialEventHighlighted: null,
|
// and then do a second dispatch with the room ID acquired.
|
||||||
roomAlias: payload.room_alias,
|
this._setState({
|
||||||
roomLoading: true,
|
roomId: null,
|
||||||
roomLoadError: null,
|
initialEventId: null,
|
||||||
});
|
initialEventPixelOffset: null,
|
||||||
MatrixClientPeg.get().getRoomIdForAlias(payload.room_alias).done(
|
isInitialEventHighlighted: null,
|
||||||
(result) => {
|
roomAlias: payload.room_alias,
|
||||||
dis.dispatch({
|
roomLoading: true,
|
||||||
action: 'view_room',
|
roomLoadError: null,
|
||||||
room_id: result.room_id,
|
|
||||||
event_id: payload.event_id,
|
|
||||||
highlighted: payload.highlighted,
|
|
||||||
room_alias: payload.room_alias,
|
|
||||||
auto_join: payload.auto_join,
|
|
||||||
oob_data: payload.oob_data,
|
|
||||||
});
|
|
||||||
}, (err) => {
|
|
||||||
dis.dispatch({
|
|
||||||
action: 'view_room_error',
|
|
||||||
room_id: null,
|
|
||||||
room_alias: payload.room_alias,
|
|
||||||
err: err,
|
|
||||||
});
|
});
|
||||||
|
try {
|
||||||
|
const result = await MatrixClientPeg.get().getRoomIdForAlias(payload.room_alias);
|
||||||
|
storeRoomAliasInCache(payload.room_alias, result.room_id);
|
||||||
|
roomId = result.room_id;
|
||||||
|
} catch (err) {
|
||||||
|
dis.dispatch({
|
||||||
|
action: 'view_room_error',
|
||||||
|
room_id: null,
|
||||||
|
room_alias: payload.room_alias,
|
||||||
|
err,
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
dis.dispatch({
|
||||||
|
action: 'view_room',
|
||||||
|
room_id: roomId,
|
||||||
|
event_id: payload.event_id,
|
||||||
|
highlighted: payload.highlighted,
|
||||||
|
room_alias: payload.room_alias,
|
||||||
|
auto_join: payload.auto_join,
|
||||||
|
oob_data: payload.oob_data,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue