RocketChat/Rocket.Chat · error · Meteor.Error
error-action-not-allowed
error-action-not-allowed
Error message
This is an enterprise feature
What it means
Meteor.Error('error-action-not-allowed', 'This is an enterprise feature') thrown by chat.getMessageReadReceipts when License.hasModule('message-read-receipt') is false. The endpoint exists on all builds but only serves requests on licensed Enterprise workspaces; otherwise it rejects with 403-shaped not-allowed.
Solutions
- Install/renew an Enterprise license that includes the message-read-receipt module.
- Feature-detect before use (GET /v1/license or check the module list) and hide read-receipt UI on unlicensed workspaces.
- If read receipts are not essential, remove the call on Community deployments.
Example fix
// before
const { receipts } = await GET('chat.getMessageReadReceipts')({ messageId }); // 403 on CE
// after
const { modules } = await GET('license')();
if (!modules.includes('message-read-receipt')) throw new Error('Feature not licensed');
const { receipts } = await GET('chat.getMessageReadReceipts')({ messageId }); Defensive patterns
Strategy: validation
Validate before calling
const hasReadReceiptModule = async (): Promise<boolean> =>
(await GET('license')()).modules.includes('message-read-receipt'); Type guard
const isEnterpriseFeatureError = (error: unknown): boolean =>
Boolean(error && typeof error === 'object' && 'error' in error && (error as { error?: string }).error === 'error-action-not-allowed' && /enterprise feature/i.test(String((error as { reason?: string }).reason ?? ''))); Try / catch
try {
const { receipts } = await GET('chat.getMessageReadReceipts')({ messageId });
} catch (error) {
if (isEnterpriseFeatureError(error)) {
hideReadReceiptsUI(); // unlicensed workspace — degrade gracefully, do not retry
return;
}
throw error;
} Prevention
- Feature-detect the license module before showing read-receipt affordances.
- Keep a licensed test workspace for EE integration tests.
- Watch license expiry: hasModule flips off when renewals lapse.
When it happens
Trigger: GET /v1/chat.getMessageReadReceipts?messageId=... on a Community workspace or one whose license does not include the message-read-receipt module.
Common situations: Apps/integrations written against EE features and deployed to Community; trial license expiring so hasModule flips to false; feature flags not purchased.
Related errors
- AI search status unavailable
- error-abac-attribute-store-external
- error-abac-not-enabled
- error-action-not-allowed
- error-invalid-user
AI-assisted analysis of RocketChat/Rocket.Chat@b2c16d5842 (2026-08-18).
Data as JSON: /api/errors/c60b58ad4f3d26f4.
Report an issue: GitHub.
Appendix: source
Thrown at apps/meteor/ee/server/api/chat.ts:52
},
required: ['receipts', 'success'],
additionalProperties: false,
});
API.v1.get(
'chat.getMessageReadReceipts',
{
authRequired: true,
query: isChatGetMessageReadReceiptsProps,
response: {
200: getMessageReadReceiptsResponseSchema,
400: validateBadRequestErrorResponse,
401: validateUnauthorizedErrorResponse,
},
},
async function action() {
if (!License.hasModule('message-read-receipt')) {
throw new Meteor.Error('error-action-not-allowed', 'This is an enterprise feature');
}
const { messageId } = this.queryParams;
return API.v1.success({
receipts: await getReadReceiptsFunction(messageId, this.userId),
});
},
);
View on GitHub (pinned to b2c16d5842)