
























@@ -75,14 +75,17 @@ describe("plugin index install records store", () => {
7575expect(JSON.parse(fs.readFileSync(indexPath, "utf8"))).toMatchObject({
7676version: 1,
7777generatedAtMs: 1777118400000,
78+installRecords: {
79+twitch: {
80+source: "npm",
81+spec: "@openclaw/plugin-twitch@1.0.0",
82+installPath: "plugins/npm/@openclaw/plugin-twitch",
83+},
84+},
7885plugins: [
7986{
8087pluginId: "twitch",
81-installRecord: {
82-source: "npm",
83-spec: "@openclaw/plugin-twitch@1.0.0",
84-installPath: "plugins/npm/@openclaw/plugin-twitch",
85-},
88+installRecordHash: expect.stringMatching(/^[a-f0-9]{64}$/u),
8689},
8790],
8891});
@@ -95,6 +98,47 @@ describe("plugin index install records store", () => {
9598});
9699});
97100101+it("preserves install records for plugins without a discovered manifest", async () => {
102+const stateDir = makeStateDir();
103+104+await writePersistedInstalledPluginIndexInstallRecords(
105+{
106+missing: {
107+source: "npm",
108+spec: "missing-plugin@1.0.0",
109+installPath: path.join(stateDir, "plugins", "missing"),
110+},
111+},
112+{
113+ stateDir,
114+candidates: [],
115+now: () => new Date(1777118400000),
116+},
117+);
118+119+expect(
120+JSON.parse(
121+fs.readFileSync(resolveInstalledPluginIndexRecordsStorePath({ stateDir }), "utf8"),
122+),
123+).toMatchObject({
124+installRecords: {
125+missing: {
126+source: "npm",
127+spec: "missing-plugin@1.0.0",
128+installPath: path.join(stateDir, "plugins", "missing"),
129+},
130+},
131+plugins: [],
132+});
133+await expect(loadInstalledPluginIndexInstallRecords({ stateDir })).resolves.toEqual({
134+missing: {
135+source: "npm",
136+spec: "missing-plugin@1.0.0",
137+installPath: path.join(stateDir, "plugins", "missing"),
138+},
139+});
140+});
141+98142it("reads persisted records from the plugin index", async () => {
99143const stateDir = makeStateDir();
100144const candidate = createPluginCandidate(stateDir, "persisted");
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。