diff --git a/invokeai/frontend/web/public/locales/en.json b/invokeai/frontend/web/public/locales/en.json
index f7dde4bd302..5f84b849380 100644
--- a/invokeai/frontend/web/public/locales/en.json
+++ b/invokeai/frontend/web/public/locales/en.json
@@ -294,6 +294,11 @@
"disableFailed": "Problem Disabling Invocation Cache",
"useCache": "Use Cache"
},
+ "modelCache": {
+ "clear": "Clear Model Cache",
+ "clearSucceeded": "Model Cache Cleared",
+ "clearFailed": "Problem Clearing Model Cache"
+ },
"gallery": {
"gallery": "Gallery",
"alwaysShowImageSizeBadge": "Always Show Image Size Badge",
diff --git a/invokeai/frontend/web/src/app/types/invokeai.ts b/invokeai/frontend/web/src/app/types/invokeai.ts
index 39b9fea1fa4..9ea267800b3 100644
--- a/invokeai/frontend/web/src/app/types/invokeai.ts
+++ b/invokeai/frontend/web/src/app/types/invokeai.ts
@@ -23,6 +23,7 @@ export type AppFeature =
| 'pauseQueue'
| 'resumeQueue'
| 'invocationCache'
+ | 'modelCache'
| 'bulkDownload'
| 'starterModels'
| 'hfToken';
diff --git a/invokeai/frontend/web/src/features/queue/components/ClearModelCacheButton.tsx b/invokeai/frontend/web/src/features/queue/components/ClearModelCacheButton.tsx
new file mode 100644
index 00000000000..6c11a9cdc67
--- /dev/null
+++ b/invokeai/frontend/web/src/features/queue/components/ClearModelCacheButton.tsx
@@ -0,0 +1,39 @@
+import { Button } from '@invoke-ai/ui-library';
+import { useFeatureStatus } from 'features/system/hooks/useFeatureStatus';
+import { toast } from 'features/toast/toast';
+import { memo, useCallback } from 'react';
+import { useTranslation } from 'react-i18next';
+import { useEmptyModelCacheMutation } from 'services/api/endpoints/models';
+
+const ClearModelCacheButton = () => {
+ const isModelCacheEnabled = useFeatureStatus('modelCache');
+ const [emptyModelCache, { isLoading }] = useEmptyModelCacheMutation();
+ const { t } = useTranslation();
+
+ const handleClearCache = useCallback(async () => {
+ try {
+ await emptyModelCache().unwrap();
+ toast({
+ status: 'success',
+ title: t('modelCache.clearSucceeded'),
+ });
+ } catch (error) {
+ toast({
+ status: 'error',
+ title: t('modelCache.clearFailed'),
+ });
+ }
+ }, [emptyModelCache, t]);
+
+ if (!isModelCacheEnabled) {
+ return <>>;
+ }
+
+ return (
+
+ );
+};
+
+export default memo(ClearModelCacheButton);
diff --git a/invokeai/frontend/web/src/features/queue/components/QueueTabQueueControls.tsx b/invokeai/frontend/web/src/features/queue/components/QueueTabQueueControls.tsx
index 3aed2f237a1..59bd02a7371 100644
--- a/invokeai/frontend/web/src/features/queue/components/QueueTabQueueControls.tsx
+++ b/invokeai/frontend/web/src/features/queue/components/QueueTabQueueControls.tsx
@@ -1,7 +1,9 @@
+/* eslint-disable i18next/no-literal-string */
import { ButtonGroup, Flex } from '@invoke-ai/ui-library';
import { useFeatureStatus } from 'features/system/hooks/useFeatureStatus';
import { memo } from 'react';
+import ClearModelCacheButton from './ClearModelCacheButton';
import ClearQueueButton from './ClearQueueButton';
import PauseProcessorButton from './PauseProcessorButton';
import PruneQueueButton from './PruneQueueButton';
@@ -11,19 +13,22 @@ const QueueTabQueueControls = () => {
const isPauseEnabled = useFeatureStatus('pauseQueue');
const isResumeEnabled = useFeatureStatus('resumeQueue');
return (
-
- {isPauseEnabled || isResumeEnabled ? (
+
+
+ {isPauseEnabled || isResumeEnabled ? (
+
+ {isResumeEnabled ? : <>>}
+ {isPauseEnabled ? : <>>}
+
+ ) : (
+ <>>
+ )}
- {isResumeEnabled ? : <>>}
- {isPauseEnabled ? : <>>}
+
+
- ) : (
- <>>
- )}
-
-
-
-
+
+
);
};
diff --git a/invokeai/frontend/web/src/services/api/endpoints/models.ts b/invokeai/frontend/web/src/services/api/endpoints/models.ts
index 3180e932b76..1b2421c4cea 100644
--- a/invokeai/frontend/web/src/services/api/endpoints/models.ts
+++ b/invokeai/frontend/web/src/services/api/endpoints/models.ts
@@ -275,6 +275,9 @@ export const modelsApi = api.injectEndpoints({
}
},
}),
+ emptyModelCache: build.mutation({
+ query: () => ({ url: buildModelsUrl('empty_model_cache'), method: 'POST' }),
+ }),
}),
});
@@ -295,6 +298,7 @@ export const {
useGetStarterModelsQuery,
useGetHFTokenStatusQuery,
useSetHFTokenMutation,
+ useEmptyModelCacheMutation,
} = modelsApi;
export const selectModelConfigsQuery = modelsApi.endpoints.getModelConfigs.select();