RocketChat/Rocket.Chat · warning · Meteor.Error

error-user-already-in-room

error-user-already-in-room

Error message

You are already in the channel

What it means

Thrown by the /join slash command when the invoking user already has a subscription record for the target room. The handler first resolves the room and warns via ephemeral message if it is not visible, then checks Subscriptions.findOneByRoomIdAndUserId; any existing subscription document triggers this Meteor.Error with code 'error-user-already-in-room'. It prevents a duplicate join through Room.join().

Source

Thrown at apps/meteor/server/slashcommands/join/server.ts:40

		channel = channel.replace('#', '');

		const room = await Rooms.findOneByNameAndType(channel, 'c');
		if (!room) {
			void api.broadcast('notify.ephemeralMessage', userId, message.rid, {
				msg: i18n.t('Channel_doesnt_exist', {
					channelName: channel,
					lng: settings.get('Language') || 'en',
				}),
			});
			return;
		}

		const subscription = await Subscriptions.findOneByRoomIdAndUserId(room._id, userId, {
			projection: { _id: 1 },
		});

		if (subscription) {
			throw new Meteor.Error('error-user-already-in-room', 'You are already in the channel', {
				method: 'slashCommands',
			});
		}

		const user = await Users.findOneById(userId);
		if (!user) {
			throw new Meteor.Error('error-invalid-user', 'Invalid user', {
				method: 'slashCommands',
			});
		}
		await Room.join({ room, user });
	},
	options: {
		description: 'Join_the_given_channel',
		params: '#channel',
		permission: 'view-c-room',
	},
});

View on GitHub (pinned to b2c16d5842)

Solutions

  1. Have the client check the user's subscription list (or room subscription cache) before invoking /join.
  2. On the server, catch the error and degrade to an informational message instead of surfacing a raw error toast.
  3. If an idempotent join is desired, replace the throw with an ephemeral 'already in channel' notice mirroring the room-not-found branch.

Example fix

// before
if (subscription) {
  throw new Meteor.Error('error-user-already-in-room', 'You are already in the channel', { method: 'slashCommands' });
}

// after (idempotent join)
if (subscription) {
  void api.broadcast('notify.ephemeralMessage', userId, message.rid, {
    msg: i18n.t('You_are_already_in_the_channel', { lng: settings.get('Language') || 'en' }),
  });
  return;
}
Defensive patterns

Strategy: validation

Validate before calling

// Before running /join, check an existing subscription client-side
const subscribed = useUserSubscribed(roomId); // or Meteor.call('rooms/get', ...) check
if (!subscribed) {
  await Meteor.callAsync('slashCommand', { command: 'join', params: `#${channelName}`, rid: currentRid });
}

Try / catch

try { await Meteor.callAsync('slashCommand', {...}); } catch (e) { if (isMeteorError(e, 'error-user-already-in-room')) { /* informational: already a member */ return; } throw e; }

Prevention

When it happens

Trigger: User types '/join #channel' (or clicks a join flow that calls the command) while already a member of that channel; the subscription lookup returns a document (only _id projected) and the error is thrown before Room.join runs.

Common situations: Stale client UI showing a join button for a channel the user already joined from another session/device; race where a user joins via invite and then runs /join; automated scripts or bots calling the join command idempotently.

Related errors


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