diff --git a/packages/main/src/plugin/extension/catalog/extensions-catalog-settings.ts b/packages/main/src/plugin/extension/catalog/extensions-catalog-settings.ts
index fcdd767b869..c9bdb537d32 100644
--- a/packages/main/src/plugin/extension/catalog/extensions-catalog-settings.ts
+++ b/packages/main/src/plugin/extension/catalog/extensions-catalog-settings.ts
@@ -19,4 +19,5 @@
export enum ExtensionsCatalogSettings {
SectionName = 'extensions',
registryUrl = 'registryUrl',
+ catalogEnabled = 'catalog.enabled',
}
diff --git a/packages/main/src/plugin/extension/catalog/extensions-catalog.spec.ts b/packages/main/src/plugin/extension/catalog/extensions-catalog.spec.ts
index d1e987ebad6..7fa9593cd44 100644
--- a/packages/main/src/plugin/extension/catalog/extensions-catalog.spec.ts
+++ b/packages/main/src/plugin/extension/catalog/extensions-catalog.spec.ts
@@ -400,7 +400,7 @@ test('Should use proxy object if proxySettings is undefined', () => {
expect(options.agent?.https?.proxy.href).toBe('https://localhost/');
});
-test('should register local extensions enabled configuration property', () => {
+test('should register local extensions and catalog enabled configuration properties', () => {
extensionsCatalog.init();
expect(configurationRegistry.registerConfigurations).toHaveBeenCalledWith([
@@ -415,6 +415,12 @@ test('should register local extensions enabled configuration property', () => {
default: true,
hidden: true,
},
+ 'extensions.catalog.enabled': {
+ description: 'Show the extension catalog in the UI. When disabled, hides the catalog suggestions.',
+ type: 'boolean',
+ default: true,
+ hidden: true,
+ },
}),
}),
]);
diff --git a/packages/main/src/plugin/extension/catalog/extensions-catalog.ts b/packages/main/src/plugin/extension/catalog/extensions-catalog.ts
index 627490c6574..a9e17bab962 100644
--- a/packages/main/src/plugin/extension/catalog/extensions-catalog.ts
+++ b/packages/main/src/plugin/extension/catalog/extensions-catalog.ts
@@ -75,6 +75,12 @@ export class ExtensionsCatalog {
default: true,
hidden: true,
},
+ [ExtensionsCatalogSettings.SectionName + '.' + ExtensionsCatalogSettings.catalogEnabled]: {
+ description: 'Show the extension catalog in the UI. When disabled, hides the catalog suggestions.',
+ type: 'boolean',
+ default: true,
+ hidden: true,
+ },
},
};
diff --git a/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.spec.ts b/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.spec.ts
index 1e37cbc6a4a..8dd84d624e0 100644
--- a/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.spec.ts
+++ b/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.spec.ts
@@ -34,6 +34,8 @@ beforeAll(() => {
beforeEach(() => {
vi.resetAllMocks();
+ // default to catalog enabled
+ vi.mocked(window.getConfigurationValue).mockResolvedValue(true);
});
const aFakeExtension: CatalogExtension = {
@@ -218,3 +220,29 @@ test('empty catalog, hide if empty', async () => {
const emptyMsg = screen.queryByText('No extensions in the catalog');
expect(emptyMsg).not.toBeInTheDocument();
});
+
+test('render nothing when catalog is disabled', async () => {
+ vi.mocked(window.getConfigurationValue).mockResolvedValue(false);
+ catalogExtensionInfos.set([aFakeExtension, bFakeExtension]);
+ extensionInfos.set(combined);
+
+ render(EmbeddableCatalogExtensionList, {});
+
+ await vi.waitFor(() => {
+ expect(screen.queryByText('Available extensions')).not.toBeInTheDocument();
+ expect(screen.queryByRole('group', { name: 'A Extension' })).not.toBeInTheDocument();
+ expect(screen.queryByRole('group', { name: 'B Extension' })).not.toBeInTheDocument();
+ });
+});
+
+test('render extensions when catalog is enabled', async () => {
+ vi.mocked(window.getConfigurationValue).mockResolvedValue(true);
+ catalogExtensionInfos.set([aFakeExtension, bFakeExtension]);
+ extensionInfos.set(combined);
+
+ render(EmbeddableCatalogExtensionList, {});
+
+ await vi.waitFor(() => {
+ expect(screen.queryByText('Available extensions')).toBeInTheDocument();
+ });
+});
diff --git a/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.svelte b/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.svelte
index 199f0b63572..3c882ea2d55 100644
--- a/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.svelte
+++ b/packages/renderer/src/lib/extensions/EmbeddableCatalogExtensionList.svelte
@@ -1,4 +1,5 @@
+{#if enableCatalog}
= derived(
showEmptyScreen={showEmptyScreen}
catalogExtensions={$catalogExtensions} />
+{/if}
diff --git a/packages/renderer/src/lib/extensions/ExtensionList.spec.ts b/packages/renderer/src/lib/extensions/ExtensionList.spec.ts
index f16b110cd61..aa3174e0be1 100644
--- a/packages/renderer/src/lib/extensions/ExtensionList.spec.ts
+++ b/packages/renderer/src/lib/extensions/ExtensionList.spec.ts
@@ -239,8 +239,8 @@ test('Search catalog page searches also description', async () => {
test('Expect to see local extensions tab content', async () => {
vi.mocked(window.getConfigurationValue).mockImplementation(async (key: string) => {
- // Return true for local extensions enabled, false for development mode to show empty screen
- return key === 'extensions.localExtensions.enabled';
+ // Return true for local extensions and catalog enabled
+ return key === 'extensions.localExtensions.enabled' || key === 'extensions.catalog.enabled';
});
catalogExtensionInfos.set([]);
extensionInfos.set([]);
@@ -330,3 +330,28 @@ test('Expect local extensions tab to not be visible if extensions.localExtension
const localExtensionsTab = screen.queryByRole('button', { name: 'Local Extensions' });
expect(localExtensionsTab).not.toBeInTheDocument();
});
+
+test('Expect catalog tab is visible', async () => {
+ vi.mocked(window.getConfigurationValue).mockResolvedValue(undefined);
+ catalogExtensionInfos.set([]);
+ extensionInfos.set([]);
+
+ render(ExtensionList);
+
+ await vi.waitFor(() => {
+ const catalogTab = screen.getByRole('button', { name: 'Catalog' });
+ expect(catalogTab).toBeInTheDocument();
+ });
+});
+
+test('Expect catalog tab to not be visible if extensions.catalog.enabled is false', async () => {
+ vi.mocked(window.getConfigurationValue).mockResolvedValue(false);
+ catalogExtensionInfos.set([]);
+ extensionInfos.set([]);
+
+ render(ExtensionList);
+
+ await vi.waitFor(() => {
+ expect(screen.queryByRole('button', { name: 'Catalog' })).not.toBeInTheDocument();
+ });
+});
diff --git a/packages/renderer/src/lib/extensions/ExtensionList.svelte b/packages/renderer/src/lib/extensions/ExtensionList.svelte
index 5adcd6b838c..33a67b3cff9 100644
--- a/packages/renderer/src/lib/extensions/ExtensionList.svelte
+++ b/packages/renderer/src/lib/extensions/ExtensionList.svelte
@@ -32,6 +32,8 @@ let enableLocalExtensions = $derived(
(await window.getConfigurationValue('extensions.localExtensions.enabled')) ?? true,
);
+let enableCatalog = $derived((await window.getConfigurationValue('extensions.catalog.enabled')) ?? true);
+
const filteredInstalledExtensions: CombinedExtensionInfoUI[] = $derived(
extensionsUtils.filterInstalledExtensions($combinedInstalledExtensions, searchTerm),
);
@@ -102,12 +104,14 @@ function changeScreen(newScreen: 'installed' | 'catalog' | 'development'): void
changeScreen('installed');
}}
selected={screen === 'installed'}>Installed
-
+ {#if enableCatalog}
+
+ {/if}
{#if enableLocalExtensions}