{"record":{"id":"b0c1a6c810845978","repo":"RocketChat/Rocket.Chat","slug":"error-invalid-token-b0c1a6","errorCode":"error-invalid-token","errorMessage":"Token cannot be empty","messagePattern":"Token cannot be empty","errorType":"exception","errorClass":"Meteor.Error","httpStatus":400,"severity":"error","filePath":"apps/meteor/server/api/v1/omnichannel/visitor.ts","lineNumber":47,"sourceCode":"\t\t\t\t\tname: Match.Maybe(String),\n\t\t\t\t\temail: Match.Maybe(String),\n\t\t\t\t\tdepartment: Match.Maybe(String),\n\t\t\t\t\tphone: Match.Maybe(String),\n\t\t\t\t\tusername: Match.Maybe(String),\n\t\t\t\t\tcustomFields: Match.Maybe([\n\t\t\t\t\t\tMatch.ObjectIncluding({\n\t\t\t\t\t\t\tkey: String,\n\t\t\t\t\t\t\tvalue: String,\n\t\t\t\t\t\t\toverwrite: Boolean,\n\t\t\t\t\t\t}),\n\t\t\t\t\t]),\n\t\t\t\t}),\n\t\t\t});\n\n\t\t\tconst { customFields, id, token, name, email, department, phone, username, connectionData } = this.bodyParams.visitor;\n\n\t\t\tif (!token?.trim()) {\n\t\t\t\tthrow new Meteor.Error('error-invalid-token', 'Token cannot be empty', { method: 'livechat/visitor' });\n\t\t\t}\n\n\t\t\tconst guest = {\n\t\t\t\ttoken,\n\t\t\t\t...(id && { id }),\n\t\t\t\t...(name && { name }),\n\t\t\t\t...(email && { email }),\n\t\t\t\t...(department && { department }),\n\t\t\t\t...(username && { username }),\n\t\t\t\t...(connectionData && { connectionData }),\n\t\t\t\t...(phone && typeof phone === 'string' && { phone: { number: phone as string } }),\n\t\t\t\tconnectionData: normalizeHttpHeaderData(this.request.headers),\n\t\t\t};\n\n\t\t\tconst visitor = await registerGuest(guest, {\n\t\t\t\tshouldConsiderIdleAgent: settings.get<boolean>('Livechat_enabled_when_agent_idle'),\n\t\t\t\tshouldConsiderOfflineAgent: settings.get<boolean>('Livechat_accept_chats_with_no_agents'),\n\t\t\t});","sourceCodeStart":29,"sourceCodeEnd":65,"githubUrl":"https://github.com/RocketChat/Rocket.Chat/blob/f9d3ec372bb580fa8d036f94cf03925a478ef768/apps/meteor/server/api/v1/omnichannel/visitor.ts#L29-L65","documentation":"Thrown as Meteor.Error('error-invalid-token', 'Token cannot be empty') in POST livechat/visitor when bodyParams.visitor.token is missing, empty, or whitespace-only after trim. The route is unauthenticated (visitor-facing), so the token is the only identity anchor and must be non-empty.","triggerScenarios":"POST /api/v1/v1/livechat/visitor with visitor omitted, with visitor.token = '' or '   ', or with token = null. The preceding check() validates the body shape but token is not constrained to a non-empty String there.","commonSituations":"Livechat widget initializing before generating a visitor token; SDK call that forgets to set token; token cleared by an upstream sanitizer.","solutions":["Generate a visitor token (UUID/v4 is typical) before calling the endpoint.","Trim and assert non-empty client-side: if (!visitor.token?.trim()) return;","Ensure the widget's token bootstrap runs before any registerVisitor network call."],"exampleFix":"// before\nawait POST('/api/v1/livechat/visitor', { body: { visitor: { name, email } } });\n\n// after\nconst token = visitor.token || crypto.randomUUID();\nawait POST('/api/v1/livechat/visitor', { body: { visitor: { token, name, email } } });","handlingStrategy":"validation","validationCode":"const token = (body.visitor?.token ?? '').trim();\nif (!token) throw new Error('visitor.token required');\nawait fetch('/api/v1/v1/livechat/visitor', { method:'POST', body: JSON.stringify({ visitor: { ...body.visitor, token } }) });","typeGuard":"function hasNonEmptyToken(v: { token?: string } | undefined): v is { token: string } {\n  return !!v?.token?.trim();\n}","tryCatchPattern":"null","preventionTips":["Generate a visitor token (crypto.randomUUID()) at widget boot, before any register call.","Trim and assert non-empty before POSTing.","Treat the token as required state in the widget store."],"tags":["omnichannel","visitor","token","validation","unauthenticated"],"backgroundTag":null,"analyzedSha":"f9d3ec372bb580fa8d036f94cf03925a478ef768","analyzedAt":"2026-08-12T19:07:17.372Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}