Files
Charon/frontend/src/api/__tests__/security.test.ts

245 lines
8.0 KiB
TypeScript

import { describe, it, expect, vi, beforeEach } from 'vitest'
import * as security from '../security'
import client from '../client'
vi.mock('../client')
describe('security API', () => {
beforeEach(() => {
vi.clearAllMocks()
})
describe('getSecurityStatus', () => {
it('should call GET /security/status', async () => {
const mockData: security.SecurityStatus = {
cerberus: { enabled: true },
crowdsec: { mode: 'local', api_url: 'http://localhost:8080', enabled: true },
waf: { mode: 'enabled', enabled: true },
rate_limit: { mode: 'enabled', enabled: true },
acl: { enabled: true }
}
vi.mocked(client.get).mockResolvedValue({ data: mockData })
const result = await security.getSecurityStatus()
expect(client.get).toHaveBeenCalledWith('/security/status')
expect(result).toEqual(mockData)
})
})
describe('getSecurityConfig', () => {
it('should call GET /security/config', async () => {
const mockData = { config: { admin_whitelist: '10.0.0.0/8' } }
vi.mocked(client.get).mockResolvedValue({ data: mockData })
const result = await security.getSecurityConfig()
expect(client.get).toHaveBeenCalledWith('/security/config')
expect(result).toEqual(mockData)
})
})
describe('updateSecurityConfig', () => {
it('should call POST /security/config with payload', async () => {
const payload: security.SecurityConfigPayload = {
name: 'test',
enabled: true,
admin_whitelist: '10.0.0.0/8'
}
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.updateSecurityConfig(payload)
expect(client.post).toHaveBeenCalledWith('/security/config', payload)
expect(result).toEqual(mockData)
})
it('should handle all payload fields', async () => {
const payload: security.SecurityConfigPayload = {
name: 'test',
enabled: true,
admin_whitelist: '10.0.0.0/8',
crowdsec_mode: 'local',
crowdsec_api_url: 'http://localhost:8080',
waf_mode: 'enabled',
waf_rules_source: 'coreruleset',
waf_learning: true,
rate_limit_enable: true,
rate_limit_burst: 10,
rate_limit_requests: 100,
rate_limit_window_sec: 60
}
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.updateSecurityConfig(payload)
expect(client.post).toHaveBeenCalledWith('/security/config', payload)
expect(result).toEqual(mockData)
})
})
describe('generateBreakGlassToken', () => {
it('should call POST /security/breakglass/generate', async () => {
const mockData = { token: 'abc123' }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.generateBreakGlassToken()
expect(client.post).toHaveBeenCalledWith('/security/breakglass/generate')
expect(result).toEqual(mockData)
})
})
describe('enableCerberus', () => {
it('should call POST /security/enable with payload', async () => {
const payload = { mode: 'full' }
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.enableCerberus(payload)
expect(client.post).toHaveBeenCalledWith('/security/enable', payload)
expect(result).toEqual(mockData)
})
it('should call POST /security/enable with empty object when no payload', async () => {
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.enableCerberus()
expect(client.post).toHaveBeenCalledWith('/security/enable', {})
expect(result).toEqual(mockData)
})
})
describe('disableCerberus', () => {
it('should call POST /security/disable with payload', async () => {
const payload = { reason: 'maintenance' }
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.disableCerberus(payload)
expect(client.post).toHaveBeenCalledWith('/security/disable', payload)
expect(result).toEqual(mockData)
})
it('should call POST /security/disable with empty object when no payload', async () => {
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.disableCerberus()
expect(client.post).toHaveBeenCalledWith('/security/disable', {})
expect(result).toEqual(mockData)
})
})
describe('getDecisions', () => {
it('should call GET /security/decisions with default limit', async () => {
const mockData = { decisions: [] }
vi.mocked(client.get).mockResolvedValue({ data: mockData })
const result = await security.getDecisions()
expect(client.get).toHaveBeenCalledWith('/security/decisions?limit=50')
expect(result).toEqual(mockData)
})
it('should call GET /security/decisions with custom limit', async () => {
const mockData = { decisions: [] }
vi.mocked(client.get).mockResolvedValue({ data: mockData })
const result = await security.getDecisions(100)
expect(client.get).toHaveBeenCalledWith('/security/decisions?limit=100')
expect(result).toEqual(mockData)
})
})
describe('createDecision', () => {
it('should call POST /security/decisions with payload', async () => {
const payload = { value: '1.2.3.4', duration: '4h', type: 'ban' }
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.createDecision(payload)
expect(client.post).toHaveBeenCalledWith('/security/decisions', payload)
expect(result).toEqual(mockData)
})
})
describe('getRuleSets', () => {
it('should call GET /security/rulesets', async () => {
const mockData: security.RuleSetsResponse = {
rulesets: [
{
id: 1,
uuid: 'abc-123',
name: 'OWASP CRS',
source_url: 'https://example.com/rules',
mode: 'blocking',
last_updated: '2025-12-04T00:00:00Z',
content: 'rule content'
}
]
}
vi.mocked(client.get).mockResolvedValue({ data: mockData })
const result = await security.getRuleSets()
expect(client.get).toHaveBeenCalledWith('/security/rulesets')
expect(result).toEqual(mockData)
})
})
describe('upsertRuleSet', () => {
it('should call POST /security/rulesets with create payload', async () => {
const payload: security.UpsertRuleSetPayload = {
name: 'Custom Rules',
content: 'rule content',
mode: 'blocking'
}
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.upsertRuleSet(payload)
expect(client.post).toHaveBeenCalledWith('/security/rulesets', payload)
expect(result).toEqual(mockData)
})
it('should call POST /security/rulesets with update payload', async () => {
const payload: security.UpsertRuleSetPayload = {
id: 1,
name: 'Updated Rules',
source_url: 'https://example.com/rules',
mode: 'detection'
}
const mockData = { success: true }
vi.mocked(client.post).mockResolvedValue({ data: mockData })
const result = await security.upsertRuleSet(payload)
expect(client.post).toHaveBeenCalledWith('/security/rulesets', payload)
expect(result).toEqual(mockData)
})
})
describe('deleteRuleSet', () => {
it('should call DELETE /security/rulesets/:id', async () => {
const mockData = { success: true }
vi.mocked(client.delete).mockResolvedValue({ data: mockData })
const result = await security.deleteRuleSet(1)
expect(client.delete).toHaveBeenCalledWith('/security/rulesets/1')
expect(result).toEqual(mockData)
})
})
})