fix: start plugins after signing in, not only after the next reload

This commit is contained in:
Linus Rath
2026-10-25 02:06:35 +02:00
parent 4efb9a2a75
commit 23eb3c5a2f
2 changed files with 23 additions and 3 deletions
+15
View File
@@ -238,6 +238,21 @@ describe('usePluginStore', () => {
expect(usePluginStore.getState().plugins[0].bundleHash).toBe('hash-v1');
});
it('starts the plugins after a sign-in when the first call ran signed out', async () => {
const { loadPlugin } = await import('@/lib/plugin-loader');
// The mail view mounts before the user has signed in.
mocks.apiFetch.mockResolvedValueOnce({ ok: false, status: 401, json: async () => ({ error: 'Not authenticated' }) });
await usePluginStore.getState().initializePlugins();
expect(usePluginStore.getState().initialized).toBe(false);
expect(loadPlugin).not.toHaveBeenCalled();
// plugin-app-events calls again once the user is signed in.
await usePluginStore.getState().initializePlugins();
expect(loadPlugin).toHaveBeenCalledWith(expect.objectContaining({ id: 'managed-plugin' }));
expect(usePluginStore.getState().initialized).toBe(true);
});
it('keeps the record when the download fails so the error can surface at load time', async () => {
usePluginStore.setState({ plugins: [syncedRecord()] });
mocks.downloadManagedBundle.mockRejectedValue(new Error('Could not download the bundle (HTTP 503)'));
+8 -3
View File
@@ -301,8 +301,12 @@ export const usePluginStore = create<PluginStoreState>()(
});
}
// Sync server-managed plugins before loading
await syncServerPlugins(get, set);
// Sync server-managed plugins before loading. The mail view starts
// this on mount, before the user has signed in; marking the store
// initialized then left every plugin off after the sign-in until
// the next page load. Stay uninitialized so the call that follows
// the sign-in (plugin-app-events) starts them.
if (await syncServerPlugins(get, set) === 'signed-out') return;
// Load all enabled plugins in parallel. Sequential `await` made one
// hung/slow plugin block every subsequent one; loadSandboxedPlugin
@@ -502,9 +506,10 @@ function markServerManagedPlugins(plugins: InstalledPlugin[]): InstalledPlugin[]
async function syncServerPlugins(
get: () => PluginStoreState,
set: (partial: Partial<PluginStoreState> | ((state: PluginStoreState) => Partial<PluginStoreState>)) => void,
): Promise<void> {
): Promise<'signed-out' | void> {
try {
const res = await apiFetch('/api/plugins');
if (res.status === 401) return 'signed-out';
if (!res.ok) return;
const data: { plugins: ServerPluginInfo[] } = await res.json();