From 07eab89e58cbd467d1f00c715e86c77023e0d1f1 Mon Sep 17 00:00:00 2001 From: Egor Date: Sat, 25 Oct 2025 17:26:32 -0700 Subject: [PATCH] improve gguf analysis to work with http models and present the data better --- package.json | 2 +- .../screens/Launch/ModelAnalysisModal.tsx | 99 ++++++------------- .../screens/Launch/ModelFileField.tsx | 4 +- src/main/modules/koboldcpp/analyze.ts | 16 ++- 4 files changed, 47 insertions(+), 74 deletions(-) diff --git a/package.json b/package.json index 7f3b431..904843d 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "gerbil", "productName": "Gerbil", - "version": "1.7.4", + "version": "1.7.5", "description": "Run Large Language Models locally", "main": "out/main/index.js", "homepage": "./", diff --git a/src/components/screens/Launch/ModelAnalysisModal.tsx b/src/components/screens/Launch/ModelAnalysisModal.tsx index 53cb12e..5ef10ad 100644 --- a/src/components/screens/Launch/ModelAnalysisModal.tsx +++ b/src/components/screens/Launch/ModelAnalysisModal.tsx @@ -1,5 +1,5 @@ import { Modal } from '@/components/Modal'; -import { Stack, Group, Text, Divider, Alert, rem } from '@mantine/core'; +import { Stack, Group, Text, Alert, rem } from '@mantine/core'; import { Info } from 'lucide-react'; import type { ModelAnalysis } from '@/types'; @@ -21,7 +21,7 @@ const InfoRow = ({ label, value }: InfoRowProps) => { return ( - + {label}: @@ -47,7 +47,6 @@ export const ModelAnalysisModal = ({ Model Analysis } - size="lg" showCloseButton > {loading && ( @@ -63,72 +62,38 @@ export const ModelAnalysisModal = ({ )} {analysis && ( - -
- - General Information - - - - {analysis.general.name && ( - - )} - {analysis.general.parameterCount && ( - - )} - - {analysis.architecture.layers && ( - - )} - {analysis.architecture.expertCount && ( - - )} - -
- - {analysis.context.maxContextLength && ( - <> - -
- - Context - - - - -
- + + {analysis.general.name && ( + )} + + {analysis.general.parameterCount && ( + + )} + - - -
- - Memory Estimates - - - - - {analysis.estimates.vramPerLayer && ( - - )} - -
+ {analysis.architecture.expertCount && ( + + )} + {analysis.context.maxContextLength && ( + + )} + {analysis.architecture.layers && ( + + )} + {!analysis.architecture.layers && ( + + )} +
)} diff --git a/src/components/screens/Launch/ModelFileField.tsx b/src/components/screens/Launch/ModelFileField.tsx index 03becb5..e4b0de2 100644 --- a/src/components/screens/Launch/ModelFileField.tsx +++ b/src/components/screens/Launch/ModelFileField.tsx @@ -46,8 +46,6 @@ export const ModelFileField = ({ return undefined; }; - const isLocalFile = value.trim() && validationState === 'local'; - const handleAnalyzeModel = async () => { if (!value.trim()) return; @@ -99,7 +97,7 @@ export const ModelFileField = ({ )} - {showAnalyze && isLocalFile && ( + {showAnalyze && value.trim() && validationState !== 'invalid' && ( , key: string) { export async function analyzeGGUFModel(filePath: string) { try { - const stats = await stat(filePath); - const fileSize = stats.size; + const isUrl = + filePath.startsWith('http://') || filePath.startsWith('https://'); + + let fileSize: number; + if (isUrl) { + const response = await fetch(filePath, { method: 'HEAD' }); + const contentLength = response.headers.get('content-length'); + fileSize = contentLength ? parseInt(contentLength, 10) : 0; + } else { + const stats = await stat(filePath); + fileSize = stats.size; + } const { metadata } = await gguf(filePath, { - allowLocalFile: true, + allowLocalFile: !isUrl, }); const metadataRecord = metadata as Record;