fix: resolve features-store test timeouts and dynamic icon-map test (#151)

- Fix installAll tests timing out by returning installed status from
  refreshBundles mock (prevents infinite retry loop) and increasing
  waitFor/test timeouts to accommodate the 2s inter-install delay
- Fix zustand-stores installAll test with same refreshBundles mock fix
- Icon-map test already fixed to derive from shared constants
This commit is contained in:
SnapOtter
2026-05-18 17:24:36 +08:00
committed by GitHub
parent 8b85a8c386
commit 436576fe15
2 changed files with 23 additions and 17 deletions
+19 -15
View File
@@ -374,7 +374,9 @@ describe("useFeaturesStore", () => {
} }
return Promise.resolve({}); return Promise.resolve({});
}); });
apiGetMock.mockResolvedValue({ bundles }); apiGetMock.mockResolvedValue({
bundles: bundles.map((b) => ({ ...b, status: "installed" })),
});
const promise = useFeaturesStore.getState().installAll(); const promise = useFeaturesStore.getState().installAll();
@@ -382,13 +384,18 @@ describe("useFeaturesStore", () => {
expect(useFeaturesStore.getState().installAllActive).toBe(true); expect(useFeaturesStore.getState().installAllActive).toBe(true);
}); });
const completeAllOpen = () => {
for (const es of FakeEventSource.instances) {
if (!es.closed) {
es.onmessage?.({ data: JSON.stringify({ phase: "complete" }) });
}
}
};
await vi.waitFor(() => { await vi.waitFor(() => {
expect(FakeEventSource.instances.length).toBeGreaterThan(0); expect(FakeEventSource.instances.length).toBeGreaterThan(0);
}); });
completeAllOpen();
for (const es of FakeEventSource.instances) {
es.onmessage?.({ data: JSON.stringify({ phase: "complete" }) });
}
await vi await vi
.waitFor( .waitFor(
@@ -397,22 +404,17 @@ describe("useFeaturesStore", () => {
throw new Error("waiting for second EventSource"); throw new Error("waiting for second EventSource");
} }
}, },
{ timeout: 2000 }, { timeout: 5000 },
) )
.catch(() => {}); .catch(() => {});
completeAllOpen();
for (const es of FakeEventSource.instances) {
if (!es.closed) {
es.onmessage?.({ data: JSON.stringify({ phase: "complete" }) });
}
}
await promise; await promise;
const state = useFeaturesStore.getState(); const state = useFeaturesStore.getState();
expect(state.installAllActive).toBe(false); expect(state.installAllActive).toBe(false);
expect(state.queued).toEqual([]); expect(state.queued).toEqual([]);
}); }, 15000);
it("clears stale errors for pending bundles", async () => { it("clears stale errors for pending bundles", async () => {
const bundles = [makeBundleState({ id: "err-bundle", status: "error" })]; const bundles = [makeBundleState({ id: "err-bundle", status: "error" })];
@@ -423,7 +425,9 @@ describe("useFeaturesStore", () => {
}); });
apiPostMock.mockResolvedValue({ jobId: "job-err" }); apiPostMock.mockResolvedValue({ jobId: "job-err" });
apiGetMock.mockResolvedValue({ bundles }); apiGetMock.mockResolvedValue({
bundles: bundles.map((b) => ({ ...b, status: "installed" })),
});
const promise = useFeaturesStore.getState().installAll(); const promise = useFeaturesStore.getState().installAll();
@@ -440,7 +444,7 @@ describe("useFeaturesStore", () => {
} }
await promise; await promise;
}); }, 15000);
}); });
describe("EventSource progress handling", () => { describe("EventSource progress handling", () => {
+4 -2
View File
@@ -2677,13 +2677,15 @@ describe("useFeaturesStore", () => {
); );
mockApiPost.mockResolvedValueOnce({ jobId: "job-clear" }); mockApiPost.mockResolvedValueOnce({ jobId: "job-clear" });
mockApiGet.mockResolvedValue({ bundles }); mockApiGet.mockResolvedValue({
bundles: bundles.map((b) => ({ ...b, status: "installed" as const })),
});
await useFeaturesStore.getState().installAll(); await useFeaturesStore.getState().installAll();
// Error should have been cleared at the start of installAll // Error should have been cleared at the start of installAll
expect(useFeaturesStore.getState().errors["ai-rembg"]).toBeUndefined(); expect(useFeaturesStore.getState().errors["ai-rembg"]).toBeUndefined();
}); }, 15000);
}); });
// ========================================================================== // ==========================================================================