import { escapeHtml, getErrorStatus, renderErrorPage, } from '../ssrErrorHandler'; describe('ssrErrorHandler', () => { describe('getErrorStatus', () => { it('should return 500 for null', () => { expect(getErrorStatus(null)).toBe(500); }); it('should return 500 for undefined', () => { expect(getErrorStatus(undefined)).toBe(500); }); it('should return 500 for plain Error without status', () => { expect(getErrorStatus(new Error('test'))).toBe(500); }); it('should return 500 for string error', () => { expect(getErrorStatus('something went wrong')).toBe(500); }); it('should return 500 for number error', () => { expect(getErrorStatus(42)).toBe(500); }); it('should extract numeric status from error object', () => { expect(getErrorStatus({ status: 404, message: 'Not Found' })).toBe(404); expect(getErrorStatus({ status: 429, message: 'Rate Limited' })).toBe( 429, ); expect( getErrorStatus({ status: 503, message: 'Service Unavailable' }), ).toBe(503); }); it('should extract string status from error object', () => { expect(getErrorStatus({ status: '404', message: 'Not Found' })).toBe(404); expect(getErrorStatus({ status: '500', message: 'Error' })).toBe(500); }); it('should return 500 for invalid numeric status codes', () => { expect(getErrorStatus({ status: 99 })).toBe(500); // too low expect(getErrorStatus({ status: 600 })).toBe(500); // too high expect(getErrorStatus({ status: -1 })).toBe(500); // negative expect(getErrorStatus({ status: 0 })).toBe(500); // zero }); it('should return 500 for invalid string status codes', () => { expect(getErrorStatus({ status: '99' })).toBe(500); // too low expect(getErrorStatus({ status: '600' })).toBe(500); // too high expect(getErrorStatus({ status: 'abc' })).toBe(500); // not a number expect(getErrorStatus({ status: '' })).toBe(500); // empty string }); it('should return 500 for non-number/string status values', () => { expect(getErrorStatus({ status: null })).toBe(500); expect(getErrorStatus({ status: undefined })).toBe(500); expect(getErrorStatus({ status: {} })).toBe(500); expect(getErrorStatus({ status: [] })).toBe(500); expect(getErrorStatus({ status: true })).toBe(500); }); it('should work with Error objects that have status property', () => { const error = new Error('Rate Limited') as Error & { status: number }; error.status = 429; expect(getErrorStatus(error)).toBe(429); }); it('should handle boundary values', () => { expect(getErrorStatus({ status: 100 })).toBe(100); // min valid expect(getErrorStatus({ status: 599 })).toBe(599); // max valid }); }); describe('escapeHtml', () => { it('should escape ampersands', () => { expect(escapeHtml('foo & bar')).toBe('foo & bar'); }); it('should escape less than', () => { expect(escapeHtml('')).toBe( '<script>alert("xss")</script>', ); }); it('should return empty string for empty input', () => { expect(escapeHtml('')).toBe(''); }); it('should not modify strings without special characters', () => { expect(escapeHtml('hello world')).toBe('hello world'); }); }); describe('renderErrorPage', () => { it('should render basic error page with status code', () => { const html = renderErrorPage(new Error('Test error'), '/test', 500); expect(html).toContain(''); expect(html).toContain('500 - Server Error'); expect(html).toContain('

500 - Server Error

'); expect(html).toContain('Test error'); expect(html).toContain('/test'); }); it('should render different status codes', () => { const html404 = renderErrorPage({ message: 'Not Found' }, '/page', 404); const html429 = renderErrorPage({ message: 'Rate Limited' }, '/api', 429); expect(html404).toContain('404 - Server Error'); expect(html404).toContain('

404 - Server Error

'); expect(html429).toContain('429 - Server Error'); expect(html429).toContain('

429 - Server Error

'); }); it('should escape URL in output', () => { const html = renderErrorPage( new Error('error'), '/test?foo='), '/test', 500, ); expect(html).toContain('<script>'); expect(html).not.toContain('', }); expect(html).toContain('<script>'); expect(html).not.toContain('', }); expect(html).toContain('<script>'); expect(html).not.toContain('