fix(plugins): keep launch specs production-ready

This commit is contained in:
Vincent Koc
2026-05-03 03:08:32 -07:00
parent 26f2241a87
commit 4545a0ed61
7 changed files with 15 additions and 15 deletions

View File

@@ -19,8 +19,8 @@ Docs: https://docs.openclaw.ai
### Fixes
- Plugins/externalization: pin beta-only official launch packages for ACPX, Google Chat, and LINE to explicit npm beta specs so catalog-driven installs do not trip the prerelease safety guard while npm `latest` still points at beta. Thanks @vincentkoc.
- CLI/doctor: keep missing-plugin repair from overriding official catalog metadata with runtime fallbacks, so ACPX repairs preserve the beta npm spec during the externalization rollout. Thanks @vincentkoc.
- Plugins/externalization: keep official ACPX, Google Chat, and LINE install specs on production package names, leaving beta-tag probing to the explicit OpenClaw beta update channel. Thanks @vincentkoc.
- CLI/doctor: keep missing-plugin repair from overriding official catalog metadata with runtime fallbacks, so ACPX repairs preserve the official npm spec during the externalization rollout. Thanks @vincentkoc.
- Plugins/catalog: preserve ClawHub install specs when generating the packaged channel catalog so future storepack-first channel plugins keep their remote source instead of becoming npm-only. Thanks @vincentkoc.
- Plugins/update: treat catalog-matched official npm updates and OpenClaw-authored externalized-bundled npm bridges as trusted official installs so launch-code plugins can update or migrate out of the bundled tree without scanner false positives. Thanks @vincentkoc.
- Plugins/onboarding: fall back from ClawHub to npm only for missing package/version errors, keeping integrity and verification failures fail-closed during storepack rollout. Thanks @vincentkoc.

View File

@@ -176,7 +176,7 @@
]
},
"install": {
"npmSpec": "@openclaw/googlechat@beta",
"npmSpec": "@openclaw/googlechat",
"defaultChoice": "npm",
"minHostVersion": ">=2026.4.10"
}
@@ -201,7 +201,7 @@
"quickstartAllowFrom": true
},
"install": {
"npmSpec": "@openclaw/line@beta",
"npmSpec": "@openclaw/line",
"defaultChoice": "npm",
"minHostVersion": ">=2026.4.10"
}

View File

@@ -11,7 +11,7 @@
"label": "ACPX Runtime"
},
"install": {
"npmSpec": "@openclaw/acpx@beta",
"npmSpec": "@openclaw/acpx",
"defaultChoice": "npm",
"minHostVersion": ">=2026.4.25"
}

View File

@@ -423,7 +423,7 @@ describe("repairMissingConfiguredPluginInstalls", () => {
id: "acpx",
label: "ACPX Runtime",
install: {
npmSpec: "@openclaw/acpx@beta",
npmSpec: "@openclaw/acpx",
defaultChoice: "npm",
},
},
@@ -442,13 +442,13 @@ describe("repairMissingConfiguredPluginInstalls", () => {
expect(mocks.installPluginFromNpmSpec).toHaveBeenCalledWith(
expect.objectContaining({
spec: "@openclaw/acpx@beta",
spec: "@openclaw/acpx",
expectedPluginId: "acpx",
trustedSourceLinkedOfficialInstall: true,
}),
);
expect(result.changes).toEqual([
'Installed missing configured plugin "acpx" from @openclaw/acpx@beta.',
'Installed missing configured plugin "acpx" from @openclaw/acpx.',
]);
});

View File

@@ -44,7 +44,7 @@ const RUNTIME_PLUGIN_INSTALL_CANDIDATES: readonly DownloadableInstallCandidate[]
{
pluginId: "acpx",
label: "ACPX Runtime",
npmSpec: "@openclaw/acpx@beta",
npmSpec: "@openclaw/acpx",
trustedSourceLinkedOfficialInstall: true,
},
// Runtime-only configs do not have a provider/channel integration catalog entry.

View File

@@ -23,17 +23,17 @@ describe("official external plugin catalog", () => {
);
});
it("opts current beta-only official launch packages into prerelease npm tags", () => {
it("keeps official launch package specs on the production package names", () => {
expect(
resolveOfficialExternalPluginInstall(getOfficialExternalPluginCatalogEntry("acpx")!)?.npmSpec,
).toBe("@openclaw/acpx@beta");
).toBe("@openclaw/acpx");
expect(
resolveOfficialExternalPluginInstall(getOfficialExternalPluginCatalogEntry("googlechat")!)
?.npmSpec,
).toBe("@openclaw/googlechat@beta");
).toBe("@openclaw/googlechat");
expect(
resolveOfficialExternalPluginInstall(getOfficialExternalPluginCatalogEntry("line")!)?.npmSpec,
).toBe("@openclaw/line@beta");
).toBe("@openclaw/line");
});
it("keeps Matrix and Mattermost out of the external catalog until cutover", () => {

View File

@@ -489,7 +489,7 @@ describe("updateNpmInstalledPlugins", () => {
await updateNpmInstalledPlugins({
config: createNpmInstallConfig({
pluginId: "acpx",
spec: "@openclaw/acpx@beta",
spec: "@openclaw/acpx",
installPath,
resolvedName: "@openclaw/acpx",
resolvedSpec: "@openclaw/acpx@2026.5.2-beta.1",
@@ -500,7 +500,7 @@ describe("updateNpmInstalledPlugins", () => {
expect(installPluginFromNpmSpecMock).toHaveBeenCalledWith(
expect.objectContaining({
spec: "@openclaw/acpx@beta",
spec: "@openclaw/acpx",
expectedPluginId: "acpx",
trustedSourceLinkedOfficialInstall: true,
}),