RocketChat/Rocket.Chat · error · Meteor.Error
error-invalid-user
error-invalid-user
Error message
Invalid user
What it means
Thrown by the exported addUsersToRoomMethod() in apps/meteor/server/meteor-methods/rooms/addUsersToRoom.ts:32 when the userId argument is falsy. Unlike the Meteor method wrappers, this helper takes the acting user ID as a parameter, so callers must supply it; the guard is a plain truthiness check before the rid validation runs.
Source
Thrown at apps/meteor/server/meteor-methods/rooms/addUsersToRoom.ts:32
declare module '@rocket.chat/ddp-client' {
// eslint-disable-next-line @typescript-eslint/naming-convention
interface ServerMethods {
addUsersToRoom(data: { rid: string; users: string[] }): boolean;
}
}
export const sanitizeUsername = (username: string) => {
const isFederatedUsername = username.includes('@') && username.includes(':');
if (isFederatedUsername) {
return username;
}
return username.replace(/(^@)|( @)/, '');
};
export const addUsersToRoomMethod = async (userId: string, data: { rid: string; users: string[] }, user?: IUser): Promise<boolean> => {
if (!userId) {
throw new Meteor.Error('error-invalid-user', 'Invalid user', {
method: 'addUsersToRoom',
});
}
if (!Match.test(data.rid, String)) {
throw new Meteor.Error('error-invalid-room', 'Invalid room', {
method: 'addUsersToRoom',
});
}
// Get user and room details
const room = await Rooms.findOneById(data.rid);
if (!room) {
throw new Meteor.Error('error-invalid-room', 'Invalid room', {
method: 'addUsersToRoom',
});
}
View on GitHub (pinned to b2c16d5842)
Solutions
- Pass a real acting user ID: resolve it via Meteor.userId() in method contexts or accept it explicitly in jobs.
- Validate before calling: if (!userId) fail fast with your own error naming the missing parameter.
- Prefer the public REST endpoints POST /v1/channels.invite / POST /v1/groups.invite for integrations, which authenticate via headers.
- If you own the call site, make the parameter required in TypeScript (userId: string, not userId?: string) so the compiler catches omissions.
Example fix
// before
await addUsersToRoomMethod(Meteor.userId(), { rid, users });
// after
const uid = Meteor.userId();
if (!uid) throw new Error('no acting user; authenticate first');
await addUsersToRoomMethod(uid, { rid, users }); Defensive patterns
Strategy: validation
Validate before calling
const uid = Meteor.userId();
if (!uid) throw new Error('no acting user; authenticate first');
await addUsersToRoomMethod(uid, { rid, users }); Type guard
const isNonEmptyString = (v: unknown): v is string => typeof v === 'string' && v.length > 0;
Try / catch
try {
await addUsersToRoomMethod(userId, data);
} catch (e) {
if (e instanceof Meteor.Error && e.error === 'error-invalid-user') {
// caller passed a falsy userId: fix the call site, do not retry
}
} Prevention
- Type the parameter as required string in your own wrappers so TS rejects omissions.
- Resolve the acting user from the session at call time.
- Fail fast at entry points when no user context is bound.
When it happens
Trigger: Calling addUsersToRoomMethod('', rid, users) or with undefined/null userId — e.g. a caller that did Meteor.userId() ?? '' , a server job that lost its user context, or code passing the user object instead of its _id (object._id of a malformed object).
Common situations: Server-side automation invoking the helper outside a request context; refactors where the first parameter was changed from an IUser to a userId string and callers were not all updated; default-parameter code paths that pass undefined.
Related errors
AI-assisted analysis of RocketChat/Rocket.Chat@b2c16d5842 (2026-08-18).
Data as JSON: /api/errors/5388910481ab5a1d.
Report an issue: GitHub.