fix: hlavičky s identitou přijímat jen z důvěryhodných adres
CI / Generate TypeScript types (push) Successful in 11s
CI / Server unit tests (push) Successful in 31s
CI / Build server (push) Successful in 27s
CI / Build client (push) Successful in 47s
CI / Playwright E2E tests (push) Successful in 1m39s
CI / Build and push Docker image (push) Successful in 45s
CI / Notify (push) Successful in 2s
CI / Generate TypeScript types (push) Successful in 11s
CI / Server unit tests (push) Successful in 31s
CI / Build server (push) Successful in 27s
CI / Build client (push) Successful in 47s
CI / Playwright E2E tests (push) Successful in 1m39s
CI / Build and push Docker image (push) Successful in 45s
CI / Notify (push) Successful in 2s
This commit is contained in:
@@ -0,0 +1,64 @@
|
||||
import express from 'express';
|
||||
import request from 'supertest';
|
||||
import { getTrustedRemoteUser, isTrustedPeer, parseTrustedIps } from '../trustedHeaders';
|
||||
|
||||
describe('parseTrustedIps / isTrustedPeer', () => {
|
||||
const trusted = parseTrustedIps('10.42.0.0/16, 127.0.0.1, ::1, fd00::/8');
|
||||
|
||||
test('rozsah CIDR i jednotlivé adresy (IPv4 i IPv6)', () => {
|
||||
expect(isTrustedPeer('10.42.0.84', trusted)).toBe(true);
|
||||
expect(isTrustedPeer('10.43.0.1', trusted)).toBe(false);
|
||||
expect(isTrustedPeer('127.0.0.1', trusted)).toBe(true);
|
||||
expect(isTrustedPeer('::1', trusted)).toBe(true);
|
||||
expect(isTrustedPeer('fd12:3456::1', trusted)).toBe(true);
|
||||
expect(isTrustedPeer('192.168.1.10', trusted)).toBe(false);
|
||||
});
|
||||
|
||||
test('IPv4 mapovaná do IPv6 (jak ji hlásí Node) se porovnává jako IPv4', () => {
|
||||
expect(isTrustedPeer('::ffff:10.42.0.84', trusted)).toBe(true);
|
||||
expect(isTrustedPeer('::FFFF:8.8.8.8', trusted)).toBe(false);
|
||||
});
|
||||
|
||||
test('chybějící nebo nesmyslná adresa není důvěryhodná', () => {
|
||||
expect(isTrustedPeer(undefined, trusted)).toBe(false);
|
||||
expect(isTrustedPeer('nesmysl', trusted)).toBe(false);
|
||||
});
|
||||
|
||||
test('neplatná konfigurace vyhodí chybu (server nenaběhne)', () => {
|
||||
expect(() => parseTrustedIps('10.0.0.0/33')).toThrow('neplatný rozsah');
|
||||
expect(() => parseTrustedIps('proxy.local')).toThrow('neplatná adresa');
|
||||
expect(() => parseTrustedIps('10.0.0.0/x')).toThrow('neplatný rozsah');
|
||||
});
|
||||
|
||||
test('prázdný seznam nedůvěřuje nikomu', () => {
|
||||
expect(isTrustedPeer('127.0.0.1', parseTrustedIps(''))).toBe(false);
|
||||
});
|
||||
});
|
||||
|
||||
describe('getTrustedRemoteUser', () => {
|
||||
/** Mini aplikace, která vrátí identitu z hlavičky (jako /api/whoami). */
|
||||
function buildApp(trustedList: string) {
|
||||
const trusted = parseTrustedIps(trustedList);
|
||||
const app = express();
|
||||
app.get('/whoami', (req, res) => res.send(getTrustedRemoteUser(req, 'remote-user', trusted) ?? ''));
|
||||
return app;
|
||||
}
|
||||
|
||||
test('hlavička od důvěryhodné adresy se přijme (i s diakritikou v latin1)', async () => {
|
||||
const res = await request(buildApp('127.0.0.1,::1,::ffff:127.0.0.1'))
|
||||
.get('/whoami')
|
||||
.set('remote-user', Buffer.from('Novák', 'utf8').toString('latin1'));
|
||||
expect(res.text).toBe('Novák');
|
||||
});
|
||||
|
||||
test('hlavička od nedůvěryhodné adresy se ignoruje — ani X-Forwarded-For nepomůže', async () => {
|
||||
const warn = jest.spyOn(console, 'warn').mockImplementation(() => { });
|
||||
const res = await request(buildApp('10.42.0.0/16'))
|
||||
.get('/whoami')
|
||||
.set('remote-user', 'utocnik')
|
||||
.set('X-Forwarded-For', '10.42.0.84');
|
||||
expect(res.text).toBe('');
|
||||
expect(warn).toHaveBeenCalledWith(expect.stringContaining('nedůvěryhodné adresy'));
|
||||
warn.mockRestore();
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user