import { expect } from '@push.rocks/tapbundle'; import { SharedSecurityManager } from '../../../ts/core/utils/shared-security-manager.js'; import type { IRouteConfig, IRouteContext } from '../../../ts/proxies/smart-proxy/models/route-types.js'; // Test security manager expect.describe('Shared Security Manager', async () => { let securityManager: SharedSecurityManager; // Set up a new security manager before each test expect.beforeEach(() => { securityManager = new SharedSecurityManager({ maxConnectionsPerIP: 5, connectionRateLimitPerMinute: 10 }); }); expect.it('should validate IPs correctly', async () => { // Should allow IPs under connection limit expect(securityManager.validateIP('192.168.1.1').allowed).to.be.true; // Track multiple connections for (let i = 0; i < 4; i++) { securityManager.trackConnectionByIP('192.168.1.1', `conn_${i}`); } // Should still allow IPs under connection limit expect(securityManager.validateIP('192.168.1.1').allowed).to.be.true; // Add one more to reach the limit securityManager.trackConnectionByIP('192.168.1.1', 'conn_4'); // Should now block IPs over connection limit expect(securityManager.validateIP('192.168.1.1').allowed).to.be.false; // Remove a connection securityManager.removeConnectionByIP('192.168.1.1', 'conn_0'); // Should allow again after connection is removed expect(securityManager.validateIP('192.168.1.1').allowed).to.be.true; }); expect.it('should authorize IPs based on allow/block lists', async () => { // Test with allow list only expect(securityManager.isIPAuthorized('192.168.1.1', ['192.168.1.*'])).to.be.true; expect(securityManager.isIPAuthorized('192.168.2.1', ['192.168.1.*'])).to.be.false; // Test with block list expect(securityManager.isIPAuthorized('192.168.1.5', ['*'], ['192.168.1.5'])).to.be.false; expect(securityManager.isIPAuthorized('192.168.1.1', ['*'], ['192.168.1.5'])).to.be.true; // Test with both allow and block lists expect(securityManager.isIPAuthorized('192.168.1.1', ['192.168.1.*'], ['192.168.1.5'])).to.be.true; expect(securityManager.isIPAuthorized('192.168.1.5', ['192.168.1.*'], ['192.168.1.5'])).to.be.false; }); expect.it('should validate route access', async () => { // Create test route with IP restrictions const route: IRouteConfig = { match: { ports: 443 }, action: { type: 'forward', target: { host: 'localhost', port: 8080 } }, security: { ipAllowList: ['192.168.1.*'], ipBlockList: ['192.168.1.5'] } }; // Create test contexts const allowedContext: IRouteContext = { port: 443, clientIp: '192.168.1.1', serverIp: 'localhost', isTls: true, timestamp: Date.now(), connectionId: 'test_conn_1' }; const blockedContext: IRouteContext = { port: 443, clientIp: '192.168.1.5', serverIp: 'localhost', isTls: true, timestamp: Date.now(), connectionId: 'test_conn_2' }; const outsideContext: IRouteContext = { port: 443, clientIp: '192.168.2.1', serverIp: 'localhost', isTls: true, timestamp: Date.now(), connectionId: 'test_conn_3' }; // Test route access expect(securityManager.isAllowed(route, allowedContext)).to.be.true; expect(securityManager.isAllowed(route, blockedContext)).to.be.false; expect(securityManager.isAllowed(route, outsideContext)).to.be.false; }); expect.it('should validate basic auth', async () => { // Create test route with basic auth const route: IRouteConfig = { match: { ports: 443 }, action: { type: 'forward', target: { host: 'localhost', port: 8080 } }, security: { basicAuth: { enabled: true, users: [ { username: 'user1', password: 'pass1' }, { username: 'user2', password: 'pass2' } ], realm: 'Test Realm' } } }; // Test valid credentials const validAuth = 'Basic ' + Buffer.from('user1:pass1').toString('base64'); expect(securityManager.validateBasicAuth(route, validAuth)).to.be.true; // Test invalid credentials const invalidAuth = 'Basic ' + Buffer.from('user1:wrongpass').toString('base64'); expect(securityManager.validateBasicAuth(route, invalidAuth)).to.be.false; // Test missing auth header expect(securityManager.validateBasicAuth(route)).to.be.false; // Test malformed auth header expect(securityManager.validateBasicAuth(route, 'malformed')).to.be.false; }); // Clean up resources after tests expect.afterEach(() => { securityManager.clearIPTracking(); }); });