RocketChat/Rocket.Chat · error · Meteor.Error

error-invalid-user

error-invalid-user

Error message

Invalid user

What it means

loadSurroundingMessages(message, limit, showThreadMessages) loads context around a given message and requires a logged-in user: Meteor.userId() returning null throws error-invalid-user immediately after the check() argument validation. There is no anonymous path for this method.

Source

Thrown at apps/meteor/server/meteor-methods/messages/loadSurroundingMessages.ts:35

			showThreadMessages?: boolean,
		):
			| {
					messages: IMessage[];
					moreBefore: boolean;
					moreAfter: boolean;
			  }
			| false;
	}
}

Meteor.methods<ServerMethods>({
	async loadSurroundingMessages(message, limit = 50, showThreadMessages = true) {
		check(message, Object);
		check(limit, Number);
		check(showThreadMessages, Boolean);

		if (!Meteor.userId()) {
			throw new Meteor.Error('error-invalid-user', 'Invalid user', {
				method: 'loadSurroundingMessages',
			});
		}

		const fromId = Meteor.userId() ?? undefined;

		if (!message._id) {
			return false;
		}

		const mainMessage = await Messages.findOneById(message._id);

		if (!mainMessage?.rid) {
			return false;
		}

		if (!(await canAccessRoomIdAsync(mainMessage.rid, fromId))) {
			return false;

View on GitHub (pinned to b2c16d5842)

Solutions

  1. Gate the surrounding-messages UI on Meteor.userId()
  2. Re-authenticate on session expiry before retrying
  3. Centralize the auth check in a wrapper around history-type methods

Example fix

// before
const result = await Meteor.callAsync('loadSurroundingMessages', message, limit);

// after
if (!Meteor.userId()) {
  // require login before loading message context
} else {
  const result = await Meteor.callAsync('loadSurroundingMessages', message, limit);
}
Defensive patterns

Strategy: validation

Validate before calling

if (!Meteor.userId()) {
  // message context requires a logged-in user
}

Try / catch

try {
  const result = await Meteor.callAsync('loadSurroundingMessages', message, limit);
} catch (error) {
  if (error instanceof Meteor.Error && error.error === 'error-invalid-user') {
    // re-authenticate before retrying the context load
  } else {
    throw error;
  }
}

Prevention

When it happens

Trigger: Meteor.call('loadSurroundingMessages', message, limit) from a logged-out session, an expired resume token, or an unauthenticated DDP client. Note the argument checks (Object/Number/Boolean) run first, so malformed arguments raise Match errors instead.

Common situations: 'Jump to message' / context-view actions triggered from stale logged-out tabs; session expiry during long idle periods followed by a click on a message permalink.

Related errors


AI-assisted analysis of RocketChat/Rocket.Chat@b2c16d5842 (2026-08-18). Data as JSON: /api/errors/f8e2026db99d91ab. Report an issue: GitHub.