RocketChat/Rocket.Chat · error · Error

apps-engine-not-initialized

apps-engine-not-initialized

Error message

apps-engine-not-initialized

What it means

_canEnableApp refuses to enable any app while the Apps Engine has not finished initializing: Apps.isInitialized() resolves false. It is the first guard in the enable flow, so it fires regardless of license state whenever the engine is still booting or was never started.

Solutions

  1. Wait for engine readiness before enabling: await Apps.isInitialized() (or wait for the apps-engine startup log) and then retry
  2. In tests, initialize the Apps Engine (app manager setup) before calling enable methods
  3. Move enable calls out of early startup hooks into a post-startup callback or queue that drains once the engine is ready

Example fix

// before
await Apps.enableApp(appId); // may throw apps-engine-not-initialized during boot

// after
while (!(await Apps.isInitialized())) {
	await new Promise((resolve) => setTimeout(resolve, 100));
}
await Apps.enableApp(appId);
Defensive patterns

Strategy: validation

Validate before calling

if (!(await Apps.isInitialized())) {
	// queue the enable for after engine startup instead of calling now
	return queueEnableAfterEngineReady(appId);
}
await Apps.enableApp(appId);

Try / catch

try {
	await Apps.enableApp(appId);
} catch (err) {
	if (err instanceof Error && err.message === 'apps-engine-not-initialized') {
		// engine still booting: retry on a later tick / after startup event
	} else {
		throw err;
	}
}

Prevention

When it happens

Trigger: Calling an app-enable path (Apps API methods such as enableApp, or REST routes that enable apps) during server startup before the Apps Engine finished loading, or in tests where the engine was never bootstrapped.

Common situations: Server code enabling apps inside Meteor.startup before engine readiness; integration tests that skip engine setup; slow marketplace/app loading creating a startup race window.

Related errors


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

Appendix: source

Thrown at apps/meteor/ee/server/lib/license/canEnableApp.ts:15

import type { IAppStorageItem } from '@rocket.chat/apps/dist/server/storage/IAppStorageItem';
import { Apps } from '@rocket.chat/core-services';
import type { LicenseModule } from '@rocket.chat/core-typings';
import { License, type LicenseImp } from '@rocket.chat/license';

import { getInstallationSourceFromAppStorageItem } from '../../../../lib/apps/getInstallationSourceFromAppStorageItem';

type _canEnableAppDependencies = {
	Apps: typeof Apps;
	License: LicenseImp;
};

export const _canEnableApp = async ({ Apps, License }: _canEnableAppDependencies, app: IAppStorageItem): Promise<void> => {
	if (!(await Apps.isInitialized())) {
		throw new Error('apps-engine-not-initialized');
	}

	// Migrated apps were installed before the validation was implemented
	// so they're always allowed to be enabled
	if (app.migrated) {
		return;
	}

	if (app.info.addon && !License.hasModule(app.info.addon as LicenseModule)) {
		throw new Error('app-addon-not-valid');
	}

	const source = getInstallationSourceFromAppStorageItem(app);
	switch (source) {
		case 'private':
			if (await License.shouldPreventAction('privateApps')) {
				throw new Error('license-prevented');
			}

View on GitHub (pinned to b2c16d5842)