Include the session handle in a method invocation instead of just the

session id.

Make _sessionData available in a nested method invocation on the
server.
This commit is contained in:
Andrew Wilcox
2013-11-20 16:13:03 -05:00
committed by Nick Martin
parent 1034e5c8a1
commit 17674196c8
4 changed files with 43 additions and 27 deletions

View File

@@ -177,23 +177,23 @@ Accounts._getLoginToken = function (methodInvocation) {
Accounts._setLoginToken = function (methodInvocation, newToken) {
var oldToken = methodInvocation._sessionData.loginToken;
methodInvocation._sessionData.loginToken = newToken;
loginTokenChanged(methodInvocation.sessionId, newToken, oldToken);
loginTokenChanged(methodInvocation.session.id, newToken, oldToken);
};
// sessionId -> SessionHandle
// XXX Wouldn't be necessary if there was an API to get the session or
// session handle from a session id.
var sessionHandles = {};
// XXX Wouldn't be necessary if there was an API to get the session
// from a session id via Meteor.server.sessions[sessionId].sessionHandle
var sessions = {};
Meteor.server.onConnection(function (sessionHandle) {
var sessionId = sessionHandle.id;
sessionHandles[sessionId] = sessionHandle;
sessionHandle.onClose(function () {
var token = sessionHandle._sessionData.loginToken;
Meteor.server.onConnection(function (session) {
var sessionId = session.id;
sessions[sessionId] = session;
session.onClose(function () {
var token = session._sessionData.loginToken;
if (token)
removeSessionFromToken(token, sessionId);
delete sessionHandles[sessionId];
delete sessions[sessionId];
});
});
@@ -205,7 +205,7 @@ var closeSessionsForTokens = function (tokens) {
_.each(tokens, function (token) {
if (_.has(sessionsByLoginToken, token)) {
_.each(sessionsByLoginToken[token], function (sessionId) {
sessionHandles[sessionId] && sessionHandles[sessionId].close();
sessions[sessionId] && sessions[sessionId].close();
});
}
});

View File

@@ -29,9 +29,8 @@ MethodInvocation = function (options) {
// reruns subscriptions
this._setUserId = options.setUserId || function () {};
// On the server, the session id of the connection this method call
// came in on.
this.sessionId = options.sessionId;
// On the server, the session this method call came in on.
this.session = options.session;
// Scratch data scoped to this connection (livedata_connection on the
// client, livedata_session on the server). This is only used

View File

@@ -566,7 +566,7 @@ _.extend(Session.prototype, {
userId: self.userId,
setUserId: setUserId,
unblock: unblock,
sessionId: self.id,
session: self.sessionHandle,
sessionData: self.sessionData
});
try {
@@ -1263,23 +1263,22 @@ _.extend(Server.prototype, {
var setUserId = function() {
throw new Error("Can't call setUserId on a server initiated method call");
};
var sessionId = null;
var session = null;
var currentInvocation = DDP._CurrentInvocation.get();
if (currentInvocation) {
userId = currentInvocation.userId;
setUserId = function(userId) {
currentInvocation.setUserId(userId);
};
sessionId = currentInvocation.sessionId;
session = currentInvocation.session;
}
var invocation = new MethodInvocation({
isSimulation: false,
userId: userId,
setUserId: setUserId,
sessionId: sessionId,
// XXX the Server object doesn't have a `sessionData` field.
sessionData: self.sessionData
session: session,
sessionData: session && session._sessionData
});
try {
var result = DDP._CurrentInvocation.withValue(invocation, function () {

View File

@@ -61,9 +61,9 @@ var innerCalled = null;
Meteor.methods({
livedata_server_test_inner: function () {
var sessionId = this.sessionId;
var self = this;
Meteor.defer(function () {
innerCalled(sessionId);
innerCalled(self);
});
},
@@ -81,8 +81,8 @@ Tinytest.addAsync(
callbackHandle.stop();
sessionId = sessionHandle.id;
});
innerCalled = function (methodSessionId) {
test.equal(methodSessionId, sessionId);
innerCalled = function (methodInvocation) {
test.equal(methodInvocation.session.id, sessionId);
onComplete();
};
var connection = DDP.connect(Meteor.absoluteUrl());
@@ -93,15 +93,33 @@ Tinytest.addAsync(
Tinytest.addAsync(
"livedata server - sessionId in nested method invocation",
"livedata server - session in nested method invocation",
function (test, onComplete) {
var sessionId;
var callbackHandle = Meteor.server.onConnection(function (sessionHandle) {
callbackHandle.stop();
sessionId = sessionHandle.id;
});
innerCalled = function (methodSessionId) {
test.equal(methodSessionId, sessionId);
innerCalled = function (methodInvocation) {
test.equal(methodInvocation.session.id, sessionId);
onComplete();
};
var connection = DDP.connect(Meteor.absoluteUrl());
connection.call('livedata_server_test_outer');
connection.disconnect();
}
);
Tinytest.addAsync(
"livedata server - session data in nested method invocation",
function (test, onComplete) {
var callbackHandle = Meteor.server.onConnection(function (session) {
callbackHandle.stop();
session._sessionData.foo = 123;
});
innerCalled = function (methodInvocation) {
test.equal(methodInvocation._sessionData.foo, 123);
onComplete();
};
var connection = DDP.connect(Meteor.absoluteUrl());