feat: US-004 - Preload ONNX model during boot sequence
This commit is contained in:
@@ -6,6 +6,7 @@ import { LoginScreen } from './components/LoginScreen'
|
|||||||
import { DashboardLayout } from './components/DashboardLayout'
|
import { DashboardLayout } from './components/DashboardLayout'
|
||||||
import { AccessibilityProvider } from './contexts/AccessibilityContext'
|
import { AccessibilityProvider } from './contexts/AccessibilityContext'
|
||||||
import { DetailPanelProvider } from './contexts/DetailPanelContext'
|
import { DetailPanelProvider } from './contexts/DetailPanelContext'
|
||||||
|
import { initModel } from './lib/embedding-model'
|
||||||
|
|
||||||
function SkipButton({ onSkip }: { onSkip: () => void }) {
|
function SkipButton({ onSkip }: { onSkip: () => void }) {
|
||||||
const [visible, setVisible] = useState(false)
|
const [visible, setVisible] = useState(false)
|
||||||
@@ -47,6 +48,10 @@ function App() {
|
|||||||
const [phase, setPhase] = useState<Phase>('login')
|
const [phase, setPhase] = useState<Phase>('login')
|
||||||
const cursorPositionRef = useRef<{ x: number; y: number } | null>(null)
|
const cursorPositionRef = useRef<{ x: number; y: number } | null>(null)
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
initModel()
|
||||||
|
}, [])
|
||||||
|
|
||||||
const skipToLogin = () => setPhase('login')
|
const skipToLogin = () => setPhase('login')
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -0,0 +1,26 @@
|
|||||||
|
import { pipeline, type FeatureExtractionPipeline } from '@xenova/transformers'
|
||||||
|
|
||||||
|
let extractor: FeatureExtractionPipeline | null = null
|
||||||
|
let loading = false
|
||||||
|
|
||||||
|
export async function initModel(): Promise<void> {
|
||||||
|
if (extractor || loading) return
|
||||||
|
loading = true
|
||||||
|
try {
|
||||||
|
extractor = await pipeline('feature-extraction', 'Xenova/all-MiniLM-L6-v2') as FeatureExtractionPipeline
|
||||||
|
} catch {
|
||||||
|
// Silently swallow — model unavailable, semantic search won't activate
|
||||||
|
} finally {
|
||||||
|
loading = false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function embedQuery(text: string): Promise<number[]> {
|
||||||
|
if (!extractor) throw new Error('Model not loaded')
|
||||||
|
const output = await extractor(text, { pooling: 'mean', normalize: true })
|
||||||
|
return Array.from(output.data as Float32Array)
|
||||||
|
}
|
||||||
|
|
||||||
|
export function isModelReady(): boolean {
|
||||||
|
return extractor !== null
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user