Revert merge up from develop

This commit is contained in:
wmwragg 2016-07-27 14:16:17 +01:00
parent 6d141d1a7b
commit 3df746ef14
7 changed files with 130 additions and 143 deletions

View file

@ -13,7 +13,7 @@
"reskindex": "./reskindex.js"
},
"scripts": {
"reskindex": "reskindex -h header",
"reskindex": "./reskindex.js -h header",
"build": "babel src -d lib --source-maps --stage 1",
"start": "babel src -w -d lib --source-maps --stage 1",
"lint": "eslint src/",
@ -42,10 +42,10 @@
"matrix-js-sdk": "matrix-org/matrix-js-sdk#develop",
"optimist": "^0.6.1",
"q": "^1.4.1",
"react": "^15.0.1",
"react-addons-css-transition-group": "^15.1.0",
"react-dom": "^15.0.1",
"react-gemini-scrollbar": "matrix-org/react-gemini-scrollbar#c3d942e",
"react": "^15.2.1",
"react-addons-css-transition-group": "^15.2.1",
"react-dom": "^15.2.1",
"react-gemini-scrollbar": "matrix-org/react-gemini-scrollbar#dbf0abf",
"sanitize-html": "^1.11.1",
"velocity-vector": "vector-im/velocity#059e3b2",
"whatwg-fetch": "^1.0.0"

View file

@ -1,51 +0,0 @@
/*
Copyright 2015 OpenMarket Ltd
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.
*/
const IS_GUEST_KEY = "matrix-is-guest";
class GuestAccess {
constructor(localStorage) {
this.localStorage = localStorage;
try {
this._isGuest = localStorage.getItem(IS_GUEST_KEY) === "true";
}
catch (e) {} // don't care
}
setPeekedRoom(roomId) {
// we purposefully do not persist this to local storage as peeking is
// entirely transient.
this._peekedRoomId = roomId;
}
getPeekedRoom() {
return this._peekedRoomId;
}
isGuest() {
return this._isGuest;
}
markAsGuest(isGuest) {
try {
this.localStorage.setItem(IS_GUEST_KEY, JSON.stringify(isGuest));
} catch (e) {} // ignore. If they don't do LS, they'll just get a new account.
this._isGuest = isGuest;
this._peekedRoomId = null;
}
}
module.exports = GuestAccess;

View file

@ -16,13 +16,9 @@ limitations under the License.
'use strict';
// A thing that holds your Matrix Client
var Matrix = require("matrix-js-sdk");
var GuestAccess = require("./GuestAccess");
import Matrix from 'matrix-js-sdk';
let matrixClient: MatrixClient = null;
var localStorage = window.localStorage;
const localStorage = window.localStorage;
function deviceId() {
// XXX: is Math.random()'s deterministicity a problem here?
@ -35,82 +31,42 @@ function deviceId() {
return id;
}
function createClientForPeg(hs_url, is_url, user_id, access_token, guestAccess) {
var opts = {
baseUrl: hs_url,
idBaseUrl: is_url,
accessToken: access_token,
userId: user_id,
timelineSupport: true,
};
if (localStorage) {
opts.sessionStore = new Matrix.WebStorageSessionStore(localStorage);
opts.deviceId = deviceId();
}
matrixClient = Matrix.createClient(opts);
// we're going to add eventlisteners for each matrix event tile, so the
// potential number of event listeners is quite high.
matrixClient.setMaxListeners(500);
if (guestAccess) {
console.log("Guest: %s", guestAccess.isGuest());
matrixClient.setGuest(guestAccess.isGuest());
var peekedRoomId = guestAccess.getPeekedRoom();
if (peekedRoomId) {
console.log("Peeking in room %s", peekedRoomId);
matrixClient.peekInRoom(peekedRoomId);
}
}
}
if (localStorage) {
var hs_url = localStorage.getItem("mx_hs_url");
var is_url = localStorage.getItem("mx_is_url") || 'https://matrix.org';
var access_token = localStorage.getItem("mx_access_token");
var user_id = localStorage.getItem("mx_user_id");
var guestAccess = new GuestAccess(localStorage);
if (access_token && user_id && hs_url) {
console.log("Restoring session for %s", user_id);
createClientForPeg(hs_url, is_url, user_id, access_token, guestAccess);
}
else {
console.log("Session not found.");
}
}
class MatrixClient {
constructor(guestAccess) {
this.guestAccess = guestAccess;
/**
* Wrapper object for handling the js-sdk Matrix Client object in the react-sdk
* Handles the creation/initialisation of client objects.
* This module provides a singleton instance of this class so the 'current'
* Matrix Client object is available easily.
*/
class MatrixClientPeg {
constructor() {
this.matrixClient = null;
}
get(): MatrixClient {
return matrixClient;
return this.matrixClient;
}
unset() {
matrixClient = null;
this.matrixClient = null;
}
// FIXME, XXX: this all seems very convoluted :(
//
// Why do we have this peg wrapper rather than just MatrixClient.get()?
// Why do we name MatrixClient as MatrixClientPeg when we export it?
//
// -matthew
/**
* Replace this MatrixClientPeg's client with a client instance that has
* Home Server / Identity Server URLs but no credentials
*/
replaceUsingUrls(hs_url, is_url) {
this.replaceClient(hs_url, is_url);
this._replaceClient(hs_url, is_url);
}
/**
* Replace this MatrixClientPeg's client with a client instance that has
* Home Server / Identity Server URLs and active credentials
*/
replaceUsingAccessToken(hs_url, is_url, user_id, access_token, isGuest) {
this.replaceClient(hs_url, is_url, user_id, access_token, isGuest);
this._replaceClient(hs_url, is_url, user_id, access_token, isGuest);
}
replaceClient(hs_url, is_url, user_id, access_token, isGuest) {
_replaceClient(hs_url, is_url, user_id, access_token, isGuest) {
if (localStorage) {
try {
localStorage.clear();
@ -118,15 +74,19 @@ class MatrixClient {
console.warn("Error clearing local storage", e);
}
}
this.guestAccess.markAsGuest(Boolean(isGuest));
createClientForPeg(hs_url, is_url, user_id, access_token, this.guestAccess);
this._createClient(hs_url, is_url, user_id, access_token, isGuest);
if (localStorage) {
try {
localStorage.setItem("mx_hs_url", hs_url);
localStorage.setItem("mx_is_url", is_url);
localStorage.setItem("mx_user_id", user_id);
localStorage.setItem("mx_access_token", access_token);
console.log("Session persisted for %s", user_id);
if (user_id !== undefined && access_token !== undefined) {
localStorage.setItem("mx_user_id", user_id);
localStorage.setItem("mx_access_token", access_token);
localStorage.setItem("mx_is_guest", JSON.stringify(isGuest));
console.log("Session persisted for %s", user_id);
}
} catch (e) {
console.warn("Error using local storage: can't persist session!", e);
}
@ -134,9 +94,68 @@ class MatrixClient {
console.warn("No local storage available: can't persist session!");
}
}
getCredentials() {
return [
this.matrixClient.baseUrl,
this.matrixClient.idBaseUrl,
this.matrixClient.credentials.userId,
this.matrixClient.getAccessToken(),
this.matrixClient.isGuest(),
];
}
tryRestore() {
if (localStorage) {
const hs_url = localStorage.getItem("mx_hs_url");
const is_url = localStorage.getItem("mx_is_url") || 'https://matrix.org';
const access_token = localStorage.getItem("mx_access_token");
const user_id = localStorage.getItem("mx_user_id");
let is_guest;
if (localStorage.getItem("mx_is_guest") !== null) {
is_guest = localStorage.getItem("mx_is_guest") === "true";
} else {
// legacy key name
is_guest = localStorage.getItem("matrix-is-guest") === "true";
}
if (access_token && user_id && hs_url) {
console.log("Restoring session for %s", user_id);
this._createClient(hs_url, is_url, user_id, access_token);
this.matrixClient.setGuest(is_guest);
} else {
console.log("Session not found.");
}
}
}
_createClient(hs_url, is_url, user_id, access_token, isGuest) {
var opts = {
baseUrl: hs_url,
idBaseUrl: is_url,
accessToken: access_token,
userId: user_id,
timelineSupport: true,
};
if (localStorage) {
opts.sessionStore = new Matrix.WebStorageSessionStore(localStorage);
opts.deviceId = deviceId();
}
this.matrixClient = Matrix.createClient(opts);
// we're going to add eventlisteners for each matrix event tile, so the
// potential number of event listeners is quite high.
this.matrixClient.setMaxListeners(500);
this.matrixClient.setGuest(Boolean(isGuest));
}
}
if (!global.mxMatrixClient) {
global.mxMatrixClient = new MatrixClient(new GuestAccess(localStorage));
if (!global.mxMatrixClientPeg) {
global.mxMatrixClientPeg = new MatrixClientPeg();
global.mxMatrixClientPeg.tryRestore();
}
module.exports = global.mxMatrixClient;
module.exports = global.mxMatrixClientPeg;

View file

@ -341,7 +341,12 @@ class TabComplete {
}
if (a.kind == 'member') {
return this.memberTabOrder[b.member.userId] - this.memberTabOrder[a.member.userId];
let orderA = this.memberTabOrder[a.member.userId];
let orderB = this.memberTabOrder[b.member.userId];
if (orderA === undefined) orderA = -1;
if (orderB === undefined) orderB = -1;
return orderB - orderA;
}
// anything else we have no ordering for

View file

@ -493,6 +493,17 @@ module.exports = React.createClass({
return;
}
if (this.props.ConferenceHandler &&
member.userId === this.props.ConferenceHandler.getConferenceUserIdForRoom(member.roomId)) {
this._updateConfCallNotification();
}
this._updateRoomMembers();
},
// rate limited because a power level change will emit an event for every
// member in the room.
_updateRoomMembers: new rate_limited_func(function() {
// a member state changed in this room, refresh the tab complete list
this.tabComplete.loadEntries(this.state.room);
this._updateAutoComplete();
@ -506,12 +517,7 @@ module.exports = React.createClass({
joining: false
});
}
if (this.props.ConferenceHandler &&
member.userId === this.props.ConferenceHandler.getConferenceUserIdForRoom(member.roomId)) {
this._updateConfCallNotification();
}
},
}, 500),
_hasUnsentMessages: function(room) {
return this._getUnsentMessages(room).length > 0;

View file

@ -406,14 +406,14 @@ module.exports = React.createClass({
this.props.onFinished();
}
else {
self.setState({ updating: self.state.updating + 1 });
this.setState({ updating: this.state.updating + 1 });
createRoom({
createOpts: {
invite: [this.props.member.userId],
},
}).finally(function() {
self.props.onFinished();
self.setState({ updating: self.state.updating - 1 });
}).finally(() => {
this.props.onFinished();
this.setState({ updating: this.state.updating - 1 });
}).done();
}
},

View file

@ -14,6 +14,14 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
/**
* 'debounces' a function to only execute every n milliseconds.
* Useful when react-sdk gets many, many events but only wants
* to update the interface once for all of them.
*
* Note that the function must not take arguments, since the args
* could be different for each invocarion of the function.
*/
module.exports = function(f, minIntervalMs) {
this.lastCall = 0;
this.scheduledCall = undefined;