languageServer-discovery.test.ts•4.66 kB
import { describe, it, expect, beforeEach, vi } from 'vitest'
import { LanguageServerManager } from '../../src/languageServerManager'
import type { LanguageServerConfig } from '../../src/types/languageServer'
import * as fs from 'fs/promises'
// Mock the fs module
vi.mock('fs/promises')
// Only test the discovery functionality without initializing TypeScript
describe('LanguageServerManager - Discovery', () => {
let manager: LanguageServerManager
let mockConfig: LanguageServerConfig
beforeEach(() => {
vi.clearAllMocks()
mockConfig = {
monorepoRoot: '/test/monorepo',
projects: [],
}
manager = new LanguageServerManager(mockConfig)
})
describe('discoverProjects', () => {
it('should discover TypeScript projects in monorepo', async () => {
// Mock file system structure
vi.mocked(fs.readdir).mockImplementation((dir, _options) => {
if (dir === '/test/monorepo') {
return Promise.resolve([
{ name: 'package-a', isDirectory: () => true },
{ name: 'package-b', isDirectory: () => true },
{ name: 'node_modules', isDirectory: () => true },
{ name: '.git', isDirectory: () => true },
] as any)
} else if (dir === '/test/monorepo/package-a') {
return Promise.resolve([
{ name: 'tsconfig.json', isDirectory: () => false },
{ name: 'package.json', isDirectory: () => false },
] as any)
} else if (dir === '/test/monorepo/package-b') {
return Promise.resolve([
{ name: 'tsconfig.json', isDirectory: () => false },
{ name: 'package.json', isDirectory: () => false },
] as any)
}
return Promise.resolve([])
})
vi.mocked(fs.readFile).mockImplementation((filePath) => {
const pathStr = filePath as string
if (pathStr.includes('package-a/package.json')) {
return Promise.resolve(
JSON.stringify({
name: 'package-a',
dependencies: {},
})
)
} else if (pathStr.includes('package-b/package.json')) {
return Promise.resolve(
JSON.stringify({
name: 'package-b',
devDependencies: {
'@sveltejs/kit': '^1.0.0',
},
})
)
}
return Promise.resolve('{}')
})
const projects = await manager.discoverProjects()
expect(projects).toHaveLength(2)
expect(projects[0]).toEqual({
name: 'package-a',
path: 'package-a',
type: 'node',
tsconfigPath: 'tsconfig.json',
rootDir: '/test/monorepo/package-a',
})
expect(projects[1]).toEqual({
name: 'package-b',
path: 'package-b',
type: 'sveltekit',
tsconfigPath: 'tsconfig.json',
rootDir: '/test/monorepo/package-b',
})
})
it('should skip hidden directories and node_modules', async () => {
vi.mocked(fs.readdir).mockResolvedValue([
{ name: '.hidden', isDirectory: () => true },
{ name: 'node_modules', isDirectory: () => true },
{ name: 'valid-package', isDirectory: () => true },
] as any)
await manager.discoverProjects()
// Should only process valid-package
expect(fs.readdir).toHaveBeenCalledWith('/test/monorepo', { withFileTypes: true })
expect(fs.readdir).not.toHaveBeenCalledWith(
'/test/monorepo/.hidden',
expect.any(Object)
)
expect(fs.readdir).not.toHaveBeenCalledWith(
'/test/monorepo/node_modules',
expect.any(Object)
)
})
})
describe('getProjectForFile', () => {
it('should return undefined for files outside any project', () => {
const result = manager.getProjectForFile('/outside/file.ts')
expect(result).toBeUndefined()
})
})
})