import { useAuthStore } from '@/features/auth/stores/authStore.js'; import { createRouter, createWebHistory } from 'vue-router'; const LoginView = () => import('@/features/auth/views/LoginView.vue'); const Landing = () => import('@/features/landing/views/Landing.vue'); const RegisterView = () => import('@/features/auth/views/RegisterView.vue'); const ForgotPasswordView = () => import('@/features/auth/views/ForgotPasswordView.vue'); const ResetPasswordView = () => import('@/features/auth/views/ResetPasswordView.vue'); const VerifyEmailView = () => import('@/features/auth/views/VerifyEmailView.vue'); const OverviewView = () => import('@/features/workspaces/views/OverviewView.vue'); const DashboardView = () => import('@/features/workspaces/views/DashboardView.vue'); const ChannelsView = () => import('@/features/channels/views/ChannelsView.vue'); const CampaignsView = () => import('@/features/projects/views/ProjectsView.vue'); const CampaignDetailView = () => import('@/features/projects/views/ProjectDetailView.vue'); const MediaLibraryView = () => import('@/features/content/views/MediaLibraryView.vue'); const WorkspaceCreateView = () => import('@/features/workspaces/views/WorkspaceCreateView.vue'); const SettingsLayoutView = () => import('@/features/settings/views/SettingsLayoutView.vue'); const UserSettingsView = () => import('@/features/user-profile/views/UserSettingsView.vue'); const IntegrationsSettingsView = () => import('@/features/settings/views/IntegrationsSettingsView.vue'); const WorkspaceSettingsView = () => import('@/features/workspaces/views/WorkspaceSettingsView.vue'); const ReviewQueueView = () => import('@/features/reviews/views/ReviewQueueView.vue'); const ContentItemsView = () => import('@/features/content/views/ContentItemsView.vue'); const ContentItemDetailView = () => import('@/features/content/views/ContentItemDetailView.vue'); const MyFeedbackListView = () => import('@/features/feedback/views/MyFeedbackListView.vue'); const MyFeedbackDetailView = () => import('@/features/feedback/views/MyFeedbackDetailView.vue'); const DeveloperFeedbackListView = () => import('@/features/feedback/views/DeveloperFeedbackListView.vue'); const DeveloperFeedbackDetailView = () => import('@/features/feedback/views/DeveloperFeedbackDetailView.vue'); const routes = [ { path: '/', name: 'landing', component: Landing, }, { path: '/app', redirect: { name: 'dashboard' }, }, { path: '/app/dashboard', name: 'dashboard', component: OverviewView, meta: { requiresAuth: true }, }, { path: '/app/workspace', name: 'workspace-dashboard', component: DashboardView, meta: { requiresAuth: true }, }, { path: '/app/channels', name: 'channels', component: ChannelsView, meta: { requiresAuth: true }, }, { path: '/app/media-library', name: 'media-library', component: MediaLibraryView, meta: { requiresAuth: true }, }, { path: '/app/campaigns', name: 'campaigns', component: CampaignsView, meta: { requiresAuth: true }, }, { path: '/app/campaigns/:projectId', name: 'campaign-detail', component: CampaignDetailView, meta: { requiresAuth: true }, }, { path: '/app/reviews', name: 'review-queue', component: ReviewQueueView, meta: { requiresAuth: true }, }, { path: '/app/my-feedback', name: 'my-feedback', component: MyFeedbackListView, meta: { requiresAuth: true }, }, { path: '/app/my-feedback/:id', name: 'my-feedback-detail', component: MyFeedbackDetailView, meta: { requiresAuth: true }, }, { path: '/app/feedback', name: 'developer-feedback', component: DeveloperFeedbackListView, meta: { requiresAuth: true, roles: ['developer'] }, }, { path: '/app/feedback/:id', name: 'developer-feedback-detail', component: DeveloperFeedbackDetailView, meta: { requiresAuth: true, roles: ['developer'] }, }, { path: '/app/workspace-settings', name: 'workspace-settings', component: WorkspaceSettingsView, meta: { requiresAuth: true, roles: ['administrator', 'manager'] }, }, { path: '/app/workspaces/new', name: 'workspace-create', component: WorkspaceCreateView, meta: { requiresAuth: true, roles: ['administrator', 'manager'] }, }, { path: '/app/settings', component: SettingsLayoutView, meta: { requiresAuth: true }, children: [ { path: '', redirect: { name: 'settings-user-information' }, }, { path: 'user-information', name: 'settings-user-information', component: UserSettingsView, }, { path: 'workspaces', name: 'settings-workspaces', component: WorkspaceSettingsView, meta: { requiresAuth: true, roles: ['administrator', 'manager'] }, }, { path: 'integrations', name: 'settings-integrations', component: IntegrationsSettingsView, meta: { requiresAuth: true, roles: ['administrator', 'manager'] }, }, ], }, { path: '/app/content', name: 'content-items', component: ContentItemsView, meta: { requiresAuth: true }, }, { path: '/app/content/new', name: 'content-item-create', component: ContentItemDetailView, meta: { requiresAuth: true }, }, { path: '/app/content/:id', name: 'content-item-detail', component: ContentItemDetailView, meta: { requiresAuth: true }, }, { path: '/login', name: 'login', component: LoginView, meta: { notAuthenticated: true }, props: route => ({ returnUrl: route.query.returnUrl || '/app/dashboard' }), }, { path: '/profile', redirect: { name: 'dashboard' }, }, { path: '/register', name: 'register', component: RegisterView, meta: { requiresAuth: false }, }, { path: '/forgot-password', name: 'forgot-password', component: ForgotPasswordView, meta: { notAuthenticated: true }, }, { path: '/reset-password', name: 'reset-password', component: ResetPasswordView, meta: { notAuthenticated: true }, props: route => ({ email: route.query.email, token: route.query.token }), }, { path: '/verify-email', name: 'verify-email', component: VerifyEmailView, meta: { notAuthenticated: true }, }, { path: '/:pathMatch(.*)*', redirect: { name: 'landing' }, }, ]; const router = createRouter({ history: createWebHistory(import.meta.env.BASE_URL), routes, }); // Navigation guards router.beforeEach((to, from, next) => { const authStore = useAuthStore(); if (to.matched.some(record => record.meta.requiresAuth)) { if (!authStore.isAuthenticated) { next({ name: 'login', query: { returnUrl: to.fullPath }, }); } else { const requiredRoles = to.matched.flatMap(record => record.meta.roles ?? []); if (requiredRoles.length > 0 && !authStore.hasAnyRole(requiredRoles)) { next({ name: 'dashboard' }); return; } next(); } } else if (to.matched.some(record => record.meta.notAuthenticated)) { if (authStore.isAuthenticated) next({ name: 'dashboard' }); else next(); } else { next(); } }); export default router;