UNPKG

backend-mcp

Version:

Generador automático de backends con Node.js, Express, Prisma y módulos configurables. Servidor MCP compatible con npx para agentes IA. Soporta PostgreSQL, MySQL, MongoDB y SQLite.

234 lines (196 loc) 8.19 kB
/** * Pruebas para el sistema de autenticación JWT */ const { validateJWT, hasToolPermission, extractToken, authenticateToolCall } = require('./jwt-auth'); const authConfig = require('./auth-config'); // Mock de https para las pruebas jest.mock('https'); describe('JWT Authentication System', () => { describe('extractToken', () => { test('should extract token from command line arguments', () => { const context = { args: ['--jwt', 'test-token-123'] }; expect(extractToken(context)).toBe('test-token-123'); }); test('should extract token from environment variables', () => { process.env.BACKEND_MCP_JWT = 'env-token-456'; const context = {}; expect(extractToken(context)).toBe('env-token-456'); delete process.env.BACKEND_MCP_JWT; }); test('should extract token from MCP message params', () => { const context = { mcpMessage: { params: { arguments: { jwt: 'mcp-token-789' } } } }; expect(extractToken(context)).toBe('mcp-token-789'); }); test('should return null when no token found', () => { const context = {}; expect(extractToken(context)).toBeNull(); }); }); describe('hasToolPermission', () => { test('should allow basic tools for basic plan', () => { const userData = { plan: 'basic', permissions: ['basic'] }; expect(hasToolPermission(userData, 'configure_project')).toBe(true); expect(hasToolPermission(userData, 'create_endpoint')).toBe(true); }); test('should deny premium tools for basic plan', () => { const userData = { plan: 'basic', permissions: ['basic'] }; expect(hasToolPermission(userData, 'setup_docker')).toBe(false); expect(hasToolPermission(userData, 'setup_ci_cd')).toBe(false); }); test('should allow premium tools for premium plan', () => { const userData = { plan: 'premium', permissions: ['basic', 'premium'] }; expect(hasToolPermission(userData, 'configure_project')).toBe(true); expect(hasToolPermission(userData, 'setup_docker')).toBe(true); }); test('should allow all tools for enterprise plan', () => { const userData = { plan: 'enterprise', permissions: ['basic', 'premium', 'enterprise'] }; expect(hasToolPermission(userData, 'configure_project')).toBe(true); expect(hasToolPermission(userData, 'setup_docker')).toBe(true); expect(hasToolPermission(userData, 'setup_microservices')).toBe(true); }); test('should return false for invalid user data', () => { expect(hasToolPermission(null, 'configure_project')).toBe(false); expect(hasToolPermission({}, 'configure_project')).toBe(false); expect(hasToolPermission({ plan: 'basic' }, 'configure_project')).toBe(false); }); }); describe('validateJWT', () => { test('should validate demo tokens', async () => { const result = await validateJWT('demo_basic_token_2024'); expect(result).toBeDefined(); expect(result.plan).toBe('basic'); expect(result.permissions).toContain('basic'); }); test('should validate premium demo tokens', async () => { const result = await validateJWT('demo_premium_token_2024'); expect(result).toBeDefined(); expect(result.plan).toBe('premium'); expect(result.permissions).toEqual(['basic', 'premium']); }); test('should validate enterprise demo tokens', async () => { const result = await validateJWT('demo_enterprise_token_2024'); expect(result).toBeDefined(); expect(result.plan).toBe('enterprise'); expect(result.permissions).toEqual(['basic', 'premium', 'enterprise']); }); test('should reject invalid tokens', async () => { await expect(validateJWT('invalid-token')).rejects.toThrow(); }); test('should handle empty token', async () => { await expect(validateJWT('')).rejects.toThrow('Token JWT requerido'); }); test('should handle null token', async () => { await expect(validateJWT(null)).rejects.toThrow('Token JWT requerido'); }); }); describe('authenticateToolCall', () => { test('should authenticate with valid token', async () => { const result = await authenticateToolCall('database_query', {}, { jwt: 'demo_basic_token_2024' }); expect(result.success).toBe(true); expect(result.user).toBeDefined(); expect(result.user.plan).toBe('basic'); }); test('should reject without token', async () => { const result = await authenticateToolCall('database_query', {}, {}); expect(result.success).toBe(false); expect(result.error).toBeDefined(); expect(result.code).toBe('AUTH_REQUIRED'); }); test('should reject insufficient permissions', async () => { const result = await authenticateToolCall('setup_microservices', {}, { jwt: 'demo_basic_token_2024' }); expect(result.success).toBe(false); expect(result.code).toBe('INSUFFICIENT_PERMISSIONS'); expect(result.requiredPlan).toBe('enterprise'); expect(result.currentPlan).toBe('basic'); }); test('should handle development bypass', async () => { // Enable development bypass const originalBypass = authConfig.development.bypassAuth; authConfig.development.bypassAuth = true; const result = await authenticateToolCall('any_tool', {}, {}); expect(result.success).toBe(true); expect(result.user.plan).toBe('enterprise'); // Restore original setting authConfig.development.bypassAuth = originalBypass; }); }); describe('Configuration', () => { test('should have valid plan configurations', () => { expect(authConfig.plans.basic).toBeDefined(); expect(authConfig.plans.premium).toBeDefined(); expect(authConfig.plans.enterprise).toBeDefined(); expect(authConfig.plans.basic.price).toBe(5); expect(authConfig.plans.premium.price).toBe(15); expect(authConfig.plans.enterprise.price).toBe(50); }); test('should have valid tool permissions', () => { expect(authConfig.toolPermissions.basic).toContain('configure_project'); expect(authConfig.toolPermissions.premium).toContain('setup_docker'); expect(authConfig.toolPermissions.enterprise).toContain('setup_microservices'); }); test('should have valid error messages', () => { expect(authConfig.getMessage('noToken', 'es')).toContain('Autenticación requerida'); expect(authConfig.getMessage('invalidToken', 'en')).toContain('Invalid or expired'); }); test('should determine required plan correctly', () => { expect(authConfig.getRequiredPlan('configure_project')).toBe('basic'); expect(authConfig.getRequiredPlan('setup_docker')).toBe('premium'); expect(authConfig.getRequiredPlan('setup_microservices')).toBe('enterprise'); expect(authConfig.getRequiredPlan('unknown_tool')).toBe('basic'); }); }); describe('Error Handling', () => { test('should handle invalid tokens gracefully', async () => { const result = await authenticateToolCall('configure_project', {}, { jwt: 'invalid-malformed-token' }); expect(result.success).toBe(false); expect(result.code).toBe('INVALID_TOKEN'); }); }); }); // Pruebas de integración describe('Integration Tests', () => { test('should work with demo tokens from config', async () => { const result = await authenticateToolCall('configure_project', {}, { jwt: 'demo_basic_token_2024' }); expect(result.success).toBe(true); expect(result.user.plan).toBe('basic'); expect(result.user.permissions).toContain('basic'); }); }); // Cleanup después de las pruebas afterEach(() => { jest.clearAllMocks(); // Limpiar variables de entorno delete process.env.BACKEND_MCP_JWT; delete process.env.JWT_SECRET; delete process.env.AUTH_API_URL; });