jan/web-app/src/hooks/__tests__/useModelProvider.test.ts
2025-09-30 21:48:38 +07:00

183 lines
4.9 KiB
TypeScript

import { describe, it, expect, beforeEach, vi } from 'vitest'
import { act, renderHook } from '@testing-library/react'
import { useModelProvider } from '../useModelProvider'
// Mock getServiceHub
vi.mock('@/hooks/useServiceHub', () => ({
getServiceHub: vi.fn(() => ({
path: () => ({
sep: () => '/',
}),
})),
}))
// Mock the localStorage key constants
vi.mock('@/constants/localStorage', () => ({
localStorageKey: {
modelProvider: 'jan-model-provider',
},
}))
// Mock localStorage
const localStorageMock = {
getItem: vi.fn(),
setItem: vi.fn(),
removeItem: vi.fn(),
clear: vi.fn(),
}
Object.defineProperty(window, 'localStorage', {
value: localStorageMock,
writable: true,
})
describe('useModelProvider - displayName functionality', () => {
beforeEach(() => {
vi.clearAllMocks()
localStorageMock.getItem.mockReturnValue(null)
// Reset Zustand store to default state
act(() => {
useModelProvider.setState({
providers: [],
selectedProvider: 'llamacpp',
selectedModel: null,
deletedModels: [],
})
})
})
it('should handle models without displayName property', () => {
const { result } = renderHook(() => useModelProvider())
const provider = {
provider: 'llamacpp',
active: true,
models: [
{
id: 'test-model.gguf',
capabilities: ['completion'],
},
],
settings: [],
} as any
// First add the provider, then update it (since updateProvider only updates existing providers)
act(() => {
result.current.addProvider(provider)
})
const updatedProvider = result.current.getProviderByName('llamacpp')
expect(updatedProvider?.models[0].displayName).toBeUndefined()
expect(updatedProvider?.models[0].id).toBe('test-model.gguf')
})
it('should preserve displayName when merging providers in setProviders', () => {
const { result } = renderHook(() => useModelProvider())
// First, set up initial state with displayName via direct state manipulation
// This simulates the scenario where a user has already customized a display name
act(() => {
useModelProvider.setState({
providers: [
{
provider: 'llamacpp',
active: true,
models: [
{
id: 'test-model.gguf',
displayName: 'My Custom Model',
capabilities: ['completion'],
},
],
settings: [],
},
] as any,
selectedProvider: 'llamacpp',
selectedModel: null,
deletedModels: [],
})
})
// Now simulate setProviders with fresh data (like from server refresh)
const freshProviders = [
{
provider: 'llamacpp',
active: true,
persist: true,
models: [
{
id: 'test-model.gguf',
capabilities: ['completion'],
// Note: no displayName in fresh data
},
],
settings: [],
},
] as any
act(() => {
result.current.setProviders(freshProviders)
})
// The displayName should be preserved from existing state
const provider = result.current.getProviderByName('llamacpp')
expect(provider?.models[0].displayName).toBe('My Custom Model')
})
it('should provide basic functionality without breaking existing behavior', () => {
const { result } = renderHook(() => useModelProvider())
// Test that basic provider operations work
expect(result.current.providers).toEqual([])
expect(result.current.selectedProvider).toBe('llamacpp')
expect(result.current.selectedModel).toBeNull()
// Test addProvider functionality
const provider = {
provider: 'openai',
active: true,
models: [],
settings: [],
} as any
act(() => {
result.current.addProvider(provider)
})
expect(result.current.providers).toHaveLength(1)
expect(result.current.getProviderByName('openai')).toBeDefined()
})
it('should handle provider operations with models that have displayName', () => {
const { result } = renderHook(() => useModelProvider())
// Test that we can at least get and set providers with displayName models
const providerWithDisplayName = {
provider: 'llamacpp',
active: true,
models: [
{
id: 'test-model.gguf',
displayName: 'Custom Model Name',
capabilities: ['completion'],
},
],
settings: [],
} as any
// Set the state directly (simulating what would happen in real usage)
act(() => {
useModelProvider.setState({
providers: [providerWithDisplayName],
selectedProvider: 'llamacpp',
selectedModel: null,
deletedModels: [],
})
})
const provider = result.current.getProviderByName('llamacpp')
expect(provider?.models[0].displayName).toBe('Custom Model Name')
expect(provider?.models[0].id).toBe('test-model.gguf')
})
})