diff --git a/src/hooks/useHospitalStore.ts b/src/hooks/useHospitalStore.ts index d2e8905..fb588a5 100644 --- a/src/hooks/useHospitalStore.ts +++ b/src/hooks/useHospitalStore.ts @@ -139,6 +139,72 @@ export function useHospitalStore() { return () => clearTimeout(t); }, [state, initialLoadComplete]); + // Utility functions + const getCamaAreaId = useCallback((camaId: string): string | null => { + const cama = state.camas.find(c => c.id === camaId); + return cama?.areaId || null; + }, [state.camas]); + + const getInternacionAreaId = useCallback((internacionId: string): string | null => { + const internacion = state.internaciones.find(i => i.id === internacionId); + return internacion?.areaId || null; + }, [state.internaciones]); + + const getPacienteAreaId = useCallback((pacienteId: string): string | null => { + const internacion = state.internaciones.find(i => i.pacienteId === pacienteId && i.activa); + if (!internacion) { + const anyInternacion = state.internaciones.find(i => i.pacienteId === pacienteId); + if (anyInternacion) return getCamaAreaId(anyInternacion.camaId); + return null; + } + return getCamaAreaId(internacion.camaId); + }, [state.internaciones, getCamaAreaId]); + + // Permission functions + const canAccessArea = useCallback((areaId: string | null | undefined): boolean => { + const user = state.currentUser; + if (!user) return false; + if (user.rol === 'admin') return true; + if (!areaId) return false; + return user.areaId === areaId; + }, [state.currentUser]); + + const canChangeBed = useCallback((internacionId: string): boolean => { + const internacion = state.internaciones.find(i => i.id === internacionId); + if (!internacion) return false; + return canAccessArea(internacion.areaId); + }, [state.internaciones, canAccessArea]); + + const canEditInternacion = useCallback((internacionId: string): boolean => { + const areaId = getInternacionAreaId(internacionId); + return canAccessArea(areaId); + }, [getInternacionAreaId, canAccessArea]); + + const canEditCama = useCallback((camaId: string): boolean => { + const areaId = getCamaAreaId(camaId); + return canAccessArea(areaId); + }, [getCamaAreaId, canAccessArea]); + + const canEditPaciente = useCallback((pacienteId: string): boolean => { + const areaId = getPacienteAreaId(pacienteId); + return canAccessArea(areaId); + }, [getPacienteAreaId, canAccessArea]); + + const hasPermission = useCallback((permission: 'read' | 'write', section: string): boolean => { + const user = state.currentUser; + if (!user) return false; + if (user.rol === 'admin') return true; + if (user.rol === 'enfermero') { + if (section === 'glucemias' || section === 'signosvitales') return permission === 'read' || permission === 'write'; + return permission === 'read'; + } + if (user.rol === 'medico') { + if (section === 'miArea') return permission === 'read' || permission === 'write'; + return permission === 'read'; + } + return false; + }, [state.currentUser]); + // Acciones de navegación const setVista = useCallback((vista: Vista) => { setState(prev => ({ ...prev, vistaActual: vista })); @@ -172,7 +238,7 @@ export function useHospitalStore() { })); }, []); -// Acciones de camas + // Acciones de camas const actualizarCama = useCallback((id: string, datos: Partial) => { const cama = state.camas.find(c => c.id === id); if (!cama) return; @@ -208,7 +274,7 @@ export function useHospitalStore() { })); }, []); -// Acciones de internaciones + // Acciones de internaciones const iniciarInternacion = useCallback((internacion: Omit) => { const nuevaInternacion: Internacion = { ...internacion, @@ -218,7 +284,7 @@ export function useHospitalStore() { setState(prev => ({ ...prev, internaciones: [...prev.internaciones, nuevaInternacion], - camaS: prev.camas.map(c => + camas: prev.camas.map(c => c.id === internacion.camaId ? { ...c, estado: 'Ocupada' as const, pacienteId: internacion.pacienteId, internacionId: nuevaInternacion.id } : c @@ -227,7 +293,7 @@ export function useHospitalStore() { return nuevaInternacion.id; }, []); -const finalizarInternacion = useCallback((internacionId: string, datos: { + const finalizarInternacion = useCallback((internacionId: string, datos: { fechaEgreso: string; diagnosticoEgreso: string; motivoEgreso: Internacion['motivoEgreso'] @@ -247,7 +313,7 @@ const finalizarInternacion = useCallback((internacionId: string, datos: { ? { ...i, ...datos, activa: false } : i ), - cams: esFueraDeArea + camas: esFueraDeArea ? prev.camas.filter(c => c.id !== internacion.camaId) : prev.camas.map(c => c.id === internacion.camaId @@ -261,18 +327,21 @@ const finalizarInternacion = useCallback((internacionId: string, datos: { const actualizarInternacion = useCallback((internacionId: string, datos: Partial) => { const internacion = state.internaciones.find(i => i.id === internacionId); if (!internacion) return; - const user = state.currentUser; - const areaId = internacion.areaId || null; const oldCamaId = internacion.camaId; const newCamaId = datos.camaId; const cambioDeCama = newCamaId && newCamaId !== oldCamaId; - if (cambioDeCama && user && user.rol !== 'admin' && areaId && user.areaId !== areaId) { + if (cambioDeCama && !canChangeBed(internacionId)) { console.warn('No tiene permisos para cambiar la cama de esta internación'); return; } + if (!cambioDeCama && !canAccessArea(internacion.areaId)) { + console.warn('No tiene permisos para actualizar esta internación'); + return; + } + const pacienteId = datos.pacienteId || internacion.pacienteId; setState(prev => { @@ -318,7 +387,7 @@ const finalizarInternacion = useCallback((internacionId: string, datos: { const agregarEvolucion = useCallback((evolucion: Omit) => { const internacion = state.internaciones.find(i => i.id === evolucion.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar evolución en esta área'); return null; } @@ -338,7 +407,7 @@ const finalizarInternacion = useCallback((internacionId: string, datos: { if (!evolucion) return; const internacion = state.internaciones.find(i => i.id === evolucion.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar evolución en esta área'); return; } @@ -353,7 +422,7 @@ const finalizarInternacion = useCallback((internacionId: string, datos: { if (!evolucion) return; const internacion = state.internaciones.find(i => i.id === evolucion.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar evolución en esta área'); return; } @@ -367,7 +436,7 @@ const finalizarInternacion = useCallback((internacionId: string, datos: { const agregarLaboratorio = useCallback((laboratorio: Omit) => { const internacion = state.internaciones.find(i => i.id === laboratorio.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar laboratorio en esta área'); return null; } @@ -382,12 +451,12 @@ const finalizarInternacion = useCallback((internacionId: string, datos: { return nuevoLaboratorio.id; }, [state.internaciones, state.currentUser]); -const eliminarLaboratorio = useCallback((id: string) => { + const eliminarLaboratorio = useCallback((id: string) => { const laboratorio = state.laboratorios.find(l => l.id === id); if (!laboratorio) return; const internacion = state.internaciones.find(i => i.id === laboratorio.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar laboratorio en esta área'); return; } @@ -402,7 +471,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!laboratorio) return; const internacion = state.internaciones.find(i => i.id === laboratorio.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar laboratorio en esta área'); return; } @@ -416,7 +485,7 @@ const eliminarLaboratorio = useCallback((id: string) => { const agregarAcidoBase = useCallback((acidoBase: Omit) => { const internacion = state.internaciones.find(i => i.id === acidoBase.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar ácido-base en esta área'); return null; } @@ -436,7 +505,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!acidoBase) return; const internacion = state.internaciones.find(i => i.id === acidoBase.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar ácido-base en esta área'); return; } @@ -451,7 +520,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!acidoBase) return; const internacion = state.internaciones.find(i => i.id === acidoBase.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar ácido-base en esta área'); return; } @@ -465,7 +534,7 @@ const eliminarLaboratorio = useCallback((id: string) => { const agregarCultivo = useCallback((cultivo: Omit) => { const internacion = state.internaciones.find(i => i.id === cultivo.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar cultivo en esta área'); return null; } @@ -485,7 +554,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!cultivo) return; const internacion = state.internaciones.find(i => i.id === cultivo.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar cultivo en esta área'); return; } @@ -500,7 +569,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!cultivo) return; const internacion = state.internaciones.find(i => i.id === cultivo.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar cultivo en esta área'); return; } @@ -514,7 +583,7 @@ const eliminarLaboratorio = useCallback((id: string) => { const agregarEstudioComplementario = useCallback((estudio: Omit) => { const internacion = state.internaciones.find(i => i.id === estudio.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar estudio complementario en esta área'); return null; } @@ -534,7 +603,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!estudio) return; const internacion = state.internaciones.find(i => i.id === estudio.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar estudio complementario en esta área'); return; } @@ -549,7 +618,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!estudio) return; const internacion = state.internaciones.find(i => i.id === estudio.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar estudio complementario en esta área'); return; } @@ -563,7 +632,7 @@ const eliminarLaboratorio = useCallback((id: string) => { const agregarInterconsulta = useCallback((interconsulta: Omit) => { const internacion = state.internaciones.find(i => i.id === interconsulta.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar interconsulta en esta área'); return null; } @@ -580,7 +649,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!interconsulta) return; const internacion = state.internaciones.find(i => i.id === interconsulta.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar interconsulta en esta área'); return; } @@ -595,7 +664,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!interconsulta) return; const internacion = state.internaciones.find(i => i.id === interconsulta.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar interconsulta en esta área'); return; } @@ -608,7 +677,7 @@ const eliminarLaboratorio = useCallback((id: string) => { const agregarATB = useCallback((atb: Omit) => { const internacion = state.internaciones.find(i => i.id === atb.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar ATB en esta área'); return null; } @@ -625,7 +694,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!atb) return; const internacion = state.internaciones.find(i => i.id === atb.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar ATB en esta área'); return; } @@ -640,7 +709,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!atb) return; const internacion = state.internaciones.find(i => i.id === atb.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar ATB en esta área'); return; } @@ -653,7 +722,7 @@ const eliminarLaboratorio = useCallback((id: string) => { const agregarIndicacion = useCallback((indicacion: Omit) => { const internacion = state.internaciones.find(i => i.id === indicacion.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar indicación en esta área'); return null; } @@ -670,7 +739,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!indicacion) return; const internacion = state.internaciones.find(i => i.id === indicacion.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para actualizar indicación en esta área'); return; } @@ -685,7 +754,7 @@ const eliminarLaboratorio = useCallback((id: string) => { if (!indicacion) return; const internacion = state.internaciones.find(i => i.id === indicacion.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para eliminar indicación en esta área'); return; } @@ -698,7 +767,7 @@ const eliminarLaboratorio = useCallback((id: string) => { const agregarMovimientoIndicacion = useCallback((movimiento: any) => { const internacion = state.internaciones.find(i => i.id === movimiento.internacionId); const areaId = internacion?.areaId || null; - if (!canEditInArea(areaId)) { + if (!canAccessArea(areaId)) { console.warn('No tiene permisos para agregar movimiento de indicación en esta área'); return; } @@ -739,7 +808,7 @@ const eliminarLaboratorio = useCallback((id: string) => { })); }, []); - // Funciones de utilidad + // Funciones de utilidad para consultas const getPacienteById = useCallback((id: string) => { return state.pacientes.find(p => p.id === id); }, [state.pacientes]); @@ -780,7 +849,7 @@ const eliminarLaboratorio = useCallback((id: string) => { .sort((a, b) => new Date(b.fechaToma).getTime() - new Date(a.fechaToma).getTime()); }, [state.cultivos]); -const getEstadisticas = useCallback(() => { + const getEstadisticas = useCallback(() => { const fueraDeAreaList = state.camas.filter(c => c.areaId === 'Fuera de Area'); const camasActivas = state.camas.filter(c => c.areaId !== 'Fuera de Area'); const camaPrincipal = state.camas.filter(c => c.areaId !== 'Fuera de Area'); @@ -866,82 +935,6 @@ const getEstadisticas = useCallback(() => { return true; }, []); - const hasPermission = useCallback((permission: 'read' | 'write', section: string): boolean => { - const user = state.currentUser; - if (!user) return false; - if (user.rol === 'admin') return true; - if (user.rol === 'enfermero') { - if (section === 'glucemias' || section === 'signosvitales') return permission === 'read' || permission === 'write'; - return permission === 'read'; - } - if (user.rol === 'medico') { - if (section === 'miArea') return permission === 'read' || permission === 'write'; - return permission === 'read'; - } - return false; - }, [state.currentUser]); - - const canAccessInternacion = useCallback((internacionId: string): boolean => { - const user = state.currentUser; - if (!user) return false; - const rol = user.rol as string; - if (rol === 'admin') return true; - if (rol === 'medico' && user.areaId) { - const internacion = state.internaciones.find(i => i.id === internacionId); - if (!internacion) return false; - const cama = state.camas.find(c => c.id === internacion.camaId); - return cama?.areaId === user.areaId; - } - return rol === 'admin'; - }, [state.currentUser, state.internaciones, state.camas]); - - const getCamaAreaId = useCallback((camaId: string): string | null => { - const cama = state.camas.find(c => c.id === camaId); - return cama?.areaId || null; - }, [state.camas]); - - const getInternacionAreaId = useCallback((internacionId: string): string | null => { - const internacion = state.internaciones.find(i => i.id === internacionId); - if (!internacion) return null; - // Use the new areaId field first - if (internacion.areaId) return internacion.areaId; - // Fallback to cama's area - return getCamaAreaId(internacion.camaId); - }, [state.internaciones, getCamaAreaId]); - - const getPacienteAreaId = useCallback((pacienteId: string): string | null => { - const internacion = state.internaciones.find(i => i.pacienteId === pacienteId && i.activa); - if (!internacion) { - const anyInternacion = state.internaciones.find(i => i.pacienteId === pacienteId); - if (anyInternacion) return getCamaAreaId(anyInternacion.camaId); - return null; - } - return getCamaAreaId(internacion.camaId); - }, [state.internaciones, getCamaAreaId]); - - const canEditInArea = useCallback((areaId: string | null | undefined): boolean => { - const user = state.currentUser; - if (!user) return false; - if (user.rol === 'admin') return true; - if (!areaId) return false; - return user.areaId === areaId; - }, [state.currentUser]); - - const canEditCama = useCallback((camaId: string): boolean => { - const areaId = getCamaAreaId(camaId); - return canEditInArea(areaId); - }, [getCamaAreaId, canEditInArea]); - - const canEditInternacion = useCallback((internacionId: string): boolean => { - const areaId = getInternacionAreaId(internacionId); - return canEditInArea(areaId); - }, [getInternacionAreaId, canEditInArea]); - - const canEditPaciente = useCallback((pacienteId: string): boolean => { - const areaId = getPacienteAreaId(pacienteId); - return canEditInArea(areaId); - }, [getPacienteAreaId, canEditInArea]); - return { ...state, isLoaded, @@ -956,8 +949,10 @@ const getEstadisticas = useCallback(() => { agregarCama, eliminarCama, agregarEvolucion, + actualizarEvolucion, eliminarEvolucion, agregarLaboratorio, + actualizarLaboratorio, eliminarLaboratorio, agregarAcidoBase, actualizarAcidoBase, @@ -990,8 +985,6 @@ const getEstadisticas = useCallback(() => { getLaboratoriosByPaciente, getAcidosBaseByPaciente, getCultivosByPaciente, - actualizarEvolucion, - actualizarLaboratorio, setCurrentInternacion, getEstadisticas, login, @@ -999,10 +992,10 @@ const getEstadisticas = useCallback(() => { changePassword, updateEmail, hasPermission, - canAccessInternacion, - canEditInArea, - canEditCama, + canAccessArea, + canChangeBed, canEditInternacion, + canEditCama, canEditPaciente, getCamaAreaId, getInternacionAreaId, diff --git a/src/sections/MapaCamas.tsx b/src/sections/MapaCamas.tsx index 1cc3a47..f8b808d 100644 --- a/src/sections/MapaCamas.tsx +++ b/src/sections/MapaCamas.tsx @@ -42,7 +42,7 @@ export function MapaCamas({ getPacienteById, getInternacionById }: MapaCamasProps) { - const { canEditCama, canEditInArea } = useHospitalStore(); + const { canEditCama, canAccessArea } = useHospitalStore(); const [filtroSala, setFiltroSala] = useState('todas'); const [filtroTipo, setFiltroTipo] = useState('todos'); const [filtroEstado, setFiltroEstado] = useState('todos');