RocketChat/Rocket.Chat · error · Error
invalid-message
Error message
invalid-message
What it means
Thrown by GET /api/v1/livechat/message/:_id when Messages.findOneByRoomIdAndMessageId(rid, _id) returns null. The lookup is scoped to both the room id and the message id, so the error means no message document exists with that _id inside that rid. Token and room have already been validated at this point, so the problem is purely the message identifier or its persistence.
Solutions
- Verify the message id against GET /api/v1/livechat/messages.history/:rid?token=... to confirm it is still present in that room.
- Treat this error as a 404-equivalent in the UI: drop the local reference to the deleted message instead of retrying.
- If it should exist, check you are querying the same server/replica where it was sent (rare cross-instance mismatch).
- Make sure the _id in the URL path is the message id and rid in the query string is the room id — swapping them produces exactly this error.
Example fix
// before
const res = await fetch(`/api/v1/livechat/message/${msgId}?token=${token}&rid=${rid}`);
const body = await res.json();
if (!body.success) throw new Error('unexpected failure');
// after (distinguish not-found from other failures)
if (body.error === 'invalid-message') {
removeMessageFromLocalState(msgId); // message was deleted, stop referencing it
} else {
throw new Error(`livechat message fetch failed: ${body.error}`);
} Defensive patterns
Strategy: fallback
Validate before calling
// Confirm the message still exists in the room before deep-linking to it
async function messageExists(token: string, rid: string, msgId: string): Promise<boolean> {
const res = await fetch(`/api/v1/livechat/messages.history/${rid}?token=${encodeURIComponent(token)}&limit=50`);
const body = await res.json();
return body.success && body.messages.some((m: { _id: string }) => m._id === msgId);
} Try / catch
if (isLivechatErrorResponse(body) && body.error === 'invalid-message') {
removeMessageFromLocalState(msgId); // treat as deleted; do not retry
} Prevention
- Treat 'invalid-message' as a 404: purge the local reference instead of retrying the request.
- Before rendering a message from a push notification/preview, verify it against room history.
- Expect concurrent deletes (agent or other tab) and design the message store to tolerate removals.
When it happens
Trigger: GET /api/v1/livechat/message/<msgId> where msgId is wrong, the message was deleted (e.g. via DELETE livechat/message/:_id in another tab), or the message exists but belongs to a different room than the rid supplied.
Common situations: UI tries to render a message referenced in a notification/preview after the agent deleted it; client caches message ids across conversation resets; typos or truncation of the 17-char message _id; using the rid as the message _id in the URL path.
Understand the failure class
Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.
Related errors
- agent-not-found
- error-forwarding-chat
- error-invalid-department-unit
- error-invalid-room
- error-invalid-user
AI-assisted analysis of RocketChat/Rocket.Chat@b2c16d5842 (2026-08-18).
Data as JSON: /api/errors/08f419c4bf1726f1.
Report an issue: GitHub.
Appendix: source
Thrown at apps/meteor/server/api/v1/omnichannel/message.ts:104
{ validateParams: { GET: isGETLivechatMessageIdParams, PUT: isPUTLivechatMessageIdParams, DELETE: isDELETELivechatMessageIdParams } },
{
async get() {
const { token, rid } = this.queryParams;
const { _id } = this.urlParams;
const guest = await findGuest(token);
if (!guest) {
throw new Error('invalid-token');
}
const room = await findRoom(token, rid);
if (!room) {
throw new Error('invalid-room');
}
let message = await Messages.findOneByRoomIdAndMessageId(rid, _id);
if (!message) {
throw new Error('invalid-message');
}
if (message.file) {
message = { ...(await normalizeMessageFileUpload(message)), ...{ _updatedAt: message._updatedAt } };
}
if (!message) {
throw new Error('invalid-message');
}
return API.v1.success({ message });
},
async put() {
const { token, rid } = this.bodyParams;
const { _id } = this.urlParams;
const guest = await findGuest(token);View on GitHub (pinned to b2c16d5842)