{"record":{"id":"db2c26e6d61b3c6c","repo":"RocketChat/Rocket.Chat","slug":"error-cant-invite-for-direct-room","errorCode":"error-cant-invite-for-direct-room","errorMessage":"Can't invite user to direct rooms","messagePattern":"Can't invite user to direct rooms","errorType":"error_code","errorClass":"Meteor.Error","httpStatus":null,"severity":"error","filePath":"apps/meteor/server/meteor-methods/rooms/addUsersToRoom.ts","lineNumber":57,"sourceCode":"\t\t\tmethod: 'addUsersToRoom',\n\t\t});\n\t}\n\n\t// Get user and room details\n\tconst room = await Rooms.findOneById(data.rid);\n\tif (!room) {\n\t\tthrow new Meteor.Error('error-invalid-room', 'Invalid room', {\n\t\t\tmethod: 'addUsersToRoom',\n\t\t});\n\t}\n\n\tconst subscription = await Subscriptions.findOneByRoomIdAndUserId(data.rid, userId, {\n\t\tprojection: { _id: 1 },\n\t});\n\tconst userInRoom = subscription != null;\n\n\tif (room.t === 'd' && !isRoomNativeFederated(room)) {\n\t\tthrow new Meteor.Error('error-cant-invite-for-direct-room', \"Can't invite user to direct rooms\", {\n\t\t\tmethod: 'addUsersToRoom',\n\t\t});\n\t}\n\n\t// Can add to any room you're in, with permission, otherwise need specific room type permission\n\tlet canAddUser = false;\n\tif (userInRoom && (await hasPermissionAsync(userId, 'add-user-to-joined-room', room._id))) {\n\t\tcanAddUser = true;\n\t} else if (room.t === 'c' && (await hasPermissionAsync(userId, 'add-user-to-any-c-room'))) {\n\t\tcanAddUser = true;\n\t} else if (room.t === 'p' && (await hasPermissionAsync(userId, 'add-user-to-any-p-room'))) {\n\t\tcanAddUser = true;\n\t}\n\n\t// Adding wasn't allowed\n\tif (!canAddUser) {\n\t\tthrow new Meteor.Error('error-not-allowed', 'Not allowed', {\n\t\t\tmethod: 'addUsersToRoom',","sourceCodeStart":39,"sourceCodeEnd":75,"githubUrl":"https://github.com/RocketChat/Rocket.Chat/blob/b2c16d5842cbe6b69b59bdf6fc5e5f1afcd1f0b0/apps/meteor/server/meteor-methods/rooms/addUsersToRoom.ts#L39-L75","documentation":"Thrown by addUsersToRoomMethod() in apps/meteor/server/meteor-methods/rooms/addUsersToRoom.ts:57 when room.t === 'd' (direct room / DM) and the room is not a natively federated room (isRoomNativeFederated(room) === false). Direct rooms have fixed membership of exactly the two participants, so inviting additional users is structurally forbidden; only natively-federated DMs (which support extra Matrix participants) are exempt.","triggerScenarios":"Calling the invite flow (addUsersToRoomMethod / 'addUserToRoom' / 'addUsersToRoom' methods, invite slash command paths) with the rid of a DM; front-end invite UI mistakenly enabled on direct rooms; code that loops over all rooms of a user and invites into DMs too.","commonSituations":"Bots or onboarding scripts inviting users into every room including DMs; UI state bugs where the invite dialog opens for room type 'd'; attempting to recreate group-chat behavior by 'adding' someone to an existing DM instead of creating a new group.","solutions":["Filter out direct rooms before inviting: if (room.t === 'd') skip or surface a clear message.","If a multi-user conversation is needed, create a new room (type 'p'/'c') or a discussion instead of adding to the DM.","If Matrix-style multi-participant DMs are required, use natively federated rooms created through the federation flow.","In custom UIs, disable/hide invite actions when the current room type is 'd'."],"exampleFix":"// before\nawait addUsersToRoomMethod(uid, { rid, users });\n\n// after\nconst room = await Rooms.findOneById(rid, { projection: { t: 1, federated: 1, federation: 1 } });\nif (room?.t === 'd' && !isRoomNativeFederated(room)) {\n  throw new Error('cannot invite into a direct room; create a group instead');\n}\nawait addUsersToRoomMethod(uid, { rid, users });","handlingStrategy":"validation","validationCode":"const room = await Rooms.findOneById(rid, { projection: { t: 1, federated: 1, federation: 1 } });\nif (room?.t === 'd' && !isRoomNativeFederated(room)) {\n  throw new Error('cannot invite into a direct room; create a group/discussion instead');\n}","typeGuard":"const isDirectRoom = (room: { t: string }): boolean => room.t === 'd';","tryCatchPattern":"try {\n  await addUsersToRoomMethod(uid, { rid, users });\n} catch (e) {\n  if (e instanceof Meteor.Error && e.error === 'error-cant-invite-for-direct-room') {\n    // redirect the user: create a new group room with the desired members instead\n  }\n}","preventionTips":["Hide invite actions for room type 'd' in UIs and bots.","When adding a person to a conversation should scale beyond 1:1, create a 'p'/'c' room rather than mutating a DM.","Filter rooms by type before running bulk invite scripts."],"tags":["meteor-method","rooms","direct-room","membership","business-rule"],"backgroundTag":"invite-to-direct-room-forbidden","analyzedSha":"b2c16d5842cbe6b69b59bdf6fc5e5f1afcd1f0b0","analyzedAt":"2026-08-18T15:26:39.429Z","schemaVersion":2},"datasetVersion":"2026-08-21T18:17:14.833Z"}