import { describe, it } from 'node:test'
import assert from 'node:assert/strict'
import { generateConfig } from '../lib/config-generator.js'
describe('generateConfig', () => {
it('generates single-backend config (backwards compat)', () => {
const registry = {
nodes: [{ petname: 'tabertron', ip: '10.22.0.1' }],
services: [
{ node: 'tabertron', name: 'viz', port: 7890, rootPath: '/viz' }
]
}
const output = generateConfig(registry)
assert.ok(output.includes('ProxyPass http://10.22.0.1:7890'), 'should have direct ProxyPass')
assert.ok(output.includes('ProxyPassReverse http://10.22.0.1:7890'), 'should have ProxyPassReverse')
assert.ok(output.includes('<Location /viz>'), 'should have Location block')
assert.ok(output.includes('ws://10.22.0.1:7890'), 'should have WebSocket rewrite')
assert.ok(!output.includes('balancer://'), 'should NOT have balancer directives')
})
it('generates balancer config for multi-backend', () => {
const registry = {
nodes: [
{ petname: 'tabertron', ip: '10.22.0.1' },
{ petname: 'stortron', ip: '10.22.0.2' }
],
services: [
{
name: 'pear-git',
rootPath: '/git',
backends: [
{ node: 'tabertron', port: 5005, mode: 'active' },
{ node: 'stortron', port: 5005, mode: 'standby' }
]
}
]
}
const output = generateConfig(registry)
assert.ok(output.includes('<Proxy balancer://pear-git>'), 'should have Proxy balancer block')
assert.ok(output.includes('BalancerMember http://10.22.0.1:5005'), 'should have active member')
assert.ok(output.includes('BalancerMember http://10.22.0.2:5005 status=+H'), 'standby should have status=+H')
assert.ok(output.includes('ProxySet timeout=300'), 'should have ProxySet with generous default timeout')
assert.ok(output.includes('<Location /git>'), 'should have Location block')
assert.ok(output.includes('ProxyPass balancer://pear-git'), 'Location should proxy to balancer')
assert.ok(output.includes('ProxyPassReverse balancer://pear-git'), 'should have ProxyPassReverse for balancer')
assert.ok(output.includes('ws://10.22.0.1:5005'), 'WebSocket should point to active backend')
})
it('mixes single and multi-backend', () => {
const registry = {
nodes: [
{ petname: 'tabertron', ip: '10.22.0.1' },
{ petname: 'stortron', ip: '10.22.0.2' }
],
services: [
{ node: 'tabertron', name: 'viz', port: 7890, rootPath: '/viz' },
{
name: 'pear-git',
rootPath: '/git',
backends: [
{ node: 'tabertron', port: 5005, mode: 'active' },
{ node: 'stortron', port: 5005, mode: 'standby' }
]
}
]
}
const output = generateConfig(registry)
// Multi-backend present
assert.ok(output.includes('<Proxy balancer://pear-git>'), 'should have balancer block')
assert.ok(output.includes('BalancerMember http://10.22.0.1:5005'), 'should have active member')
// Single-backend present
assert.ok(output.includes('ProxyPass http://10.22.0.1:7890'), 'should have direct ProxyPass for single')
assert.ok(output.includes('<Location /viz>'), 'should have Location for single backend')
})
it('active-active mode has no status=+H', () => {
const registry = {
nodes: [
{ petname: 'tabertron', ip: '10.22.0.1' },
{ petname: 'stortron', ip: '10.22.0.2' }
],
services: [
{
name: 'api',
rootPath: '/api',
backends: [
{ node: 'tabertron', port: 8080, mode: 'active' },
{ node: 'stortron', port: 8080, mode: 'active' }
]
}
]
}
const output = generateConfig(registry)
assert.ok(output.includes('<Proxy balancer://api>'), 'should have balancer block')
assert.ok(output.includes('BalancerMember http://10.22.0.1:8080'), 'should have first member')
assert.ok(output.includes('BalancerMember http://10.22.0.2:8080'), 'should have second member')
assert.ok(!output.includes('status=+H'), 'should NOT have status=+H for active-active')
})
})