mirror of
https://github.com/R0m1k3/LogiFlow.git
synced 2026-10-14 18:59:18 +02:00
Ensure all users can view relevant data by filtering it by their selected store
Fix data fetching logic to correctly apply store filtering for all user roles, and add an alert for managers/directors if no store is selected. Replit-Commit-Author: Agent Replit-Commit-Session-Id: 15f19c36-9aac-46a4-a181-3dc5f496fabd Replit-Commit-Checkpoint-Type: full_checkpoint Replit-Commit-Screenshot-Url: https://storage.googleapis.com/screenshot-production-us-central1/1957c339-2757-4d1f-8e92-e9f71a1ce58e/15f19c36-9aac-46a4-a181-3dc5f496fabd/H1nJA1b
This commit is contained in:
1 parent
46de48f459
commit
20efd9251e
4 files changed
+53
-9
No files matched your search
@@ -2,7 +2,7 @@ import { ReactNode, useState, createContext, useContext, useEffect } from "react
|
||||
import { useQuery, useQueryClient } from "@tanstack/react-query";
|
||||
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select";
|
||||
import { Button } from "@/components/ui/button";
|
||||
import { LogOut, Store, Menu } from "lucide-react";
|
||||
import { LogOut, Store, Menu, AlertTriangle } from "lucide-react";
|
||||
import { useAuthUnified } from "@/hooks/useAuthUnified";
|
||||
import { useIsMobile } from "@/hooks/use-mobile";
|
||||
import Sidebar from "./Sidebar";
|
||||
@@ -72,29 +72,52 @@ export default function Layout({ children }: LayoutProps) {
|
||||
// Effet pour marquer l'initialisation comme terminée
|
||||
useEffect(() => {
|
||||
if (user && stores.length > 0) {
|
||||
// Pour les admins, vérifier que selectedStoreId est cohérent avec les stores disponibles
|
||||
if (user.role === 'admin' && selectedStoreId) {
|
||||
let needsUpdate = false;
|
||||
|
||||
// Pour tous les rôles, vérifier que selectedStoreId est cohérent avec les stores disponibles
|
||||
if (selectedStoreId) {
|
||||
const storeExists = stores.find(store => store.id === selectedStoreId);
|
||||
if (!storeExists) {
|
||||
console.log('🏪 Selected store not found in available stores, clearing selection');
|
||||
console.log('🏪 Selected store not found in available stores, clearing selection:', {
|
||||
selectedStoreId,
|
||||
userRole: user.role,
|
||||
availableStores: stores.map(s => s.id)
|
||||
});
|
||||
setSelectedStoreId(null);
|
||||
localStorage.removeItem('selectedStoreId');
|
||||
needsUpdate = true;
|
||||
} else {
|
||||
console.log('🏪 Selected store validated successfully:', {
|
||||
selectedStoreId,
|
||||
userRole: user.role,
|
||||
storeName: storeExists.name
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
// IMPORTANT FIX: Pour les rôles directeur/manager, forcer la sélection d'un magasin spécifique
|
||||
// si aucun n'est sélectionné et qu'ils n'ont accès qu'à un seul magasin
|
||||
if ((user.role === 'directeur' || user.role === 'manager') && !selectedStoreId && stores.length === 1) {
|
||||
if ((user.role === 'directeur' || user.role === 'manager') && !selectedStoreId && stores.length === 1 && !needsUpdate) {
|
||||
console.log('🏪 Auto-selecting single available store for directeur/manager:', stores[0].id);
|
||||
const singleStoreId = stores[0].id;
|
||||
setSelectedStoreId(singleStoreId);
|
||||
localStorage.setItem('selectedStoreId', singleStoreId.toString());
|
||||
}
|
||||
|
||||
// VALIDATION CRITIQUE: Pour les directeurs/managers, s'assurer qu'un magasin est toujours sélectionné
|
||||
if ((user.role === 'directeur' || user.role === 'manager') && !selectedStoreId && !needsUpdate) {
|
||||
console.log('🚨 CRITICAL: Directeur/Manager has no store selected, this will cause empty data display:', {
|
||||
userId: user.id,
|
||||
userRole: user.role,
|
||||
availableStores: stores.map(s => ({ id: s.id, name: s.name }))
|
||||
});
|
||||
}
|
||||
|
||||
console.log('🏪 Store initialization complete:', {
|
||||
user: user.role,
|
||||
selectedStoreId,
|
||||
storesCount: stores.length,
|
||||
validatedStore: selectedStoreId ? stores.find(s => s.id === selectedStoreId)?.name : 'None',
|
||||
autoSelected: (user.role === 'directeur' || user.role === 'manager') && !selectedStoreId && stores.length === 1
|
||||
});
|
||||
setStoreInitialized(true);
|
||||
@@ -206,6 +229,23 @@ export default function Layout({ children }: LayoutProps) {
|
||||
)}
|
||||
</header>
|
||||
|
||||
{/* Alert for directeur/manager without store selection */}
|
||||
{user && (user.role === 'directeur' || user.role === 'manager') && !selectedStoreId && storeInitialized && (
|
||||
<div className="bg-red-50 border-l-4 border-red-400 p-4 m-4">
|
||||
<div className="flex">
|
||||
<div className="flex-shrink-0">
|
||||
<AlertTriangle className="h-5 w-5 text-red-400" />
|
||||
</div>
|
||||
<div className="ml-3">
|
||||
<p className="text-sm text-red-700">
|
||||
<strong>Action requise :</strong> Veuillez sélectionner un magasin pour afficher les données.
|
||||
Vos permissions ne permettent pas de voir les données de tous les magasins.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
<div className="flex-1 bg-gray-50 p-6 h-full overflow-y-auto">
|
||||
{children}
|
||||
</div>
|
||||
|
||||
@@ -71,7 +71,8 @@ export default function Deliveries() {
|
||||
const [deliveryToDelete, setDeliveryToDelete] = useState<DeliveryWithRelations | null>(null);
|
||||
|
||||
// Construire l'URL pour l'historique complet sans filtrage par date
|
||||
const deliveriesUrl = `/api/deliveries${selectedStoreId && user?.role === 'admin' ? `?storeId=${selectedStoreId}` : ''}`;
|
||||
// CRITICAL FIX: Appliquer le filtrage par storeId pour TOUS les rôles, pas seulement admin
|
||||
const deliveriesUrl = `/api/deliveries${selectedStoreId ? `?storeId=${selectedStoreId}` : ''}`;
|
||||
|
||||
const { data: deliveriesData = [], isLoading } = useQuery<DeliveryWithRelations[]>({
|
||||
queryKey: ['/api/deliveries', selectedStoreId, user?.role],
|
||||
|
||||
@@ -69,7 +69,8 @@ export default function Orders() {
|
||||
const [orderToDelete, setOrderToDelete] = useState<OrderWithRelations | null>(null);
|
||||
|
||||
// Construire l'URL pour l'historique complet sans filtrage par date
|
||||
const ordersUrl = `/api/orders${selectedStoreId && user?.role === 'admin' ? `?storeId=${selectedStoreId}` : ''}`;
|
||||
// CRITICAL FIX: Appliquer le filtrage par storeId pour TOUS les rôles, pas seulement admin
|
||||
const ordersUrl = `/api/orders${selectedStoreId ? `?storeId=${selectedStoreId}` : ''}`;
|
||||
|
||||
const { data: ordersData = [], isLoading } = useQuery<OrderWithRelations[]>({
|
||||
queryKey: [ordersUrl, selectedStoreId],
|
||||
|
||||
@@ -339,14 +339,16 @@ export default function Tasks() {
|
||||
queryFn: async () => {
|
||||
try {
|
||||
const params = new URLSearchParams();
|
||||
if (selectedStoreId && user?.role === 'admin') {
|
||||
// CRITICAL FIX: Appliquer le filtrage par storeId pour TOUS les rôles, pas seulement admin
|
||||
if (selectedStoreId) {
|
||||
params.append('storeId', selectedStoreId.toString());
|
||||
}
|
||||
console.log('📋 TASKS QUERY - Fetching with params:', {
|
||||
selectedStoreId,
|
||||
userRole: user?.role,
|
||||
storeInitialized,
|
||||
url: `/api/tasks?${params.toString()}`
|
||||
url: `/api/tasks?${params.toString()}`,
|
||||
willFilterByStore: !!selectedStoreId
|
||||
});
|
||||
|
||||
const response = await fetch(`/api/tasks?${params.toString()}`, {
|
||||
|
||||
Reference in new issue
Block a user