From 57818b180a42c1530e5b6210d77186cab245eafb Mon Sep 17 00:00:00 2001 From: Lizandro Guarnizo <77708265+lizandrogd@users.noreply.github.com> Date: Tue, 11 Aug 2026 09:05:48 -0500 Subject: [PATCH] =?UTF-8?q?Estaci=C3=B3n=20de=20muestras:=20corregir=20la?= =?UTF-8?q?=20ficha=20del=20paciente=20desde=20el=20turno?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Los campos del formulario F-LAB-08 son vinculados: leen de la ficha del paciente. Si el dato está mal, no había forma de arreglarlo desde la estación —el modal era de solo lectura— y corregirlo únicamente en el documento habría dejado la ficha equivocada, reapareciendo en el próximo turno, orden o consentimiento. Por eso se corrige la ficha y no el documento: el dato queda bien en todo el sistema y el formulario, al ser automático, lo toma solo. La edición tiene dos niveles de fricción. Teléfono, dirección y EPS se editan directo: cambian seguido y el error es de bajo riesgo. Nombre, tipo y número de documento y fecha de nacimiento quedan tras un botón aparte con confirmación, porque identifican al paciente en toda su historia clínica. Si el turno ya tiene documentos firmados se advierte que corregir la ficha no los modifica y que hay que emitirlos de nuevo, para que nadie espere que un PDF ya firmado se actualice solo. Paciente::actualizar registraba en la bitácora solo el valor nuevo, lo que impedía reconstruir el anterior si la corrección resultaba equivocada —justo cuando hace falta consultarlo. Ahora guarda antes y después, y únicamente de los campos que realmente cambiaron. La validación del servidor ya cubría nombre, celular, documento y correo, y la cédula tiene índice único, así que no hizo falta agregar validación. Co-Authored-By: Claude Opus 5 --- classes/lab/Paciente.php | 16 ++- modules/turnero/views/lugar.php | 179 ++++++++++++++++++++++++++++++++ 2 files changed, 194 insertions(+), 1 deletion(-) diff --git a/classes/lab/Paciente.php b/classes/lab/Paciente.php index a30beef..413bc59 100644 --- a/classes/lab/Paciente.php +++ b/classes/lab/Paciente.php @@ -173,8 +173,22 @@ class Paciente { } } + // Registrar antes y después de lo que realmente cambia. Guardar solo el + // valor nuevo impide reconstruir el dato anterior si la corrección + // resultó equivocada, que es justo cuando hace falta consultarlo. + $antes = $this->db->fetch('SELECT * FROM lab_pacientes WHERE id = ?', [$id]) ?: []; + $cambios = []; + foreach ($campos as $campo => $nuevo) { + $previo = $antes[$campo] ?? null; + if ((string)$previo !== (string)$nuevo) { + $cambios[$campo] = ['antes' => $previo, 'despues' => $nuevo]; + } + } + $ok = $this->db->update('lab_pacientes', $campos, 'id = ?', [$id]); - $this->log->registrar($adminId, 'pacientes', 'editar', $id, $campos); + if ($cambios) { + $this->log->registrar($adminId, 'pacientes', 'editar', $id, $cambios); + } return $ok > 0; } diff --git a/modules/turnero/views/lugar.php b/modules/turnero/views/lugar.php index 12bef02..730a4d8 100644 --- a/modules/turnero/views/lugar.php +++ b/modules/turnero/views/lugar.php @@ -520,6 +520,15 @@ try { } /* Historial timeline */ .mpac-timeline { padding: 0; } + .mpac-lbl { font-size:.7rem; color:#64748b; font-weight:600; display:block; margin-bottom:2px; } + .mpac-aviso { font-size:.74rem; color:#1e40af; background:#eff6ff; border:1px solid #bfdbfe; + border-radius:8px; padding:7px 10px; margin-bottom:10px; } + .mpac-lock { background:#fffbeb; border:1px solid #fde68a; border-radius:8px; + padding:9px 11px; margin:4px 0 10px; } + .mpac-lock-txt { font-size:.72rem; color:#92400e; margin-bottom:7px; line-height:1.45; } + .mpac-aviso-firmados { font-size:.74rem; color:#7f1d1d; background:#fef2f2; + border:1px solid #fecaca; border-radius:8px; + padding:8px 11px; margin-bottom:10px; line-height:1.45; } .mtl-item { display:flex; gap:10px; align-items:flex-start; padding-bottom:12px; position:relative; @@ -949,6 +958,79 @@ require_once __DIR__ . '/../../../shared/components/sidebar.php';
Paciente embarazada
+
+ +
+ + + +
+
+ + Lo que corrija aquí cambia la ficha del paciente en todo el sistema. +
+ + + + + + + + + + + +
+
+ + Nombre, documento y fecha de nacimiento identifican al paciente en toda su + historia clínica. +
+ +
+ +
+ + + +
+
+ + +
+
+ + +
+
+ + + +
+ +
+ + Este turno ya tiene documentos firmados. Corregir la ficha + no modifica lo que ya se firmó: si un documento salió con datos + equivocados, hay que emitirlo de nuevo. +
+ +
+
+ + +
Historial de visitas
@@ -2386,6 +2468,103 @@ function abrirModalPaciente() { function cerrarModalPaciente() { document.getElementById('modal-pac-lugar').classList.remove('show'); + mpacEditar(false); +} + +/* ── Corrección de la ficha del paciente desde la estación ── + Los campos del formulario son vinculados: leen de la ficha. Por eso se + corrige la ficha y no el documento — así el dato queda bien en el turnero, + los domicilios y las órdenes, no solo en la hoja que se está llenando. */ + +function mpacEditar(abrir) { + document.getElementById('mpac-form').classList.toggle('d-none', !abrir); + document.getElementById('mpac-datos').classList.toggle('d-none', abrir); + document.getElementById('mpac-msg').textContent = ''; + + if (!abrir) { mpacBloquearIdentidad(); return; } + + const p = _pacienteActivo || {}; + document.getElementById('mpac-in-tel').value = p.telefono || p.celular || ''; + document.getElementById('mpac-in-dir').value = p.direccion || ''; + document.getElementById('mpac-in-eps').value = p.eps || ''; + document.getElementById('mpac-in-nombre').value = p.nombre_completo || ''; + document.getElementById('mpac-in-tipodoc').value = p.tipo_documento || 'CC'; + document.getElementById('mpac-in-doc').value = p.numero_documento || p.documento || ''; + document.getElementById('mpac-in-fnac').value = (p.fecha_nacimiento || '').slice(0, 10); + + mpacBloquearIdentidad(); + + // Si ya hay documentos firmados, advertir que corregir no los modifica. + // El botón "Ver firmado" solo se renderiza para consentimientos ya firmados. + const firmados = document.querySelectorAll('#lista-consent button[title="Ver firmado"]').length > 0; + document.getElementById('mpac-aviso-firmados').classList.toggle('d-none', !firmados); +} + +function mpacBloquearIdentidad() { + document.getElementById('mpac-identidad').classList.add('d-none'); + document.getElementById('mpac-identidad-lock').classList.remove('d-none'); +} + +function mpacDesbloquearIdentidad() { + if (!confirm('Nombre, documento y fecha de nacimiento identifican al paciente en toda su ' + + 'historia clínica.\n\n¿Confirma que quiere corregirlos?')) return; + document.getElementById('mpac-identidad').classList.remove('d-none'); + document.getElementById('mpac-identidad-lock').classList.add('d-none'); +} + +async function mpacGuardarFicha() { + if (!_pacienteActivo?.id) return; + const msg = document.getElementById('mpac-msg'); + const btn = document.getElementById('mpac-btn-guardar'); + const val = id => document.getElementById(id).value.trim(); + + const cuerpo = { + id: _pacienteActivo.id, + telefono: val('mpac-in-tel'), + direccion: val('mpac-in-dir'), + eps: val('mpac-in-eps'), + }; + // Los datos de identidad solo se envían si se desbloquearon + if (!document.getElementById('mpac-identidad').classList.contains('d-none')) { + cuerpo.nombre_completo = val('mpac-in-nombre'); + cuerpo.tipo_documento = val('mpac-in-tipodoc'); + cuerpo.numero_documento = val('mpac-in-doc'); + cuerpo.fecha_nacimiento = val('mpac-in-fnac') || null; + } + + btn.disabled = true; + msg.className = 'small mb-2 text-muted'; + msg.textContent = 'Guardando…'; + + try { + const r = await fetch(`${BASE_WA}api/lab/save_paciente.php`, { + method: 'POST', headers: { 'Content-Type': 'application/json' }, + body: JSON.stringify(cuerpo), + }); + const d = await r.json(); + if (!d.ok) { + msg.className = 'small mb-2 text-danger'; + msg.textContent = d.error || 'No se pudo guardar.'; + btn.disabled = false; + return; + } + // Reflejar el cambio sin recargar: ficha del modal, tarjeta del turno + // y el formulario abierto, cuyos campos vinculados leen de la ficha. + Object.assign(_pacienteActivo, cuerpo); + msg.className = 'small mb-2 text-success'; + msg.textContent = 'Ficha actualizada.'; + setTimeout(() => { + mpacEditar(false); + abrirModalPaciente(); + if (turnoActivo?.id) actualizarConsentimientos(turnoActivo.id); + const marco = document.querySelector('#modal-consent iframe'); + if (marco && marco.src) marco.src = marco.src; + }, 700); + } catch (_) { + msg.className = 'small mb-2 text-danger'; + msg.textContent = 'Error de conexión.'; + btn.disabled = false; + } } async function cargarHistorialModal(pacienteId) {