mirror of
https://github.com/meteor/meteor.git
synced 2026-05-02 03:01:46 -04:00
Handle token observe better with overlapping login
Before this, we could see the "non-null user observe" error if: - One login method ran (eg login) and it called _setLoginToken. It stored null in userObservesForConnections and gets to the defer/observe part - Another login method ran (eg getNewToken) and it called _setLoginToken. The call to removeTokenFromConnection at the top clears the null from userObservesForConnections, and it then stores its own null in userObservesForConnections, and defers - One of them finishes the observe and puts its observe in userObservesForConnections, overwriting the null which it thinks is its alone - The other one gets there and throws Also, consistently use _.has when checking if userObservesForConnections has an element.
This commit is contained in:
@@ -644,8 +644,8 @@ Accounts._getUserObserve = function (connectionId) {
|
||||
// the observe that we started when we associated the connection with
|
||||
// this token.
|
||||
var removeTokenFromConnection = function (connectionId) {
|
||||
var observe = userObservesForConnections[connectionId];
|
||||
if (observe !== undefined) {
|
||||
if (_.has(userObservesForConnections, connectionId)) {
|
||||
var observe = userObservesForConnections[connectionId];
|
||||
if (observe === null) {
|
||||
// We're in the process of setting up an observe for this
|
||||
// connection. We can't clean up that observe yet, but if we
|
||||
@@ -703,18 +703,26 @@ Accounts._setLoginToken = function (userId, connection, newToken) {
|
||||
}
|
||||
});
|
||||
|
||||
if (_.has(userObservesForConnections, connection.id)) {
|
||||
if (userObservesForConnections[connection.id] !== null) {
|
||||
throw new Error("Non-null user observe for connection " +
|
||||
connection.id + " while observe was being set up?");
|
||||
}
|
||||
userObservesForConnections[connection.id] = observe;
|
||||
} else {
|
||||
// Oops, this connection was closed while we were setting up the
|
||||
// observe. Clean it up now.
|
||||
// If the user ran another login or logout command we were waiting for
|
||||
// the defer or added to fire, then we let the later one win (start an
|
||||
// observe, etc) and just stop our observe now.
|
||||
//
|
||||
// Similarly, if the connection was already closed, then the onClose
|
||||
// callback would have called removeTokenFromConnection and there won't be
|
||||
// an entry in userObservesForConnections. We can stop the observe.
|
||||
if (Accounts._getAccountData(connection.id, 'loginToken') !== newToken ||
|
||||
!_.has(userObservesForConnections, connection.id)) {
|
||||
observe.stop();
|
||||
return;
|
||||
}
|
||||
|
||||
if (userObservesForConnections[connection.id] !== null) {
|
||||
throw new Error("Non-null user observe for connection " +
|
||||
connection.id + " while observe was being set up?");
|
||||
}
|
||||
|
||||
userObservesForConnections[connection.id] = observe;
|
||||
|
||||
if (! foundMatchingUser) {
|
||||
// We've set up an observe on the user associated with `newToken`,
|
||||
// so if the new token is removed from the database, we'll close
|
||||
|
||||
Reference in New Issue
Block a user