From 4129ae68d0a74362da4696845ed6a9b2a5596262 Mon Sep 17 00:00:00 2001 From: michaelschal <35957947-michaelschal@users.noreply.replit.com> Date: Mon, 8 Sep 2025 16:36:18 +0000 Subject: [PATCH] Restrict users from creating or viewing data for groups they are not assigned to Modify the Avoirs page to filter data and group selection based on user's assigned groups, enhancing role-based access control. Replit-Commit-Author: Agent Replit-Commit-Session-Id: 9fcf4b21-eb0c-4e53-a567-e2ce4a6ad869 Replit-Commit-Checkpoint-Type: full_checkpoint Replit-Commit-Screenshot-Url: https://storage.googleapis.com/screenshot-production-us-central1/1957c339-2757-4d1f-8e92-e9f71a1ce58e/9fcf4b21-eb0c-4e53-a567-e2ce4a6ad869/OaTUMqA --- client/src/pages/Avoirs.tsx | 63 ++++++++++++++++++++----------------- 1 file changed, 35 insertions(+), 28 deletions(-) diff --git a/client/src/pages/Avoirs.tsx b/client/src/pages/Avoirs.tsx index ff49c35..a3797fc 100644 --- a/client/src/pages/Avoirs.tsx +++ b/client/src/pages/Avoirs.tsx @@ -1,6 +1,7 @@ import { useState } from "react"; import { useQuery, useMutation, useQueryClient } from "@tanstack/react-query"; -import { Plus, Search, FileText, CheckCircle, AlertCircle, Clock, Edit, Trash2 } from "lucide-react"; +import { Plus, Search, FileText, CheckCircle, AlertCircle, Clock, Edit, Trash2, UserCheck } from "lucide-react"; +import { useStore } from "@/components/Layout"; import { Button } from "@/components/ui/button"; import { Input } from "@/components/ui/input"; import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card"; @@ -99,7 +100,8 @@ export default function Avoirs() { const [isEditDialogOpen, setIsEditDialogOpen] = useState(false); const [isDeleteDialogOpen, setIsDeleteDialogOpen] = useState(false); const [selectedAvoir, setSelectedAvoir] = useState(null); - const [selectedStoreId, setSelectedStoreId] = useState("all"); + // Utiliser le contexte global du magasin + const { selectedStoreId } = useStore(); const { toast } = useToast(); const queryClient = useQueryClient(); @@ -120,10 +122,20 @@ export default function Avoirs() { enabled: !!user, }); - // Fetch avoirs + // Fetch avoirs avec filtrage par groupe (comme Orders/Deliveries) + const avoirsUrl = `/api/avoirs${selectedStoreId ? `?storeId=${selectedStoreId}` : ''}`; const { data: avoirs = [], isLoading } = useQuery({ - queryKey: ['/api/avoirs', selectedStoreId], - queryFn: () => apiRequest(`/api/avoirs${selectedStoreId !== 'all' ? `?storeId=${selectedStoreId}` : ''}`), + queryKey: [avoirsUrl, selectedStoreId, (user as any)?.role], + queryFn: async () => { + console.log('💰 Fetching avoirs from:', avoirsUrl); + const response = await fetch(avoirsUrl, { credentials: 'include' }); + if (!response.ok) { + throw new Error('Failed to fetch avoirs'); + } + const data = await response.json(); + console.log('💰 Avoirs received:', Array.isArray(data) ? data.length : 'NOT_ARRAY', 'items'); + return Array.isArray(data) ? data : []; + }, enabled: !!user, }); @@ -406,7 +418,15 @@ export default function Avoirs() { - {groups.map((group) => ( + {groups + .filter((group) => { + // Admin voit tous les groupes + if ((user as any)?.role === 'admin') return true; + // Autres rôles voient seulement leurs groupes assignés + const userGroupIds = (user as any)?.userGroups?.map((ug: any) => ug.groupId) || []; + return userGroupIds.includes(group.id); + }) + .map((group) => (
- {(user as any)?.role === 'admin' && ( - - )} + {/* Filtrage maintenant géré par le contexte global Layout */}
{/* Avoirs List - Format Table */} @@ -633,7 +633,14 @@ export default function Avoirs() { - {avoir.amount ? `${avoir.amount.toFixed(2)} €` : 'Non spécifié'} +
+ {avoir.amount ? `${avoir.amount.toFixed(2)} €` : 'Non spécifié'} + {avoir.commercialProcessed && ( +
+ +
+ )} +