Маршрутизация
Маршрутизация в PreffX управляется корневым сигналом url. Навигация обновляет его, а отрисованное дерево реагирует автоматически. Библиотека не зависит от источника навигации: она работает с браузерным Navigation API, когда он доступен, и переключается на автономную навигацию на основе сигналов в SSR- или headless-средах.
Чтение URL
Утилита url — это доступный только для чтения сигнал URL:
import type { PC } from 'preffx';
export const Path: PC = (_props, { url }) => {
return <p>You are at: {url.value.pathname}</p>;
};Запуск навигации
Используйте navigate, чтобы перейти на другой URL:
import type { PC } from 'preffx';
export const Go: PC = (_props, { navigate }) => {
return <button onClick={() => navigate('/about')}>About</button>;
};Декларативные маршруты через routes
Утилита routes принимает карту «шаблон пути → компонент» и возвращает реактивный сигнал, содержащий отрисованное содержимое первого подходящего маршрута. Сопоставление работает по принципу «первое совпадение побеждает»: шаблоны проверяются в порядке ключей объекта.
import type { PC } from 'preffx';
export const App: PC = (_props, { routes }) => {
const content = routes({
'/': () => <div>Home</div>,
'/:lang?/user/:id': (_, { routeParams }) => (
<div>User #{routeParams.id} ({routeParams.lang || 'en'})</div>
),
'*': () => <div>Not found</div>
});
return (
<div>
<a href="/">Home</a>
<a href="/user/42">User page</a>
<a href="/ru/user/42">User page (ru)</a>
<a href="/unknown">Unknown page</a>
{content}
</div>
);
};Шаблоны маршрутов
| Шаблон | Описание | Пример совпадения |
|---|---|---|
/users | Статический сегмент | /users |
/user/:id | Обязательный параметр (:id) | /user/42 → { id: '42' } |
/:lang?/home | Необязательный параметр (?); пуст при отсутствии | /home → { lang: '' } |
/files/* | Splat — захватывает остаток (после завершающего *) | /files/a/b → { '*': 'a/b' } |
* | Catch-all — соответствует любому пути | /anything |
Примечания:
- Параметры маршрута автоматически декодируются из URI.
- Шаблон соответствует префиксу пути:
/usersтакже соответствует/users/42. Используйте catch-all или более конкретный шаблон, когда нужен точный поиск. *работает как подстановочный знак только в качестве последнего сегмента; в остальных местах он трактуется как литерал.- Подобранные параметры маршрута доступны через
routeParams. - Во вложенном макете относительные шаблоны разрешаются относительно совпавшего пути родительского маршрута.
Вложенные маршруты
Вызовите routes() в родительском компоненте; совпавший дочерний компонент отрисовывается в возвращаемый сигнал. Параметры маршрута из совпавшего шаблона предоставляются через routeParams и также доступны потомкам через контекст.
Сводка утилит
| Опция | Тип | Описание |
|---|---|---|
defaultURL | string | URL | Начальный URL (для SSR передайте URL запроса) |
url | ReadonlySignal<URL> | Текущий URL, реактивный |
navigate | (url, options?) | Переход по URL |
routes | (paths) => signal | Рендер маршрута по первому совпадению |
routeParams | Record<string, string> | Параметры текущего совпавшего маршрута |