diff --git a/app/dashboard/company/[slug]/events/page.tsx b/app/dashboard/company/[slug]/events/page.tsx index 886d8bca..949d75e7 100644 --- a/app/dashboard/company/[slug]/events/page.tsx +++ b/app/dashboard/company/[slug]/events/page.tsx @@ -25,13 +25,15 @@ import { } from '@/components/ui/alert-dialog' export default function CompanyEventsPage() { - const { currentCompany, loading: companyLoading } = useCompanyContext() + const { currentCompany, userRole, loading: companyLoading } = useCompanyContext() const isPendingInvitation = usePendingInvitationRedirect() const [events, setEvents] = useState([]) const [loading, setLoading] = useState(true) const [searchTerm, setSearchTerm] = useState('') const [deletingEventSlug, setDeletingEventSlug] = useState(null) + const canManageEvents = userRole && ['owner', 'admin', 'editor'].includes(userRole) + const fetchEvents = useCallback(async () => { if (!currentCompany) return @@ -170,15 +172,17 @@ export default function CompanyEventsPage() {

Events

- Manage your company's events and hackathons + {canManageEvents ? "Manage your company's events and hackathons" : "View your company's events"}

- - - + {canManageEvents && ( + + + + )} {/* Stats Cards */} @@ -239,7 +243,7 @@ export default function CompanyEventsPage() { All Events ({filteredEvents.length}) - View and manage all your events + {canManageEvents ? 'View and manage all your events' : 'View all company events'} @@ -254,10 +258,10 @@ export default function CompanyEventsPage() { No events found

- {searchTerm ? 'Try adjusting your search' : 'Get started by creating your first event'} + {searchTerm ? 'Try adjusting your search' : canManageEvents ? 'Get started by creating your first event' : 'No events available yet'}

- {!searchTerm && ( - + {!searchTerm && canManageEvents && ( + - - {event.approval_status === 'approved' && ( + {canManageEvents ? ( + +
+ + + + {event.approval_status === 'approved' && ( + + + + )} + + + + + + + Delete Event + + Are you sure you want to delete "{event.title}"? This action cannot be undone. + {event.registered && event.registered > 0 && ( + + Warning: This event has {event.registered} registered participant{event.registered > 1 ? 's' : ''}. + + )} + + + + Cancel + handleDeleteEvent(event.slug)} + className="bg-red-600 hover:bg-red-700" + > + Delete + + + + +
+
+ ) : ( + event.approval_status === 'approved' && ( + - )} - - - - - - - Delete Event - - Are you sure you want to delete "{event.title}"? This action cannot be undone. - {event.registered && event.registered > 0 && ( - - Warning: This event has {event.registered} registered participant{event.registered > 1 ? 's' : ''}. - - )} - - - - Cancel - handleDeleteEvent(event.slug)} - className="bg-red-600 hover:bg-red-700" - > - Delete - - - - - - + + ) + )} ))} diff --git a/app/dashboard/company/[slug]/hackathons/page.tsx b/app/dashboard/company/[slug]/hackathons/page.tsx index 9da9f887..049861e0 100644 --- a/app/dashboard/company/[slug]/hackathons/page.tsx +++ b/app/dashboard/company/[slug]/hackathons/page.tsx @@ -29,12 +29,14 @@ interface Hackathon { } export default function CompanyHackathonsPage() { - const { currentCompany, loading: companyLoading } = useCompanyContext() + const { currentCompany, userRole, loading: companyLoading } = useCompanyContext() const isPendingInvitation = usePendingInvitationRedirect() const [hackathons, setHackathons] = useState([]) const [loading, setLoading] = useState(true) const [searchTerm, setSearchTerm] = useState('') + const canManageEvents = userRole && ['owner', 'admin', 'editor'].includes(userRole) + const fetchHackathons = useCallback(async () => { if (!currentCompany) return @@ -149,15 +151,17 @@ export default function CompanyHackathonsPage() {

Hackathons

- Manage your company's hackathons and coding challenges + {canManageEvents ? "Manage your company's hackathons and coding challenges" : "View your company's hackathons"}

- - - + {canManageEvents && ( + + + + )} {/* Stats Cards */} @@ -218,7 +222,7 @@ export default function CompanyHackathonsPage() { All Hackathons ({filteredHackathons.length}) - View and manage all your hackathons + {canManageEvents ? 'View and manage all your hackathons' : 'View all company hackathons'} @@ -247,7 +251,7 @@ export default function CompanyHackathonsPage() { Approval Views Participants - Actions + {canManageEvents && Actions} @@ -279,22 +283,34 @@ export default function CompanyHackathonsPage() { {hackathon.registered || 0} - -
- - - - {hackathon.approval_status === 'approved' && ( + {canManageEvents ? ( + +
+ + + + {hackathon.approval_status === 'approved' && ( + + + + )} +
+
+ ) : ( + hackathon.approval_status === 'approved' && ( + - )} -
-
+ + ) + )} ))}
diff --git a/app/dashboard/company/[slug]/page.tsx b/app/dashboard/company/[slug]/page.tsx index de1c6c03..0d2a7d24 100644 --- a/app/dashboard/company/[slug]/page.tsx +++ b/app/dashboard/company/[slug]/page.tsx @@ -76,14 +76,16 @@ export default function CompanySlugDashboardPage() { Here's what's happening with {currentCompany.name}

-
- -
+ {userRole && ['owner', 'admin', 'editor'].includes(userRole) && ( +
+ +
+ )} {/* Subscription Expiry Warning */} @@ -162,13 +164,15 @@ export default function CompanySlugDashboardPage() {

-
- -
+ {userRole && ['owner', 'admin'].includes(userRole) && ( +
+ +
+ )}
diff --git a/app/dashboard/company/[slug]/subscription/page.tsx b/app/dashboard/company/[slug]/subscription/page.tsx index 9af77795..89750561 100644 --- a/app/dashboard/company/[slug]/subscription/page.tsx +++ b/app/dashboard/company/[slug]/subscription/page.tsx @@ -5,8 +5,8 @@ import { companyService } from '@/lib/services/company-service' import { SubscriptionManagement } from '@/components/subscription/SubscriptionManagement' export const metadata: Metadata = { - title: 'Subscription Management | CodeUnia', - description: 'Manage your company subscription and billing', + title: 'Subscription | CodeUnia', + description: 'View your company subscription and billing information', } interface PageProps { @@ -59,17 +59,19 @@ export default async function SubscriptionPage({ params }: PageProps) { redirect('/dashboard/company') } - // Only owners and admins can manage subscription - if (!['owner', 'admin'].includes(membership.role)) { - redirect(`/dashboard/company/${slug}`) - } + // Check if user can manage subscription + const canManageSubscription = ['owner', 'admin'].includes(membership.role) return (
-

Subscription Management

+

+ {canManageSubscription ? 'Subscription Management' : 'Subscription Information'} +

- Manage your subscription plan and view usage details + {canManageSubscription + ? 'Manage your subscription plan and view usage details' + : 'View your company subscription plan and usage details'}

diff --git a/app/dashboard/company/[slug]/team/page.tsx b/app/dashboard/company/[slug]/team/page.tsx index 77d6ac57..50110fbd 100644 --- a/app/dashboard/company/[slug]/team/page.tsx +++ b/app/dashboard/company/[slug]/team/page.tsx @@ -51,19 +51,23 @@ export default function TeamPage() { ) } + const canManageTeam = userRole && ['owner', 'admin'].includes(userRole) + return (

Team Management

- Manage your team members, roles, and permissions + {canManageTeam + ? 'Manage your team members, roles, and permissions' + : 'View your team members and their roles'}

) diff --git a/components/dashboard/CompanyDashboard.tsx b/components/dashboard/CompanyDashboard.tsx index 76f167aa..a7d03833 100644 --- a/components/dashboard/CompanyDashboard.tsx +++ b/components/dashboard/CompanyDashboard.tsx @@ -22,6 +22,7 @@ import { } from 'lucide-react' import { Company } from '@/types/company' import { format, formatDistanceToNow } from 'date-fns' +import { useCompanyContext } from '@/contexts/CompanyContext' interface CompanyDashboardStats { totalEvents: number @@ -63,12 +64,17 @@ interface CompanyDashboardProps { } export function CompanyDashboard({ company }: CompanyDashboardProps) { + const { userRole } = useCompanyContext() const [stats, setStats] = useState(null) const [recentActivity, setRecentActivity] = useState([]) const [upcomingEvents, setUpcomingEvents] = useState([]) const [loading, setLoading] = useState(true) const [error, setError] = useState(null) + // Check permissions based on role + const canManageEvents = userRole && ['owner', 'admin', 'editor'].includes(userRole) + const canManageTeam = userRole && ['owner', 'admin'].includes(userRole) + const fetchDashboardData = useCallback(async () => { try { setLoading(true) @@ -342,18 +348,22 @@ export function CompanyDashboard({ company }: CompanyDashboardProps) {
- - + {canManageEvents && ( + + )} + {canManageTeam && ( + + )} setCollapsed(!collapsed) const pathname = usePathname() const { navigateTo } = useSafeNavigation() - const { currentCompany, userCompanies, switchCompany } = useCompanyContext() + const { currentCompany, userCompanies, userRole, switchCompany } = useCompanyContext() return ( @@ -164,7 +164,7 @@ export function CompanySidebar({ {name} - {currentCompany?.name} + {userRole ? `${userRole.charAt(0).toUpperCase() + userRole.slice(1)} • ${currentCompany?.name}` : currentCompany?.name}
@@ -420,7 +420,7 @@ export function CompanySidebar({ {name} - {currentCompany?.name} + {userRole ? `${userRole.charAt(0).toUpperCase() + userRole.slice(1)} • ${currentCompany?.name}` : currentCompany?.name}
diff --git a/components/dashboard/TeamManagement.tsx b/components/dashboard/TeamManagement.tsx index 39912dc3..096fb8d2 100644 --- a/components/dashboard/TeamManagement.tsx +++ b/components/dashboard/TeamManagement.tsx @@ -319,7 +319,9 @@ export function TeamManagement({
Team Members - Manage your team members and their roles + {canManageTeam + ? 'Manage your team members and their roles' + : 'View your team members and their roles'}
{canManageTeam && (