ruch
Version:
Revolutionary React TypeScript CLI with hexagonal architecture & AI-powered development assistance. Create maintainable, scalable applications with domain-driven design and integrated AI tooling.
189 lines (146 loc) • 7.73 kB
text/typescript
import { describe, it, expect, beforeEach, vi } from 'vitest';
import fs from 'fs-extra';
import { logger } from '../../src/utils/logger';
import { updateMswDomain } from '../../src/commands/msw';
// Mock all dependencies
vi.mock('fs-extra');
vi.mock('../../src/utils/logger', () => ({
logger: {
error: vi.fn(),
success: vi.fn(),
info: vi.fn(),
warning: vi.fn(),
log: vi.fn(),
}
}));
vi.mock('../../src/utils/domain-analyzer', () => ({
getExistingDomains: vi.fn(),
}));
vi.mock('../../src/utils/domain-file-analyzer', () => ({
analyzeDomain: vi.fn(),
}));
describe('MSW Domain Validation Tests', () => {
const projectRoot = '/test/project';
beforeEach(() => {
vi.clearAllMocks();
});
describe('updateMswDomain domain name validation', () => {
it('should reject domain names with hyphens', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
(fs.exists as any).mockResolvedValue(true);
(getExistingDomains as any).mockResolvedValue([
{ name: 'user', path: '/test/domains/user' }
]);
await updateMswDomain('test-analytics', fs, logger, projectRoot, true);
expect(logger.error).toHaveBeenCalledWith('Domain "test-analytics" not found. Available domains: user');
});
it('should reject domain names with spaces', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
(fs.exists as any).mockResolvedValue(true);
(getExistingDomains as any).mockResolvedValue([
{ name: 'user', path: '/test/domains/user' }
]);
await updateMswDomain('test analytics', fs, logger, projectRoot, true);
expect(logger.error).toHaveBeenCalledWith('Domain "test analytics" not found. Available domains: user');
});
it('should accept valid camelCase domain names', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
const { analyzeDomain } = await import('../../src/utils/domain-file-analyzer');
const mockAnalysis = {
domainName: 'testAnalytics',
entities: [{ name: 'TestAnalytics', fields: [], filePath: '' }],
ports: [{ name: 'TestAnalyticsPort', methods: [], filePath: '' }],
adapters: [{ name: 'TestAnalyticsAdapter', methods: [], filePath: '' }],
primaryEntity: { name: 'TestAnalytics', fields: [], filePath: '' }
};
(fs.exists as any).mockImplementation((filePath: string) => {
if (filePath.includes('mocks')) return Promise.resolve(true);
if (filePath.includes('testAnalytics.ts') || filePath.includes('mockData.ts')) return Promise.resolve(true);
return Promise.resolve(false);
});
(fs.readFile as any).mockResolvedValue('// existing content');
(fs.writeFile as any).mockResolvedValue(undefined);
(fs.ensureDir as any).mockResolvedValue(undefined);
(getExistingDomains as any).mockResolvedValue([
{ name: 'testAnalytics', path: '/test/domains/testAnalytics' }
]);
(analyzeDomain as any).mockResolvedValue(mockAnalysis);
await updateMswDomain('testAnalytics', fs, logger, projectRoot, true);
expect(logger.success).toHaveBeenCalledWith('MSW configuration updated for domain "testAnalytics"!');
});
it('should accept valid snake_case domain names', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
const { analyzeDomain } = await import('../../src/utils/domain-file-analyzer');
const mockAnalysis = {
domainName: 'test_analytics',
entities: [{ name: 'TestAnalytics', fields: [], filePath: '' }],
ports: [{ name: 'TestAnalyticsPort', methods: [], filePath: '' }],
adapters: [{ name: 'TestAnalyticsAdapter', methods: [], filePath: '' }],
primaryEntity: { name: 'TestAnalytics', fields: [], filePath: '' }
};
(fs.exists as any).mockImplementation((filePath: string) => {
if (filePath.includes('mocks')) return Promise.resolve(true);
if (filePath.includes('test_analytics.ts') || filePath.includes('mockData.ts')) return Promise.resolve(true);
return Promise.resolve(false);
});
(fs.readFile as any).mockResolvedValue('// existing content');
(fs.writeFile as any).mockResolvedValue(undefined);
(fs.ensureDir as any).mockResolvedValue(undefined);
(getExistingDomains as any).mockResolvedValue([
{ name: 'test_analytics', path: '/test/domains/test_analytics' }
]);
(analyzeDomain as any).mockResolvedValue(mockAnalysis);
await updateMswDomain('test_analytics', fs, logger, projectRoot, true);
expect(logger.success).toHaveBeenCalledWith('MSW configuration updated for domain "test_analytics"!');
});
it('should handle empty domain list gracefully', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
(fs.exists as any).mockResolvedValue(true);
(getExistingDomains as any).mockResolvedValue([]);
await updateMswDomain('anyDomain', fs, logger, projectRoot, true);
expect(logger.error).toHaveBeenCalledWith('Domain "anyDomain" not found. Available domains: ');
});
it('should list available domains when target not found', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
(fs.exists as any).mockResolvedValue(true);
(getExistingDomains as any).mockResolvedValue([
{ name: 'user', path: '/test/domains/user' },
{ name: 'product', path: '/test/domains/product' },
{ name: 'orderProcessing', path: '/test/domains/orderProcessing' }
]);
await updateMswDomain('nonExistent', fs, logger, projectRoot, true);
expect(logger.error).toHaveBeenCalledWith('Domain "nonExistent" not found. Available domains: user, product, orderProcessing');
});
});
describe('Error handling edge cases', () => {
it('should handle very long domain names', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
const veryLongName = 'a'.repeat(100);
(fs.exists as any).mockResolvedValue(true);
(getExistingDomains as any).mockResolvedValue([
{ name: 'user', path: '/test/domains/user' }
]);
await updateMswDomain(veryLongName, fs, logger, projectRoot, true);
expect(logger.error).toHaveBeenCalledWith(`Domain "${veryLongName}" not found. Available domains: user`);
});
it('should handle special characters in domain names', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
const specialCharName = 'test@domain!';
(fs.exists as any).mockResolvedValue(true);
(getExistingDomains as any).mockResolvedValue([
{ name: 'user', path: '/test/domains/user' }
]);
await updateMswDomain(specialCharName, fs, logger, projectRoot, true);
expect(logger.error).toHaveBeenCalledWith(`Domain "${specialCharName}" not found. Available domains: user`);
});
it('should handle numeric domain names', async () => {
const { getExistingDomains } = await import('../../src/utils/domain-analyzer');
(fs.exists as any).mockResolvedValue(true);
(getExistingDomains as any).mockResolvedValue([
{ name: 'user', path: '/test/domains/user' }
]);
await updateMswDomain('123domain', fs, logger, projectRoot, true);
expect(logger.error).toHaveBeenCalledWith('Domain "123domain" not found. Available domains: user');
});
});
});