747 lines
20 KiB
TypeScript
747 lines
20 KiB
TypeScript
/**
|
|
* Route configuration for the bakery management application
|
|
*/
|
|
|
|
import { ROLE_COMBINATIONS } from '../types/roles';
|
|
|
|
export interface RouteConfig {
|
|
path: string;
|
|
name: string;
|
|
component: string;
|
|
title: string;
|
|
description?: string;
|
|
icon?: string;
|
|
requiresAuth: boolean;
|
|
requiredRoles?: readonly string[];
|
|
requiredPermissions?: readonly string[];
|
|
requiredSubscriptionFeature?: string;
|
|
requiredAnalyticsLevel?: 'basic' | 'advanced' | 'predictive';
|
|
showInNavigation?: boolean;
|
|
showInBreadcrumbs?: boolean;
|
|
children?: RouteConfig[];
|
|
meta?: {
|
|
layout?: 'default' | 'auth' | 'minimal';
|
|
headerTitle?: string;
|
|
breadcrumbTitle?: string;
|
|
hideHeader?: boolean;
|
|
hideSidebar?: boolean;
|
|
fullScreen?: boolean;
|
|
scrollToTop?: boolean;
|
|
preload?: boolean;
|
|
cache?: boolean;
|
|
};
|
|
}
|
|
|
|
// Route paths as constants
|
|
export const ROUTES = {
|
|
// Public routes
|
|
HOME: '/',
|
|
FEATURES: '/features',
|
|
LOGIN: '/login',
|
|
REGISTER: '/register',
|
|
FORGOT_PASSWORD: '/forgot-password',
|
|
RESET_PASSWORD: '/reset-password',
|
|
VERIFY_EMAIL: '/verify-email',
|
|
|
|
// Dashboard
|
|
DASHBOARD: '/app/dashboard',
|
|
|
|
// Inventory Management
|
|
INVENTORY: '/app/database/inventory',
|
|
INVENTORY_INGREDIENTS: '/inventory/ingredients',
|
|
INVENTORY_STOCK: '/inventory/stock',
|
|
INVENTORY_MOVEMENTS: '/inventory/movements',
|
|
INVENTORY_ALERTS: '/inventory/alerts',
|
|
INVENTORY_QUALITY: '/inventory/quality',
|
|
INVENTORY_REPORTS: '/inventory/reports',
|
|
|
|
// Production Management
|
|
PRODUCTION: '/app/operations/production',
|
|
PRODUCTION_BATCHES: '/production/batches',
|
|
PRODUCTION_RECIPES: '/production/recipes',
|
|
PRODUCTION_SCHEDULE: '/production/schedule',
|
|
PRODUCTION_QUALITY: '/production/quality',
|
|
PRODUCTION_REPORTS: '/production/reports',
|
|
PRODUCTION_ANALYTICS: '/app/analytics/production',
|
|
|
|
// Sales & Analytics
|
|
SALES: '/sales',
|
|
SALES_DATA: '/sales/data',
|
|
SALES_ANALYTICS: '/sales/analytics',
|
|
SALES_REPORTS: '/sales/reports',
|
|
SALES_FORECASTING: '/sales/forecasting',
|
|
|
|
// Forecasting & ML
|
|
FORECASTING: '/forecasting',
|
|
FORECASTING_MODELS: '/forecasting/models',
|
|
FORECASTING_PREDICTIONS: '/forecasting/predictions',
|
|
FORECASTING_TRAINING: '/forecasting/training',
|
|
FORECASTING_ANALYTICS: '/forecasting/analytics',
|
|
|
|
// Orders Management
|
|
ORDERS: '/app/database/orders',
|
|
ORDERS_LIST: '/orders/list',
|
|
ORDERS_QUEUE: '/orders/queue',
|
|
ORDERS_HISTORY: '/orders/history',
|
|
ORDERS_CUSTOMERS: '/orders/customers',
|
|
|
|
// Procurement
|
|
PROCUREMENT: '/app/operations/procurement',
|
|
PROCUREMENT_ORDERS: '/procurement/orders',
|
|
PROCUREMENT_SUPPLIERS: '/procurement/suppliers',
|
|
PROCUREMENT_DELIVERIES: '/procurement/deliveries',
|
|
PROCUREMENT_ANALYTICS: '/app/analytics/procurement',
|
|
|
|
// Distribution
|
|
DISTRIBUTION: '/app/operations/distribution',
|
|
|
|
// Recipes
|
|
RECIPES: '/app/database/recipes',
|
|
|
|
// Suppliers
|
|
SUPPLIERS: '/app/database/suppliers',
|
|
|
|
// Sustainability
|
|
SUSTAINABILITY: '/app/database/sustainability',
|
|
|
|
// Point of Sale
|
|
POS: '/app/operations/pos',
|
|
POS_INTEGRATION: '/pos/integration',
|
|
POS_TRANSACTIONS: '/pos/transactions',
|
|
POS_WEBHOOKS: '/pos/webhooks',
|
|
POS_SETTINGS: '/pos/settings',
|
|
|
|
// Analytics
|
|
ANALYTICS_EVENTS: '/app/analytics/events',
|
|
|
|
// Training & ML
|
|
TRAINING: '/training',
|
|
TRAINING_MODELS: '/training/models',
|
|
TRAINING_JOBS: '/training/jobs',
|
|
TRAINING_EVALUATION: '/training/evaluation',
|
|
TRAINING_DATASETS: '/training/datasets',
|
|
|
|
// Notifications
|
|
NOTIFICATIONS: '/notifications',
|
|
NOTIFICATIONS_LIST: '/notifications/list',
|
|
NOTIFICATIONS_TEMPLATES: '/notifications/templates',
|
|
NOTIFICATIONS_SETTINGS: '/notifications/settings',
|
|
|
|
// Settings
|
|
SETTINGS: '/settings',
|
|
SETTINGS_PROFILE: '/app/settings/profile',
|
|
SETTINGS_BAKERY: '/app/settings/bakery',
|
|
SETTINGS_SUBSCRIPTION: '/app/settings/subscription',
|
|
SETTINGS_ORGANIZATIONS: '/app/settings/organizations',
|
|
// Legacy routes (will redirect)
|
|
SETTINGS_PERSONAL_INFO_OLD: '/app/settings/personal-info',
|
|
SETTINGS_COMMUNICATION_OLD: '/app/settings/communication-preferences',
|
|
SETTINGS_PRIVACY_OLD: '/app/settings/privacy',
|
|
SETTINGS_BAKERY_INFO_OLD: '/app/database/information',
|
|
SETTINGS_BAKERY_AJUSTES_OLD: '/app/database/ajustes',
|
|
SETTINGS_TENANT: '/settings/tenant',
|
|
SETTINGS_USERS: '/settings/users',
|
|
SETTINGS_PERMISSIONS: '/settings/permissions',
|
|
SETTINGS_INTEGRATIONS: '/settings/integrations',
|
|
SETTINGS_BILLING: '/settings/billing',
|
|
SETTINGS_TEAM: '/app/database/team',
|
|
QUALITY_TEMPLATES: '/app/database/quality-templates',
|
|
|
|
// Legal & Privacy Pages
|
|
PRIVACY_POLICY: '/privacy',
|
|
TERMS_OF_SERVICE: '/terms',
|
|
COOKIE_POLICY: '/cookies',
|
|
COOKIE_PREFERENCES: '/cookie-preferences',
|
|
|
|
// Reports
|
|
REPORTS: '/reports',
|
|
REPORTS_PRODUCTION: '/reports/production',
|
|
REPORTS_INVENTORY: '/reports/inventory',
|
|
REPORTS_SALES: '/reports/sales',
|
|
REPORTS_FINANCIAL: '/reports/financial',
|
|
REPORTS_QUALITY: '/reports/quality',
|
|
|
|
// Help & Support
|
|
HELP: '/help',
|
|
HELP_DOCUMENTATION: '/help/docs',
|
|
HELP_TUTORIALS: '/help/tutorials',
|
|
HELP_SUPPORT: '/help/support',
|
|
HELP_FEEDBACK: '/help/feedback',
|
|
|
|
// Onboarding (Setup is now integrated into UnifiedOnboardingWizard)
|
|
ONBOARDING: '/app/onboarding',
|
|
|
|
// Error pages
|
|
NOT_FOUND: '/404',
|
|
UNAUTHORIZED: '/401',
|
|
FORBIDDEN: '/403',
|
|
SERVER_ERROR: '/500',
|
|
} as const;
|
|
|
|
// Route configurations
|
|
export const routesConfig: RouteConfig[] = [
|
|
// Public routes
|
|
{
|
|
path: ROUTES.HOME,
|
|
name: 'Home',
|
|
component: 'HomePage',
|
|
title: 'BakeWise - Gestión Inteligente',
|
|
requiresAuth: false,
|
|
showInNavigation: false,
|
|
meta: {
|
|
layout: 'minimal',
|
|
scrollToTop: true,
|
|
},
|
|
},
|
|
{
|
|
path: ROUTES.LOGIN,
|
|
name: 'Login',
|
|
component: 'LoginPage',
|
|
title: 'Iniciar Sesión',
|
|
requiresAuth: false,
|
|
showInNavigation: false,
|
|
meta: {
|
|
layout: 'auth',
|
|
hideHeader: true,
|
|
hideSidebar: true,
|
|
},
|
|
},
|
|
{
|
|
path: ROUTES.REGISTER,
|
|
name: 'Register',
|
|
component: 'RegisterPage',
|
|
title: 'Crear Cuenta',
|
|
requiresAuth: false,
|
|
showInNavigation: false,
|
|
meta: {
|
|
layout: 'auth',
|
|
hideHeader: true,
|
|
hideSidebar: true,
|
|
},
|
|
},
|
|
{
|
|
path: ROUTES.FEATURES,
|
|
name: 'Features',
|
|
component: 'FeaturesPage',
|
|
title: 'Funcionalidades - BakeWise',
|
|
requiresAuth: false,
|
|
showInNavigation: false,
|
|
meta: {
|
|
layout: 'minimal',
|
|
scrollToTop: true,
|
|
},
|
|
},
|
|
|
|
// Dashboard
|
|
{
|
|
path: ROUTES.DASHBOARD,
|
|
name: 'Dashboard',
|
|
component: 'DashboardPage',
|
|
title: 'Panel de Control',
|
|
icon: 'dashboard',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
meta: {
|
|
headerTitle: 'Panel de Control',
|
|
preload: true,
|
|
cache: true,
|
|
},
|
|
},
|
|
|
|
// Operations Section - Business Operations Only
|
|
{
|
|
path: '/app/operations',
|
|
name: 'Operations',
|
|
component: 'OperationsPage',
|
|
title: 'Operaciones',
|
|
icon: 'production',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
children: [
|
|
{
|
|
path: '/app/operations/procurement',
|
|
name: 'Procurement',
|
|
component: 'ProcurementPage',
|
|
title: 'Compras',
|
|
icon: 'procurement',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/operations/production',
|
|
name: 'Production',
|
|
component: 'ProductionPage',
|
|
title: 'Producción',
|
|
icon: 'production',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/operations/pos',
|
|
name: 'POS',
|
|
component: 'POSPage',
|
|
title: 'Punto de Venta',
|
|
icon: 'pos',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/operations/distribution',
|
|
name: 'Distribution',
|
|
component: 'DistributionPage',
|
|
title: 'Distribución',
|
|
icon: 'truck',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
requiredSubscriptionFeature: 'distribution',
|
|
},
|
|
],
|
|
},
|
|
|
|
// Analytics Section - Subscription protected
|
|
{
|
|
path: '/app/analytics',
|
|
name: 'Analytics',
|
|
component: 'AnalyticsPage',
|
|
title: 'Análisis',
|
|
icon: 'analytics',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'basic',
|
|
showInNavigation: true,
|
|
children: [
|
|
{
|
|
path: '/app/analytics/production',
|
|
name: 'ProductionAnalytics',
|
|
component: 'ProductionAnalyticsPage',
|
|
title: 'Dashboard de Producción',
|
|
icon: 'production',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'advanced',
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/analytics/procurement',
|
|
name: 'ProcurementAnalytics',
|
|
component: 'ProcurementAnalyticsPage',
|
|
title: 'Dashboard de Compras',
|
|
icon: 'procurement',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'advanced',
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/analytics/forecasting',
|
|
name: 'Forecasting',
|
|
component: 'ForecastingPage',
|
|
title: 'Predicciones',
|
|
icon: 'forecasting',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'advanced',
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/analytics/sales',
|
|
name: 'SalesAnalytics',
|
|
component: 'SalesAnalyticsPage',
|
|
title: 'Dashboard de Ventas',
|
|
icon: 'sales',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'advanced',
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/analytics/performance',
|
|
name: 'PerformanceAnalytics',
|
|
component: 'PerformanceAnalyticsPage',
|
|
title: 'KPIs Generales',
|
|
icon: 'performance',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'advanced',
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/analytics/scenario-simulation',
|
|
name: 'ScenarioSimulation',
|
|
component: 'ScenarioSimulationPage',
|
|
title: 'Análisis What-If',
|
|
icon: 'simulation',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'advanced',
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/analytics/ai-insights',
|
|
name: 'AIInsights',
|
|
component: 'AIInsightsPage',
|
|
title: 'Recomendaciones',
|
|
icon: 'insights',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
requiredAnalyticsLevel: 'advanced', // Available for Professional and Enterprise tiers
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/analytics/events',
|
|
name: 'EventRegistry',
|
|
component: 'EventRegistryPage',
|
|
title: 'Eventos del Sistema',
|
|
icon: 'events',
|
|
requiresAuth: true,
|
|
requiredRoles: ['admin', 'owner'],
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
|
|
],
|
|
},
|
|
|
|
// Catalog Section - Current Bakery Status
|
|
{
|
|
path: '/app/database',
|
|
name: 'Database',
|
|
component: 'DatabasePage',
|
|
title: 'Mi Panadería',
|
|
icon: 'database',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
children: [
|
|
{
|
|
path: '/app/settings/bakery',
|
|
name: 'BakerySettings',
|
|
component: 'BakerySettingsPage',
|
|
title: 'Ajustes',
|
|
icon: 'settings',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.ADMIN_ACCESS,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/suppliers',
|
|
name: 'Suppliers',
|
|
component: 'SuppliersPage',
|
|
title: 'Proveedores',
|
|
icon: 'procurement',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/inventory',
|
|
name: 'Inventory',
|
|
component: 'InventoryPage',
|
|
title: 'Inventario',
|
|
icon: 'inventory',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/recipes',
|
|
name: 'Recipes',
|
|
component: 'RecipesPage',
|
|
title: 'Recetas',
|
|
icon: 'chef-hat',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/orders',
|
|
name: 'Orders',
|
|
component: 'OrdersPage',
|
|
title: 'Pedidos',
|
|
icon: 'orders',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/maquinaria',
|
|
name: 'Maquinaria',
|
|
component: 'MaquinariaPage',
|
|
title: 'Maquinaria',
|
|
icon: 'cog',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/quality-templates',
|
|
name: 'QualityTemplates',
|
|
component: 'QualityTemplatesPage',
|
|
title: 'Plantillas de Calidad',
|
|
icon: 'clipboard-check',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.MANAGEMENT_ACCESS,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/team',
|
|
name: 'Team',
|
|
component: 'TeamPage',
|
|
title: 'Trabajadores',
|
|
icon: 'user',
|
|
requiresAuth: true,
|
|
requiredRoles: ROLE_COMBINATIONS.ADMIN_ACCESS,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/models',
|
|
name: 'ModelsConfig',
|
|
component: 'ModelsConfigPage',
|
|
title: 'Modelos IA',
|
|
icon: 'brain-circuit',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/database/sustainability',
|
|
name: 'Sustainability',
|
|
component: 'SustainabilityPage',
|
|
title: 'Sostenibilidad',
|
|
icon: 'leaf',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
}
|
|
],
|
|
},
|
|
|
|
|
|
// Settings Section
|
|
{
|
|
path: '/app/settings',
|
|
name: 'Settings',
|
|
component: 'SettingsPage',
|
|
title: 'Mi Perfil',
|
|
icon: 'user',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
children: [
|
|
{
|
|
path: '/app/settings/profile',
|
|
name: 'Profile',
|
|
component: 'NewProfileSettingsPage',
|
|
title: 'Ajustes',
|
|
icon: 'user',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/settings/subscription',
|
|
name: 'Subscription',
|
|
component: 'SubscriptionPage',
|
|
title: 'Suscripción',
|
|
icon: 'credit-card',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
{
|
|
path: '/app/settings/organizations',
|
|
name: 'Organizations',
|
|
component: 'OrganizationsPage',
|
|
title: 'Establecimientos',
|
|
icon: 'database',
|
|
requiresAuth: true,
|
|
showInNavigation: true,
|
|
showInBreadcrumbs: true,
|
|
},
|
|
],
|
|
},
|
|
|
|
// Onboarding Section - Complete 9-step flow
|
|
{
|
|
path: '/app/onboarding',
|
|
name: 'Onboarding',
|
|
component: 'OnboardingPage',
|
|
title: 'Configuración Inicial',
|
|
description: 'Configuración completa en 9 pasos con IA',
|
|
icon: 'settings',
|
|
requiresAuth: true,
|
|
showInNavigation: false,
|
|
meta: {
|
|
hideHeader: true,
|
|
hideSidebar: true,
|
|
fullScreen: true,
|
|
},
|
|
},
|
|
|
|
// Setup is now integrated into UnifiedOnboardingWizard - route removed
|
|
|
|
|
|
// Error pages
|
|
{
|
|
path: ROUTES.NOT_FOUND,
|
|
name: 'NotFound',
|
|
component: 'NotFoundPage',
|
|
title: 'Página no encontrada',
|
|
requiresAuth: false,
|
|
showInNavigation: false,
|
|
meta: {
|
|
layout: 'minimal',
|
|
},
|
|
},
|
|
{
|
|
path: ROUTES.UNAUTHORIZED,
|
|
name: 'Unauthorized',
|
|
component: 'UnauthorizedPage',
|
|
title: 'No autorizado',
|
|
requiresAuth: false,
|
|
showInNavigation: false,
|
|
meta: {
|
|
layout: 'minimal',
|
|
},
|
|
},
|
|
{
|
|
path: ROUTES.FORBIDDEN,
|
|
name: 'Forbidden',
|
|
component: 'ForbiddenPage',
|
|
title: 'Acceso prohibido',
|
|
requiresAuth: false,
|
|
showInNavigation: false,
|
|
meta: {
|
|
layout: 'minimal',
|
|
},
|
|
},
|
|
];
|
|
|
|
// Helper functions
|
|
export const getRouteByPath = (path: string): RouteConfig | undefined => {
|
|
const findRoute = (routes: RouteConfig[], targetPath: string): RouteConfig | undefined => {
|
|
for (const route of routes) {
|
|
if (route.path === targetPath) {
|
|
return route;
|
|
}
|
|
if (route.children) {
|
|
const childRoute = findRoute(route.children, targetPath);
|
|
if (childRoute) {
|
|
return childRoute;
|
|
}
|
|
}
|
|
}
|
|
return undefined;
|
|
};
|
|
|
|
return findRoute(routesConfig, path);
|
|
};
|
|
|
|
export const getRouteByName = (name: string): RouteConfig | undefined => {
|
|
const findRoute = (routes: RouteConfig[], targetName: string): RouteConfig | undefined => {
|
|
for (const route of routes) {
|
|
if (route.name === targetName) {
|
|
return route;
|
|
}
|
|
if (route.children) {
|
|
const childRoute = findRoute(route.children, targetName);
|
|
if (childRoute) {
|
|
return childRoute;
|
|
}
|
|
}
|
|
}
|
|
return undefined;
|
|
};
|
|
|
|
return findRoute(routesConfig, name);
|
|
};
|
|
|
|
export const getNavigationRoutes = (): RouteConfig[] => {
|
|
const filterNavRoutes = (routes: RouteConfig[]): RouteConfig[] => {
|
|
return routes
|
|
.filter(route => route.showInNavigation)
|
|
.map(route => ({
|
|
...route,
|
|
children: route.children ? filterNavRoutes(route.children) : undefined,
|
|
}));
|
|
};
|
|
|
|
return filterNavRoutes(routesConfig);
|
|
};
|
|
|
|
export const getBreadcrumbs = (path: string): RouteConfig[] => {
|
|
const breadcrumbs: RouteConfig[] = [];
|
|
const pathSegments = path.split('/').filter(segment => segment);
|
|
|
|
let currentPath = '';
|
|
for (const segment of pathSegments) {
|
|
currentPath += `/${segment}`;
|
|
const route = getRouteByPath(currentPath);
|
|
if (route && route.showInBreadcrumbs !== false) {
|
|
breadcrumbs.push(route);
|
|
}
|
|
}
|
|
|
|
return breadcrumbs;
|
|
};
|
|
|
|
export const hasPermission = (route: RouteConfig, userPermissions: string[]): boolean => {
|
|
if (!route.requiredPermissions || route.requiredPermissions.length === 0) {
|
|
return true;
|
|
}
|
|
|
|
// Check for wildcard permission
|
|
if (userPermissions.includes('*')) {
|
|
return true;
|
|
}
|
|
|
|
return route.requiredPermissions.every(permission =>
|
|
userPermissions.includes(permission)
|
|
);
|
|
};
|
|
|
|
export const hasRole = (route: RouteConfig, userRoles: string[]): boolean => {
|
|
if (!route.requiredRoles || route.requiredRoles.length === 0) {
|
|
return true;
|
|
}
|
|
|
|
return route.requiredRoles.some(role =>
|
|
userRoles.includes(role)
|
|
);
|
|
};
|
|
|
|
export const canAccessRoute = (
|
|
route: RouteConfig,
|
|
isAuthenticated: boolean,
|
|
userRoles: string[] = [],
|
|
userPermissions: string[] = []
|
|
): boolean => {
|
|
// Check authentication requirement
|
|
if (route.requiresAuth && !isAuthenticated) {
|
|
return false;
|
|
}
|
|
|
|
// Check role requirements
|
|
if (!hasRole(route, userRoles)) {
|
|
return false;
|
|
}
|
|
|
|
// Check permission requirements
|
|
if (!hasPermission(route, userPermissions)) {
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}; |