* call jan api * fix lint * ci: add jan server web * chore: add Dockerfile * clean up ui ux and support for reasoning fields, make app spa * add logo * chore: update tag for preview image * chore: update k8s service name * chore: update image tag and image name * fixed test --------- Co-authored-by: Minh141120 <minh.itptit@gmail.com> Co-authored-by: Nguyen Ngoc Minh <91668012+Minh141120@users.noreply.github.com>
206 lines
7.5 KiB
TypeScript
206 lines
7.5 KiB
TypeScript
import { expect, afterEach, vi } from 'vitest'
|
|
import { cleanup } from '@testing-library/react'
|
|
import * as matchers from '@testing-library/jest-dom/matchers'
|
|
|
|
// extends Vitest's expect method with methods from react-testing-library
|
|
expect.extend(matchers)
|
|
|
|
// Global mock for platform features to enable all features in tests
|
|
// This ensures consistent behavior across all tests and enables testing of
|
|
// platform-specific features like Hub, Hardware monitoring, etc.
|
|
vi.mock('@/lib/platform/const', () => ({
|
|
PlatformFeatures: {
|
|
hardwareMonitoring: true,
|
|
extensionManagement: true,
|
|
localInference: true,
|
|
mcpServers: true,
|
|
localApiServer: true,
|
|
modelHub: true,
|
|
systemIntegrations: true,
|
|
httpsProxy: true,
|
|
defaultProviders: true,
|
|
analytics: true,
|
|
webAutoModelSelection: true,
|
|
modelProviderSettings: true,
|
|
}
|
|
}))
|
|
|
|
// Create a mock ServiceHub
|
|
const mockServiceHub = {
|
|
theme: () => ({
|
|
getTheme: vi.fn().mockReturnValue('light'),
|
|
setTheme: vi.fn(),
|
|
toggleTheme: vi.fn(),
|
|
}),
|
|
window: vi.fn().mockReturnValue({
|
|
minimize: vi.fn(),
|
|
maximize: vi.fn(),
|
|
close: vi.fn(),
|
|
isMaximized: vi.fn().mockResolvedValue(false),
|
|
openLogsWindow: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
events: () => ({
|
|
emit: vi.fn().mockResolvedValue(undefined),
|
|
listen: vi.fn().mockResolvedValue(() => {}),
|
|
}),
|
|
hardware: () => ({
|
|
getHardwareInfo: vi.fn().mockResolvedValue(null),
|
|
getSystemUsage: vi.fn().mockResolvedValue(null),
|
|
getLlamacppDevices: vi.fn().mockResolvedValue([]), // cspell: disable-line
|
|
setActiveGpus: vi.fn().mockResolvedValue(undefined),
|
|
// Legacy methods for backward compatibility
|
|
getGpuInfo: vi.fn().mockResolvedValue([]),
|
|
getCpuInfo: vi.fn().mockResolvedValue({}),
|
|
getMemoryInfo: vi.fn().mockResolvedValue({}),
|
|
}),
|
|
app: () => ({
|
|
getAppSettings: vi.fn().mockResolvedValue({}),
|
|
updateAppSettings: vi.fn().mockResolvedValue(undefined),
|
|
getSystemInfo: vi.fn().mockResolvedValue({}),
|
|
relocateJanDataFolder: vi.fn().mockResolvedValue(undefined),
|
|
getJanDataFolder: vi.fn().mockResolvedValue('/mock/jan/data'),
|
|
}),
|
|
analytic: () => ({
|
|
track: vi.fn(),
|
|
identify: vi.fn(),
|
|
page: vi.fn(),
|
|
}),
|
|
messages: () => ({
|
|
createMessage: vi.fn().mockResolvedValue({ id: 'test-message' }),
|
|
deleteMessage: vi.fn().mockResolvedValue(undefined),
|
|
updateMessage: vi.fn().mockResolvedValue(undefined),
|
|
getMessages: vi.fn().mockResolvedValue([]),
|
|
getMessage: vi.fn().mockResolvedValue(null),
|
|
fetchMessages: vi.fn().mockResolvedValue([]),
|
|
}),
|
|
mcp: () => ({
|
|
updateMCPConfig: vi.fn().mockResolvedValue(undefined),
|
|
restartMCPServers: vi.fn().mockResolvedValue(undefined),
|
|
getMCPConfig: vi.fn().mockResolvedValue({}),
|
|
getTools: vi.fn().mockResolvedValue([]),
|
|
getConnectedServers: vi.fn().mockResolvedValue([]),
|
|
callTool: vi.fn().mockResolvedValue({ error: '', content: [] }),
|
|
callToolWithCancellation: vi.fn().mockReturnValue({
|
|
promise: Promise.resolve({ error: '', content: [] }),
|
|
cancel: vi.fn().mockResolvedValue(undefined),
|
|
token: 'test-token'
|
|
}),
|
|
cancelToolCall: vi.fn().mockResolvedValue(undefined),
|
|
activateMCPServer: vi.fn().mockResolvedValue(undefined),
|
|
deactivateMCPServer: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
threads: () => ({
|
|
createThread: vi.fn().mockResolvedValue({ id: 'test-thread', messages: [] }),
|
|
deleteThread: vi.fn().mockResolvedValue(undefined),
|
|
updateThread: vi.fn().mockResolvedValue(undefined),
|
|
getThreads: vi.fn().mockResolvedValue([]),
|
|
getThread: vi.fn().mockResolvedValue(null),
|
|
fetchThreads: vi.fn().mockResolvedValue([]),
|
|
}),
|
|
providers: () => ({
|
|
getProviders: vi.fn().mockResolvedValue([]),
|
|
createProvider: vi.fn().mockResolvedValue({ id: 'test-provider' }),
|
|
deleteProvider: vi.fn().mockResolvedValue(undefined),
|
|
updateProvider: vi.fn().mockResolvedValue(undefined),
|
|
getProvider: vi.fn().mockResolvedValue(null),
|
|
}),
|
|
models: () => ({
|
|
getModels: vi.fn().mockResolvedValue([]),
|
|
getModel: vi.fn().mockResolvedValue(null),
|
|
createModel: vi.fn().mockResolvedValue({ id: 'test-model' }),
|
|
deleteModel: vi.fn().mockResolvedValue(undefined),
|
|
updateModel: vi.fn().mockResolvedValue(undefined),
|
|
startModel: vi.fn().mockResolvedValue(undefined),
|
|
isModelSupported: vi.fn().mockResolvedValue('GREEN'),
|
|
checkMmprojExists: vi.fn().mockResolvedValue(true), // cspell: disable-line
|
|
stopAllModels: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
assistants: () => ({
|
|
getAssistants: vi.fn().mockResolvedValue([]),
|
|
getAssistant: vi.fn().mockResolvedValue(null),
|
|
createAssistant: vi.fn().mockResolvedValue({ id: 'test-assistant' }),
|
|
deleteAssistant: vi.fn().mockResolvedValue(undefined),
|
|
updateAssistant: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
dialog: () => ({
|
|
open: vi.fn().mockResolvedValue({ confirmed: true }),
|
|
save: vi.fn().mockResolvedValue('/path/to/file'),
|
|
message: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
opener: vi.fn().mockReturnValue({
|
|
open: vi.fn().mockResolvedValue(undefined),
|
|
revealItemInDir: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
updater: () => ({
|
|
checkForUpdates: vi.fn().mockResolvedValue(null),
|
|
installUpdate: vi.fn().mockResolvedValue(undefined),
|
|
downloadAndInstallWithProgress: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
path: vi.fn().mockReturnValue({
|
|
sep: () => '/',
|
|
join: vi.fn((...args) => args.join('/')),
|
|
resolve: vi.fn((path) => path),
|
|
dirname: vi.fn((path) => path.split('/').slice(0, -1).join('/')),
|
|
basename: vi.fn((path) => path.split('/').pop()),
|
|
}),
|
|
core: () => ({
|
|
startCore: vi.fn().mockResolvedValue(undefined),
|
|
stopCore: vi.fn().mockResolvedValue(undefined),
|
|
getCoreStatus: vi.fn().mockResolvedValue('stopped'),
|
|
}),
|
|
deeplink: () => ({ // cspell: disable-line
|
|
register: vi.fn().mockResolvedValue(undefined),
|
|
handle: vi.fn().mockResolvedValue(undefined),
|
|
getCurrent: vi.fn().mockResolvedValue(null),
|
|
onOpenUrl: vi.fn().mockResolvedValue(undefined),
|
|
}),
|
|
}
|
|
|
|
// Mock the useServiceHub module
|
|
vi.mock('@/hooks/useServiceHub', () => ({
|
|
useServiceHub: () => mockServiceHub,
|
|
getServiceHub: () => mockServiceHub,
|
|
initializeServiceHubStore: vi.fn(),
|
|
isServiceHubInitialized: () => true,
|
|
}))
|
|
|
|
// Mock window.matchMedia for useMediaQuery tests
|
|
Object.defineProperty(window, 'matchMedia', {
|
|
writable: true,
|
|
value: vi.fn().mockImplementation(query => ({
|
|
matches: false,
|
|
media: query,
|
|
onchange: null,
|
|
addListener: vi.fn(), // deprecated
|
|
removeListener: vi.fn(), // deprecated
|
|
addEventListener: vi.fn(),
|
|
removeEventListener: vi.fn(),
|
|
dispatchEvent: vi.fn(),
|
|
})),
|
|
})
|
|
|
|
// Mock globalThis.core.api for @janhq/core functions // cspell: disable-line
|
|
;(globalThis as Record<string, unknown>).core = {
|
|
api: {
|
|
getJanDataFolderPath: vi.fn().mockResolvedValue('/mock/jan/data'),
|
|
openFileExplorer: vi.fn().mockResolvedValue(undefined),
|
|
joinPath: vi.fn((...paths: string[]) => paths.join('/')),
|
|
}
|
|
}
|
|
|
|
// Mock globalThis.fs for @janhq/core fs functions // cspell: disable-line
|
|
;(globalThis as Record<string, unknown>).fs = {
|
|
existsSync: vi.fn().mockResolvedValue(false),
|
|
readFile: vi.fn().mockResolvedValue(''),
|
|
writeFile: vi.fn().mockResolvedValue(undefined),
|
|
readdir: vi.fn().mockResolvedValue([]),
|
|
mkdir: vi.fn().mockResolvedValue(undefined),
|
|
unlink: vi.fn().mockResolvedValue(undefined),
|
|
rmdir: vi.fn().mockResolvedValue(undefined),
|
|
}
|
|
|
|
|
|
// runs a cleanup after each test case (e.g. clearing jsdom)
|
|
afterEach(() => {
|
|
cleanup()
|
|
}) |