From dd064ba0a1339239a7a334d780a145e1b74423f8 Mon Sep 17 00:00:00 2001 From: Richard van der Hoff Date: Wed, 20 Jul 2016 20:06:14 +0100 Subject: [PATCH] /login, /register: Add device_id and initial_device_display_name To help test the forthcoming device_id support for /login and /register, add the device_id and initial_device_display_name parameters to those calls. Allow the app to specify the default device displayname when creating the client (as well as the device_id). Also, don't try initialising the Olm layer unless a userId is provided. Currently this isn't a problem because react-sdk doesn't provide a sessionStore when it doesn't provide a userId, but that is a bad thing to rely on (and I am going to break it with a react-sdk PR). --- lib/client.js | 80 +++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 58 insertions(+), 22 deletions(-) diff --git a/lib/client.js b/lib/client.js index ea0a67720..1704f9c60 100644 --- a/lib/client.js +++ b/lib/client.js @@ -80,8 +80,12 @@ var DeviceVerification = { * @param {Object=} opts.store The data store to use. If not specified, * this client will not store any HTTP responses. * - * @param {string=} opts.deviceId A unique identifier for this device, for use - * in end-to-end crypto. If not specified, end-to-end crypto will be disabled. + * @param {string=} opts.deviceId A unique identifier for this device; used for + * tracking things like crypto keys and access tokens. If not specified, + * end-to-end crypto will be disabled. + * + * @param {string=} opts.defaultDeviceDisplayName Initial display name to set + * on new devices * * @param {Object=} opts.sessionStore A store to be used for end-to-end crypto * session data. This should be a {@link @@ -115,9 +119,16 @@ function MatrixClient(opts) { this.sessionStore = opts.sessionStore || null; this.deviceId = opts.deviceId; + this.defaultDeviceDisplayName = opts.defaultDeviceDisplayName || "js-sdk device"; + + var userId = (opts.userId || null); + this.credentials = { + userId: userId, + }; + this._olmDevice = null; - if (CRYPTO_ENABLED && this.sessionStore !== null) { + if (CRYPTO_ENABLED && this.sessionStore !== null && userId !== null) { this._olmDevice = new OlmDevice(opts.sessionStore); var json = '{"algorithms":["' + OLM_ALGORITHM + '"]'; @@ -128,13 +139,13 @@ function MatrixClient(opts) { json += ',"curve25519:' + this.deviceId + '":'; json += JSON.stringify(this._olmDevice.deviceCurve25519Key); json += '}'; - json += ',"user_id":' + JSON.stringify(opts.userId); + json += ',"user_id":' + JSON.stringify(userId); json += '}'; var signature = this._olmDevice.sign(json); this.deviceKeys = JSON.parse(json); var signatures = {}; - signatures[opts.userId] = {}; - signatures[opts.userId]["ed25519:" + this.deviceId] = signature; + signatures[userId] = {}; + signatures[userId]["ed25519:" + this.deviceId] = signature; this.deviceKeys.signatures = signatures; var deviceInfo = { @@ -143,11 +154,11 @@ function MatrixClient(opts) { verified: DeviceVerification.VERIFIED, }; var myDevices = this.sessionStore.getEndToEndDevicesForUser( - opts.userId + userId ) || {}; myDevices[opts.deviceId] = deviceInfo; this.sessionStore.storeEndToEndDevicesForUser( - opts.userId, myDevices + userId, myDevices ); setupCryptoEventHandler(this); } @@ -174,9 +185,6 @@ function MatrixClient(opts) { onlyData: true, extraParams: opts.queryParams }; - this.credentials = { - userId: (opts.userId || null) - }; this._http = new httpApi.MatrixHttpApi(this, httpOpts); this.callList = { // callId: MatrixCall @@ -2675,9 +2683,19 @@ MatrixClient.prototype.paginateEventTimeline = function(eventTimeline, opts) { * @return {module:http-api.MatrixError} Rejects: with an error response. */ MatrixClient.prototype.login = function(loginType, data, callback) { - data.type = loginType; + var login_data = { + type: loginType, + device_id: this.deviceId, + initial_device_display_name: this.defaultDeviceDisplayName, + }; + + // merge data into login_data + for (var k in data) { + if (data.hasOwnProperty(k)) { login_data[k] = data[k]; } + } + return this._http.authedRequest( - callback, "POST", "/login", undefined, data + callback, "POST", "/login", undefined, login_data ); }; @@ -2692,13 +2710,7 @@ MatrixClient.prototype.login = function(loginType, data, callback) { MatrixClient.prototype.registerGuest = function(opts, callback) { opts = opts || {}; opts.body = opts.body || {}; - - return this._http.request( - callback, "POST", "/register", { - kind: "guest" - }, - opts.body - ); + return this.registerRequest(opts.body, "guest", callback); }; /** @@ -2779,9 +2791,33 @@ MatrixClient.prototype.register = function(username, password, if (bindEmail !== undefined) { params.bind_email = bindEmail; } if (guestAccessToken !== undefined) { params.guest_access_token = guestAccessToken; } + return this.registerRequest(params, undefined, callback); +}; + + +/** + * @param {Object} data parameters for registration request + * @param {string=} kind type of user to register. may be "guest" + * @param {module:client.callback=} callback + * @return {module:client.Promise} Resolves: to the /register response + * @return {module:http-api.MatrixError} Rejects: with an error response. + */ +MatrixClient.prototype.registerRequest = function(data, kind, callback) { + var request_data = { + device_id: this.deviceId, + initial_device_display_name: this.defaultDeviceDisplayName, + }; + + // merge data into request_data + for (var k in data) { + if (data.hasOwnProperty(k)) { request_data[k] = data[k]; } + } + + var params = {}; + if (kind) { params.kind = kind; } + return this._http.request( - callback, "POST", "/register", undefined, - params + callback, "POST", "/register", params, request_data ); };