{"record":{"id":"642581361a2ac853","repo":"moeru-ai/airi","slug":"extension-manifest-id-does-not-support-runtime-runtime","errorCode":null,"errorMessage":"Extension \\`${manifest.id}\\` does not support runtime \\`${runtime}\\`.","messagePattern":"Extension \\\\`(.+?)\\\\` does not support runtime \\\\`(.+?)\\\\`\\.","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/plugin-sdk/src/plugin-host/core.ts","lineNumber":244,"sourceCode":"    this.loader = new FileSystemLoader()\n    this.runtime = options.runtime ?? 'electron'\n    if (options.airiVersion && !semver.valid(options.airiVersion)) {\n      throw new Error(`AIRI version must be a valid semantic version: ${options.airiVersion}`)\n    }\n    this.airiVersion = options.airiVersion\n    this.permissionResolver = options.permissionResolver\n    this.resources.setValue(protocolListProvidersEventName, [] as Array<{ name: string }>)\n    this.markCapabilityReady(protocolListProvidersEventName, { source: 'plugin-host' })\n    this.installContext = this.createInstallContext()\n\n    for (const contribution of options.contributions ?? []) {\n      this.installContribution(contribution)\n    }\n  }\n\n  private assertManifestCompatibility(manifest: ExtensionManifestV2, runtime: PluginRuntime) {\n    if (!manifest.engines.runtimes.includes(runtime)) {\n      throw new Error(`Extension \\`${manifest.id}\\` does not support runtime \\`${runtime}\\`.`)\n    }\n    if (this.airiVersion && !semver.satisfies(this.airiVersion, manifest.engines.airi, { includePrerelease: true })) {\n      throw new Error(\n        `Extension \\`${manifest.id}\\` requires AIRI \\`${manifest.engines.airi}\\`, but the running version is \\`${this.airiVersion}\\`.`,\n      )\n    }\n  }\n\n  async startExtension(\n    extension: Extension,\n    options: { manifest: ExtensionManifestV2, cwd?: string, runtime?: PluginRuntime },\n  ) {\n    const runtime = options.runtime ?? this.runtime\n    this.assertManifestCompatibility(options.manifest, runtime)\n\n    if (extension.id !== options.manifest.id) {\n      throw new Error(`Extension entrypoint id \\`${extension.id}\\` must match manifest id \\`${options.manifest.id}\\`.`)\n    }","sourceCodeStart":226,"sourceCodeEnd":262,"githubUrl":"https://github.com/moeru-ai/airi/blob/438a067dde47aa0bdb46c2323d1fe293dc805218/packages/plugin-sdk/src/plugin-host/core.ts#L226-L262","documentation":"The plugin host's assertManifestCompatibility checks that an extension manifest declares the current PluginRuntime (e.g. 'electron', 'node') in manifest.engines.runtimes before starting it. If the runtime is not listed, the extension is considered platform-incompatible and startExtension/start aborts. This prevents loading extensions whose entrypoints were not built for the host runtime.","triggerScenarios":"Calling startExtension(extension, { manifest, runtime }) or start() where manifest.engines.runtimes does not include the resolved runtime (options.runtime ?? host runtime).","commonSituations":"An extension authored only for the browser runtime is installed into the Electron host; a manifest forgot to add the runtime string after a rename; passing an explicit runtime option that differs from the manifest's declared list.","solutions":["Add the host runtime to manifest.engines.runtimes (e.g. \"runtimes\": [\"electron\"]) and rebuild/reinstall the extension.","Verify the runtime string spelling matches the PluginRuntime union exactly (case-sensitive).","Pass the correct options.runtime to startExtension so it matches a runtime the manifest declares.","Use an extension build/manifest variant that targets the running host."],"exampleFix":"// before\n\"engines\": { \"runtimes\": [\"node\"], \"airi\": \">=1.0.0\" }\n// after\n\"engines\": { \"runtimes\": [\"node\", \"electron\"], \"airi\": \">=1.0.0\" }","handlingStrategy":"validation","validationCode":"if (!manifest.engines.runtimes.includes(currentRuntime)) {\n  throw new Error(`Extension ${manifest.id} unsupported on ${currentRuntime}`)\n}","typeGuard":null,"tryCatchPattern":"try {\n  await host.startExtension(extension, { manifest })\n} catch (e) {\n  if (e.message.includes('does not support runtime')) showIncompatibleExtensionNotice(manifest.id)\n  else throw e\n}","preventionTips":["Keep engines.runtimes in the manifest generated from the build target so it cannot drift.","Add a CI check that validates manifest runtimes against the build matrix.","Test extensions in each runtime the product supports before publishing."],"tags":["plugin-host","manifest","runtime-compatibility","extensions"],"backgroundTag":"unsupported-platform","analyzedSha":"438a067dde47aa0bdb46c2323d1fe293dc805218","analyzedAt":"2026-09-17T01:14:42.644Z","contentChangedAt":"2026-09-17T01:14:42.644Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}