RocketChat/Rocket.Chat · error · Meteor.Error

error-canned-response-not-found

error-canned-response-not-found

Error message

Canned Response not found

What it means

saveCannedResponse (saveCannedResponse.ts:86) takes the update path when _id is provided; if CannedResponse.findOneById(_id) returns null (the record was deleted after the editor loaded it), it throws error-canned-response-not-found instead of upserting.

Solutions

  1. Refresh the canned responses list; if the record is gone, create it again instead of updating
  2. Handle error-canned-response-not-found in the editor by warning the user the item was deleted
  3. Pre-check existence before saving when the editing session is long-lived

Example fix

// before
await saveCannedResponse(uid, responseData, _id);

// after
const existing = _id ? await CannedResponse.findOneById(_id, { projection: { _id: 1 } }) : null;
if (_id && !existing) {
	// record deleted meanwhile — fall back to create
	return saveCannedResponse(uid, responseData);
}
await saveCannedResponse(uid, responseData, _id);
Defensive patterns

Strategy: validation

Validate before calling

if (_id) {
	const existing = await CannedResponse.findOneById(_id, { projection: { _id: 1 } });
	if (!existing) {
		// record deleted meanwhile — create instead of update
		return saveCannedResponse(userId, responseData);
	}
}
await saveCannedResponse(userId, responseData, _id);

Try / catch

try {
	await saveCannedResponse(userId, responseData, _id);
} catch (e) {
	if (e instanceof Meteor.Error && e.error === 'error-canned-response-not-found') {
		// refresh the list and re-open; the record was deleted by someone else
	}
	throw e;
}

Prevention

When it happens

Trigger: Updating a canned response that no longer exists — another user/session deleted it while the editor form was open, or the _id is stale/wrong.

Common situations: Two agents editing the same canned response and one deleting it; list not refreshed after a deletion; retrying a save after the record was removed by an admin cleanup.

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


AI-assisted analysis of RocketChat/Rocket.Chat@b2c16d5842 (2026-08-18). Data as JSON: /api/errors/343afb98ee142483. Report an issue: GitHub.

Appendix: source

Thrown at apps/meteor/ee/server/meteor-methods/saveCannedResponse.ts:86

			method: 'saveCannedResponse',
		});
	}

	if (
		responseData.departmentId &&
		!(await LivechatDepartment.findOneById<Pick<ILivechatDepartment, '_id'>>(responseData.departmentId, { projection: { _id: 1 } }))
	) {
		throw new Meteor.Error('error-invalid-department', 'Invalid department', {
			method: 'saveCannedResponse',
		});
	}

	let result: Omit<IOmnichannelCannedResponse, '_updatedAt' | '_createdAt'> & { _createdAt?: Date };

	if (_id) {
		const cannedResponse = await CannedResponse.findOneById(_id);
		if (!cannedResponse) {
			throw new Meteor.Error('error-canned-response-not-found', 'Canned Response not found', {
				method: 'saveCannedResponse',
			});
		}

		result = await CannedResponse.updateCannedResponse(_id, {
			...responseData,
			...(cannedResponse.scope === 'user' && { userId: cannedResponse.userId }),
			createdBy: cannedResponse.createdBy,
		});
	} else {
		const user = await Users.findOneById(userId);

		const data = {
			...responseData,
			...(responseData.scope === 'user' && { userId: user?._id }),
			createdBy: { _id: user?._id || '', username: user?.username || '' },
			_createdAt: new Date(),
		};

View on GitHub (pinned to b2c16d5842)