В Universal Router маршруты представляют собой объекты с
определёнными свойствами, среди которых ключевыми являются
path, action и children.
Композиция маршрутов позволяет создавать иерархическую структуру
маршрутов, упрощая управление сложными приложениями с большим
количеством путей.
const routes = [
{
path: '/users',
action: () => 'Список пользователей',
children: [
{
path: '/:id',
action: ({ params }) => `Профиль пользователя ${params.id}`
}
]
}
];
В этом примере маршрут /users/:id является дочерним для
/users. Иерархия маршрутов отражает структуру
URL и позволяет автоматически наследовать параметры и
контекст.
childrenСвойство children — это массив маршрутов, вложенных в
родительский маршрут. Оно позволяет:
const routes = [
{
path: '/dashboard',
action: () => 'Главная панель',
children: [
{
path: '/analytics',
action: () => 'Аналитика',
},
{
path: '/settings',
action: () => 'Настройки',
}
]
}
];
При обращении к /dashboard/analytics
Universal Router сначала сопоставляет
/dashboard, затем ищет соответствие среди дочерних
маршрутов.
При использовании вложенных маршрутов параметры и контекст родителя автоматически передаются в дочерние маршруты.
const routes = [
{
path: '/users/:userId',
action: ({ params }) => `Пользователь ${params.userId}`,
children: [
{
path: '/posts/:postId',
action: ({ params }) => `Пост ${params.postId} пользователя ${params.userId}`
}
]
}
];
Запрос к /users/42/posts/100 создаёт объект
params:
{
userId: '42',
postId: '100'
}
Таким образом, дочерние маршруты могут полностью использовать контекст родителя, что исключает необходимость повторного определения параметров.
Universal Router поддерживает асинхронные функции для
action. При композиции маршрутов это позволяет загружать
данные на разных уровнях иерархии.
const routes = [
{
path: '/products',
action: async () => fetch('/api/products').then(res => res.json()),
children: [
{
path: '/:id',
action: async ({ params }) => fetch(`/api/products/${params.id}`).then(res => res.json())
}
]
}
];
В этом примере сначала загружается общий список продуктов, затем данные конкретного продукта. Асинхронная композиция обеспечивает гибкую загрузку данных по мере необходимости.
parent и childrenПомимо простого вложения, маршруты можно комбинировать динамически, используя функции для генерации дочерних маршрутов:
function createProductRoutes() {
return [
{
path: '/:id',
action: ({ params }) => `Продукт ${params.id}`
},
{
path: '/:id/reviews',
action: ({ params }) => `Отзывы для продукта ${params.id}`
}
];
}
const routes = [
{
path: '/products',
action: () => 'Список продуктов',
children: createProductRoutes()
}
];
Это позволяет создавать модульные маршруты, которые можно использовать повторно в разных частях приложения.
Universal Router поддерживает промежуточные уровни
маршрутов, которые могут не иметь собственного action, а
служить только для организации структуры.
const routes = [
{
path: '/app',
children: [
{
path: '/users',
action: () => 'Пользователи'
},
{
path: '/settings',
action: () => 'Настройки'
}
]
}
];
При запросе /app/users вызывается только действие
дочернего маршрута. Родительский маршрут служит
контейнером, обеспечивая общую структуру URL.
Маршруты могут быть добавлены в иерархию динамически в зависимости от условий:
const adminRoutes = [
{
path: '/dashboard',
action: () => 'Панель администратора'
}
];
const routes = [
{
path: '/',
action: () => 'Главная',
children: isAdmin ? adminRoutes : []
}
];
Такой подход полезен для разграничения доступа и включения только необходимых маршрутов в зависимости от роли пользователя.
Композиция маршрутов позволяет назначать отдельные обработчики ошибок
на каждом уровне иерархии с помощью свойства action и
блоков try/catch в асинхронных действиях:
const routes = [
{
path: '/users',
action: async () => {
try {
return await fetchUsers();
} catch (err) {
return 'Ошибка загрузки пользователей';
}
},
children: [
{
path: '/:id',
action: async ({ params }) => {
try {
return await fetchUser(params.id);
} catch (err) {
return `Ошибка загрузки пользователя ${params.id}`;
}
}
}
]
}
];
Такой подход позволяет локализовать обработку ошибок на уровне конкретного маршрута без нарушения работы остальных частей маршрутизатора.
action.Комплексное применение этих принципов обеспечивает модульность, повторное использование и простоту поддержки маршрутов в больших JavaScript-приложениях.