diff --git a/src/pages/Operators.tsx b/src/pages/Operators.tsx index 8e5f122d..955c9063 100644 --- a/src/pages/Operators.tsx +++ b/src/pages/Operators.tsx @@ -1,19 +1,30 @@ import React, { useState } from 'react'; import { useQuery } from '@tanstack/react-query'; +import { useNavigate } from 'react-router-dom'; import { Header } from '@/components/layout/Header'; import { Input } from '@/components/ui/input'; import { Button } from '@/components/ui/button'; import { Badge } from '@/components/ui/badge'; +import { Dialog, DialogContent } from '@/components/ui/dialog'; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '@/components/ui/select'; -import { Search, Filter, Building } from 'lucide-react'; +import { Search, Filter, Building, Plus } from 'lucide-react'; import { supabase } from '@/integrations/supabase/client'; import OperatorCard from '@/components/operators/OperatorCard'; +import { OperatorForm } from '@/components/admin/OperatorForm'; import { Company } from '@/types/database'; +import { useAuth } from '@/hooks/useAuth'; +import { useUserRole } from '@/hooks/useUserRole'; +import { toast } from '@/hooks/use-toast'; +import { submitCompanyCreation } from '@/lib/companyHelpers'; const Operators = () => { + const navigate = useNavigate(); + const { user } = useAuth(); + const { isModerator } = useUserRole(); const [searchTerm, setSearchTerm] = useState(''); const [sortBy, setSortBy] = useState('name'); const [filterBy, setFilterBy] = useState('all'); + const [isCreateModalOpen, setIsCreateModalOpen] = useState(false); const { data: operators, isLoading } = useQuery({ queryKey: ['operators'], @@ -46,6 +57,37 @@ const Operators = () => { }, }); + const handleCreateSubmit = async (data: any) => { + try { + if (!user) { + navigate('/auth'); + return; + } + + const result = await submitCompanyCreation( + data, + 'operator', + user.id, + isModerator() + ); + + toast({ + title: result.submitted ? "Operator Submitted" : "Operator Created", + description: result.submitted + ? "Your submission has been sent for review." + : "The operator has been created successfully." + }); + + setIsCreateModalOpen(false); + } catch (error: any) { + toast({ + title: "Error", + description: error.message || "Failed to create operator.", + variant: "destructive" + }); + } + }; + const filteredAndSortedOperators = React.useMemo(() => { if (!operators) return []; @@ -105,6 +147,22 @@ const Operators = () => { )} + +
+ +
@@ -178,6 +236,16 @@ const Operators = () => {

)} + + {/* Create Modal */} + + + setIsCreateModalOpen(false)} + /> + + ); diff --git a/src/pages/ParkOwners.tsx b/src/pages/ParkOwners.tsx index 93faaadb..8253492a 100644 --- a/src/pages/ParkOwners.tsx +++ b/src/pages/ParkOwners.tsx @@ -1,19 +1,30 @@ import React, { useState } from 'react'; import { useQuery } from '@tanstack/react-query'; +import { useNavigate } from 'react-router-dom'; import { Header } from '@/components/layout/Header'; import { Input } from '@/components/ui/input'; import { Button } from '@/components/ui/button'; import { Badge } from '@/components/ui/badge'; +import { Dialog, DialogContent } from '@/components/ui/dialog'; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '@/components/ui/select'; -import { Search, Filter, Building2 } from 'lucide-react'; +import { Search, Filter, Building2, Plus } from 'lucide-react'; import { supabase } from '@/integrations/supabase/client'; import ParkOwnerCard from '@/components/park-owners/ParkOwnerCard'; +import { PropertyOwnerForm } from '@/components/admin/PropertyOwnerForm'; import { Company } from '@/types/database'; +import { useAuth } from '@/hooks/useAuth'; +import { useUserRole } from '@/hooks/useUserRole'; +import { toast } from '@/hooks/use-toast'; +import { submitCompanyCreation } from '@/lib/companyHelpers'; const ParkOwners = () => { + const navigate = useNavigate(); + const { user } = useAuth(); + const { isModerator } = useUserRole(); const [searchTerm, setSearchTerm] = useState(''); const [sortBy, setSortBy] = useState('name'); const [filterBy, setFilterBy] = useState('all'); + const [isCreateModalOpen, setIsCreateModalOpen] = useState(false); const { data: parkOwners, isLoading } = useQuery({ queryKey: ['park-owners'], @@ -46,6 +57,37 @@ const ParkOwners = () => { }, }); + const handleCreateSubmit = async (data: any) => { + try { + if (!user) { + navigate('/auth'); + return; + } + + const result = await submitCompanyCreation( + data, + 'property_owner', + user.id, + isModerator() + ); + + toast({ + title: result.submitted ? "Property Owner Submitted" : "Property Owner Created", + description: result.submitted + ? "Your submission has been sent for review." + : "The property owner has been created successfully." + }); + + setIsCreateModalOpen(false); + } catch (error: any) { + toast({ + title: "Error", + description: error.message || "Failed to create property owner.", + variant: "destructive" + }); + } + }; + const filteredAndSortedOwners = React.useMemo(() => { if (!parkOwners) return []; @@ -105,6 +147,22 @@ const ParkOwners = () => { )} + +
+ +
@@ -178,6 +236,16 @@ const ParkOwners = () => {

)} + + {/* Create Modal */} + + + setIsCreateModalOpen(false)} + /> + + ); diff --git a/src/pages/Rides.tsx b/src/pages/Rides.tsx index a99417fd..3483e306 100644 --- a/src/pages/Rides.tsx +++ b/src/pages/Rides.tsx @@ -1,20 +1,31 @@ import { useState, useEffect } from 'react'; +import { useNavigate } from 'react-router-dom'; import { Header } from '@/components/layout/Header'; +import { Button } from '@/components/ui/button'; import { Badge } from '@/components/ui/badge'; +import { Dialog, DialogContent } from '@/components/ui/dialog'; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '@/components/ui/select'; -import { Filter, SlidersHorizontal, FerrisWheel } from 'lucide-react'; +import { Filter, SlidersHorizontal, FerrisWheel, Plus } from 'lucide-react'; import { AutocompleteSearch } from '@/components/search/AutocompleteSearch'; import { RideCard } from '@/components/rides/RideCard'; +import { RideForm } from '@/components/admin/RideForm'; import { Ride } from '@/types/database'; import { supabase } from '@/integrations/supabase/client'; +import { useAuth } from '@/hooks/useAuth'; +import { useUserRole } from '@/hooks/useUserRole'; +import { toast } from '@/hooks/use-toast'; export default function Rides() { + const navigate = useNavigate(); + const { user } = useAuth(); + const { isModerator } = useUserRole(); const [rides, setRides] = useState([]); const [loading, setLoading] = useState(true); const [searchQuery, setSearchQuery] = useState(''); const [sortBy, setSortBy] = useState('name'); const [filterCategory, setFilterCategory] = useState('all'); const [filterStatus, setFilterStatus] = useState('all'); + const [isCreateModalOpen, setIsCreateModalOpen] = useState(false); useEffect(() => { fetchRides(); @@ -65,6 +76,55 @@ export default function Rides() { } }; + const handleCreateSubmit = async (data: any) => { + try { + if (!user) { + navigate('/auth'); + return; + } + + if (isModerator()) { + const { error } = await supabase + .from('rides') + .insert(data); + + if (error) throw error; + + toast({ + title: "Ride Created", + description: "The ride has been created successfully.", + }); + + setIsCreateModalOpen(false); + fetchRides(); + } else { + const { error } = await supabase + .from('content_submissions') + .insert({ + user_id: user.id, + submission_type: 'ride', + status: 'pending', + content: data + }); + + if (error) throw error; + + toast({ + title: "Submission Sent", + description: "Your ride submission has been sent for moderation review.", + }); + + setIsCreateModalOpen(false); + } + } catch (error: any) { + toast({ + title: "Submission Failed", + description: error.message || "Failed to submit ride.", + variant: "destructive" + }); + } + }; + const filteredRides = rides.filter(ride => ride.name.toLowerCase().includes(searchQuery.toLowerCase()) || ride.park?.name?.toLowerCase().includes(searchQuery.toLowerCase()) || @@ -132,6 +192,22 @@ export default function Rides() { {rides.filter(r => r.category === 'roller_coaster').length} coasters + +
+ +
@@ -208,6 +284,17 @@ export default function Rides() {

)} + + {/* Create Modal */} + + + setIsCreateModalOpen(false)} + isEditing={false} + /> + + );