RocketChat/Rocket.Chat · error · MeteorError
error-invalid-contact-manager
error-invalid-contact-manager
Error message
The contact manager must have the role "livechat-agent"
What it means
registerContact found a user with the given contactManager.username, but that user's roles array is missing, malformed, or does not include 'livechat-agent'. Omnichannel requires contact managers to be livechat agents so routing and visibility rules hold. This is a role/permission problem, not a lookup problem — the user exists but is not an agent.
Source
Thrown at apps/meteor/server/lib/omnichannel/contacts/registerContact.ts:41
export async function registerContact(
{ token, name, email = '', phone, username, customFields = {}, contactManager }: RegisterContactProps,
userId: string,
): Promise<string> {
if (!token || typeof token !== 'string') {
throw new MeteorError('error-invalid-contact-data', 'Invalid visitor token');
}
const visitorEmail = email.trim().toLowerCase();
if (contactManager?.username) {
// verify if the user exists with this username and has a livechat-agent role
const manager = await Users.findOneByUsername(contactManager.username, { projection: { roles: 1 } });
if (!manager) {
throw new MeteorError('error-contact-manager-not-found', `No user found with username ${contactManager.username}`);
}
if (!manager.roles || !Array.isArray(manager.roles) || !manager.roles.includes('livechat-agent')) {
throw new MeteorError('error-invalid-contact-manager', 'The contact manager must have the role "livechat-agent"');
}
}
const existingUserByToken = await LivechatVisitors.getVisitorByToken(token, { projection: { _id: 1 } });
let visitorId = existingUserByToken?._id;
if (!existingUserByToken) {
if (!username) {
username = await LivechatVisitors.getNextVisitorUsername();
}
const existingUserByEmail = await LivechatVisitors.findOneGuestByEmailAddress(visitorEmail);
visitorId = existingUserByEmail?._id;
if (!existingUserByEmail) {
const userData = {
username,
ts: new Date(),View on GitHub (pinned to b2c16d5842)
Solutions
- Add the 'livechat-agent' role to the user (POST /api/v1/user.update or add them under Administration > Omnichannel > Agents)
- Confirm the user now appears as an agent via GET /api/v1/livechat/agents, then retry registration
- If the user should not be an agent, pass a different contactManager.username or omit contactManager
Example fix
// before
// user 'johndoe' exists but has roles: ['user']
await registerContact({ token, email, contactManager: { username: 'johndoe' } }, userId);
// after
await POST('/api/v1/user.update', { userId, data: { roles: ['user', 'livechat-agent'] } });
await registerContact({ token, email, contactManager: { username: 'johndoe' } }, userId); Defensive patterns
Strategy: type-guard
Validate before calling
const manager = await Users.findOneByUsername(contactManager.username, { projection: { roles: 1 } });
if (!manager?.roles?.includes('livechat-agent')) {
throw new Error('Contact manager must be a livechat agent; add the role first');
}
await registerContact(params, userId); Type guard
type AgentUser = { _id: string; roles?: string[] };
const isLivechatAgent = (u: AgentUser | null): u is AgentUser & { roles: string[] } =>
Array.isArray(u?.roles) && (u.roles as string[]).includes('livechat-agent'); Try / catch
try {
await registerContact(params, userId);
} catch (err) {
if (err instanceof MeteorError && err.code === 'error-invalid-contact-manager') {
// add livechat-agent role or pick another manager, then retry
}
throw err;
} Prevention
- Only offer users from GET /api/v1/livechat/agents as contact-manager choices in UIs
- When deactivating an agent, update contacts that reference them as manager
- Check roles via users.info in integration smoke tests
When it happens
Trigger: POST /api/v1/omnichannel/contact (or registerContact) with contactManager.username of a valid user who was never added as an omnichannel agent, was removed from the agent list, or whose roles field is empty/non-array due to a data issue.
Common situations: Admin removed the agent from Omnichannel > Agents but integrations still reference them; user was created via SSO without the livechat-agent role; roles document corrupted after a migration.
Related errors
- error-contact-manager-not-found
- error-contact-manager-not-found
- error-contact-not-found
- error-contact-not-found
- error-contact-not-found
AI-assisted analysis of RocketChat/Rocket.Chat@b2c16d5842 (2026-08-18).
Data as JSON: /api/errors/f2ac31be36873936.
Report an issue: GitHub.