Модульное тестирование маршрутов в библиотеке Universal Router
позволяет проверять корректность работы маршрутизации без необходимости
запускать полный веб-сервер или интерфейс пользователя. Это обеспечивает
изоляцию тестов и позволяет выявлять ошибки на раннем этапе разработки.
Тестирование базируется на проверке результатов работы метода
resolve() и правильности обработки параметров, контекста и
переходов между маршрутами.
Для тестирования маршрутов рекомендуется использовать фреймворки, поддерживающие асинхронные тесты, такие как Jest или Mocha. Важным элементом является создание контекста маршрутизатора, который может включать в себя:
user, roles);state);fetch,
redirect).Пример создания базового маршрутизатора для тестов:
import UniversalRouter from 'universal-router';
const routes = [
{ path: '/', action: () => 'Home' },
{ path: '/about', action: () => 'About' },
{ path: '/users/:id', action: ({ params }) => `User ${params.id}` }
];
const router = new UniversalRouter(routes);
Контекст можно передавать в метод resolve() для имитации
реального окружения приложения:
const context = { user: { name: 'Alice' }, state: {} };
const result = await router.resolve({ pathname: '/users/42', context });
Для простых маршрутов важно проверить, что путь правильно
сопоставляется с ожидаемой функцией action и возвращает
корректное значение.
test('должен возвращать Home для корневого пути', async () => {
const result = await router.resolve({ pathname: '/' });
expect(result).toBe('Home');
});
test('должен возвращать About для /about', async () => {
const result = await router.resolve({ pathname: '/about' });
expect(result).toBe('About');
});
Маршруты с параметрами требуют проверки правильности разбора
параметров params:
test('должен возвращать корректного пользователя', async () => {
const result = await router.resolve({ pathname: '/users/99' });
expect(result).toBe('User 99');
});
Важный момент — проверка не только значения параметра, но и его типизации, если приложение использует строгую типизацию или валидацию.
Маршруты часто выполняют асинхронные операции, такие как загрузка
данных с сервера. Для тестирования необходимо использовать
async/await и мокировать внешние вызовы:
const routes = [
{
path: '/data/:id',
async action({ params, context }) {
const data = await context.fetch(`/api/data/${params.id}`);
return data;
}
}
];
test('должен возвращать данные пользователя', async () => {
const mockFetch = jest.fn().mockResolvedValue({ name: 'Bob' });
const result = await new UniversalRouter(routes).resolve({ pathname: '/data/5', context: { fetch: mockFetch } });
expect(result).toEqual({ name: 'Bob' });
});
Universal Router поддерживает вложенные маршруты через массив
children. Тестирование таких маршрутов требует проверки
корректного разрешения вложенных путей:
const routes = [
{
path: '/dashboard',
children: [
{ path: '', action: () => 'Dashboard Home' },
{ path: 'stats', action: () => 'Dashboard Stats' }
]
}
];
test('должен возвращать Dashboard Home', async () => {
const result = await new UniversalRouter(routes).resolve({ pathname: '/dashboard' });
expect(result).toBe('Dashboard Home');
});
test('должен возвращать Dashboard Stats', async () => {
const result = await new UniversalRouter(routes).resolve({ pathname: '/dashboard/stats' });
expect(result).toBe('Dashboard Stats');
});
Для маршрутов, использующих редиректы или выбрасывающих ошибки, важно
тестировать корректную обработку исключений и возврат значений
redirect:
const routes = [
{ path: '/old', action: () => ({ redirect: '/new' }) },
{ path: '/new', action: () => 'New Page' }
];
test('должен редиректить с /old на /new', async () => {
const result = await new UniversalRouter(routes).resolve({ pathname: '/old' });
expect(result.redirect).toBe('/new');
});
const errorRoute = [
{ path: '/secret', action: () => { throw new Error('Forbidden'); } }
];
test('должен выбрасывать ошибку для /secret', async () => {
await expect(new UniversalRouter(errorRoute).resolve({ pathname: '/secret' }))
.rejects.toThrow('Forbidden');
});
await и
mockResolvedValue/mockRejectedValue.router.resolve({ pathname, context }) вместо ручной
имитации переходов.Модульное тестирование маршрутов повышает надежность приложения и обеспечивает уверенность, что переходы между страницами работают корректно в любых условиях.