# Modulo de Asistencia y Marcaciones (Asistencia)

# Obtiene descarga boleta de pago (2) - [getDownloadBoletaPago]

### 🧾 Descripción

*Este servicio valida si un empleado **debe descargar obligatoriamente su boleta de pago del último mes** antes de poder realizar acciones como:*

- Registrar marcación
- Registrar solicitudes en la app
- Acceder a otros módulos operativos

*El servicio evalúa:*

1. Si está dentro del rango de validación (solo **del día 1 al 3** de cada mes).
2. La **fecha de ingreso del trabajador**.
3. Si tiene boleta generada el mes anterior.
4. Si el mes correspondiente está **habilitado para descarga**.
5. Si el empleado **ya descargó** la boleta (se revisa historial en MySQL).
6. Si el empleado está **PreActivo**, no se valida la descarga.

---

# 🚀 Endpoint

### GET /get-download-boleta-pago/{empleado}

📌 **Parámetro obligatorio:**

- **empleado** → ID del Employee (name)

---

# 🔐 Seguridad

- Requiere autenticación interna por el ERP mediante `dbErp()` y conexión MySQL interna.
- El servicio está pensado solo para uso interno de la aplicación móvil corporativa.

---

# 🧠 Flujo del Servicio (resumen)

### 1️⃣ Validación de fecha

Solo se ejecuta validación si el día actual está entre **1 y 3**.  
Si el día &gt; 3 → se omite toda validación:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"No está dentro del rango de fecha de validación"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>---

### 2️⃣ Obtener información del empleado

Consulta ERP:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-select-fecha_de_ingr"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-keyword">SELECT</span> fecha_de_ingreso_real, status<span class="hljs-keyword">FROM</span> `tabEmployee`<span class="hljs-keyword">WHERE</span> name <span class="hljs-operator">=</span> <span class="hljs-operator"><</span>empleado<span class="hljs-operator">></span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>Si el empleado está **PreActivo**, no se valida boleta:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-1"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"No validar descarga de boleta en PreActivo"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>---

### 3️⃣ Comparar fecha de ingreso vs fecha límite

Se calcula:

- Mes anterior
- Último día del mes anterior

Solo se valida si el empleado ingresó **antes del cierre del mes previo**.

---

### 4️⃣ Verificar en MySQL si ya descargó la boleta

Consulta tabla `historial_procesos_app`:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-where-empleado-%3D-%3F-a"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-keyword">WHERE</span> empleado <span class="hljs-operator">=</span> ? <span class="hljs-keyword">AND</span> proceso <span class="hljs-operator">=</span> <span class="hljs-string">'NOMINA'</span><span class="hljs-keyword">AND</span> <span class="hljs-keyword">month</span> <span class="hljs-operator">=</span> <span class="hljs-operator"><</span>mes_anterior<span class="hljs-operator">></span><span class="hljs-keyword">AND</span> <span class="hljs-keyword">year</span> <span class="hljs-operator">=</span> <span class="hljs-operator"><</span>year_anterior<span class="hljs-operator">></span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>Si no existe registro se sigue validación.

---

### 5️⃣ Validar si EXISTE boleta en ERP

Consulta Salary Slip del último mes:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-select-posting_date-"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-keyword">SELECT</span> posting_date<span class="hljs-keyword">FROM</span> `tabSalary Slip`<span class="hljs-keyword">WHERE</span> employee <span class="hljs-operator">=</span> ?<span class="hljs-keyword">AND</span> posting_date <span class="hljs-keyword">between</span> <span class="hljs-operator"><</span>primer_día_mes_anterior<span class="hljs-operator">></span> <span class="hljs-keyword">AND</span> <span class="hljs-operator"><</span>último_día_mes_anterior<span class="hljs-operator">></span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>Si no tiene boleta:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-2"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"No tiene boleta de pago por lo tanto no se valida"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>---

### 6️⃣ Validar si el mes está habilitado para descarga

Consulta:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-select-name-from-%60ta"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-keyword">SELECT</span> name<span class="hljs-keyword">FROM</span> `tabEstado Boleta Mensual`<span class="hljs-keyword">WHERE</span> mes <span class="hljs-operator">=</span> <span class="hljs-operator"><</span>mes_texto<span class="hljs-operator">></span> <span class="hljs-keyword">AND</span> año <span class="hljs-operator">=</span> <span class="hljs-operator"><</span><span class="hljs-keyword">year</span><span class="hljs-operator">></span> <span class="hljs-keyword">AND</span> habilitado <span class="hljs-operator">=</span> <span class="hljs-number">1</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>Si está habilitado pero **el trabajador NO la descargó**, se bloquea:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-false%2C-%22"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">false</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Para poder registrar su marcación o realizar alguna solicitud, descargar su boleta pendiente del mes"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>---

### 7️⃣ Si pasa todas las validaciones → OK

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-3"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Se ha descargado la boleta de pago"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>---

# 📥 Request

**No usa body**, solo el parámetro de ruta: `<span class="hljs-symbol">empleado:</span> <span class="hljs-type">string</span>`

---

# 📤 Response – Ejemplos

### ✔ Caso permitido (día fuera de rango)

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-4"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"No está dentro del rango de fecha de validación"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>### ✔ Empleado en PreActivo

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-5"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"No validar descarga de boleta en PreActivo"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>### ✔ No tiene boleta generada

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-6"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"No tiene boleta de pago por lo tanto no se valida"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>### ❌ No ha descargado la boleta y es obligatoria

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-false%2C-%22-1"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">false</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Para poder registrar su marcación o realizar alguna solicitud, descargar su boleta pendiente del mes"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>### ✔ Todo correcto

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-7"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Se ha descargado la boleta de pago"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>---

# ❗ Posibles errores

<div class="_tableContainer_1rjym_1" id="bkmrk-error-descripci%C3%B3n-em"><div class="group _tableWrapper_1rjym_13 flex w-fit flex-col-reverse" tabindex="-1"><table class="w-fit min-w-(--thread-content-width)" data-end="4308" data-start="4013"><thead data-end="4036" data-start="4013"><tr data-end="4036" data-start="4013"><th data-col-size="sm" data-end="4021" data-start="4013">Error</th><th data-col-size="sm" data-end="4036" data-start="4021">Descripción</th></tr></thead><tbody data-end="4308" data-start="4060"><tr data-end="4107" data-start="4060"><td data-col-size="sm" data-end="4081" data-start="4060">Empleado no existe</td><td data-col-size="sm" data-end="4107" data-start="4081">No se encuentra en ERP</td></tr><tr data-end="4173" data-start="4108"><td data-col-size="sm" data-end="4135" data-start="4108">No tiene boleta generada</td><td data-col-size="sm" data-end="4173" data-start="4135">Salary Slip del mes anterior vacío</td></tr><tr data-end="4248" data-start="4174"><td data-col-size="sm" data-end="4213" data-start="4174">Boleta habilitada pero no descargada</td><td data-col-size="sm" data-end="4248" data-start="4213">Bloquea marcación y solicitudes</td></tr><tr data-end="4308" data-start="4249"><td data-col-size="sm" data-end="4272" data-start="4249">Error en ERP o MySQL</td><td data-col-size="sm" data-end="4308" data-start="4272">Respuesta capturada por el catch</td></tr></tbody></table>

</div></div>---

# 🧩 Tablas consultadas

### ERP (Frappe/ERPNext)

- `tabEmployee`
- `tabSalary Slip`
- `tabEstado Boleta Mensual`

### MySQL externo

- `historial_procesos_app`

---

# 🗃 Pseudocódigo del servicio

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-if-day-%3E-3%3A-return-o"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%; height: 29.6px;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr style="height: 29.6px;"><td style="height: 29.6px;">`<span class="hljs-keyword">if</span> day > <span class="hljs-number">3</span>:    <span class="hljs-keyword">return</span> OK (no validar)empleado = GET Employee<span class="hljs-keyword">if</span> empleado.status == PreActivo:    <span class="hljs-keyword">return</span> OK<span class="hljs-keyword">if</span> fecha_ingreso < ultimo_dia_mes_anterior:    verificar si ya descargó boleta en MySQL    verificar si tiene boleta en ERP    <span class="hljs-keyword">if</span> no tiene:        <span class="hljs-keyword">return</span> OK    verificar si mes habilitado    <span class="hljs-keyword">if</span> habilitado y no descargado:        bloquear<span class="hljs-keyword">return</span> OK`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>

# Obtiene descarga Renovación de contrato (2) - [getRenovacionContrato]

## 🧾 Descripción

*Valida si un empleado **debe descargar su renovación de contrato**, según reglas internas de fecha y estado en el ERP.*

Este servicio determina:

- Si hoy es la fecha válida para revisar renovaciones (solo a partir del día 26 de cada mes).
- Si el empleado ingresó antes del cierre del mes anterior (lo que lo vuelve candidato a renovación).
- Si el empleado tiene una solicitud de renovación aprobada y marcada como “Validado”.
- Si el empleado **ya descargó** su documento de renovación.
    
    
    - Caso contrario, se bloquean ciertas funcionalidades hasta que la descargue.

*Se combina información del **ERP** y del registro histórico en **MySQL2**.*

---

# 🚀 Endpoint

<span style="color: rgb(224, 62, 45);">GET /get-renovacion-contrato/{empleado}</span>

📌 *El parámetro <span style="color: rgb(224, 62, 45);">**`empleado`** </span>es obligatorio (ID del Employee en ERP).*

---

# 🔐 Seguridad

✔ Requiere autenticación interna vía <span style="color: rgb(224, 62, 45);">**`dbErp()`** </span>y tokens del ERP.  
✔ Acceso restringido a servicios del backend.

---

# 🧠 Flujo del Servicio (Resumen)

1. **Verifica la fecha actual.**
    
    
    - Si el día del mes es menor a 26 → No corresponde validar renovaciones.
2. **Obtiene datos del empleado.**
    
    <div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs">  
    </div></div></div><div class="overflow-y-auto p-4" dir="ltr">`<span class="hljs-keyword">SELECT</span> fecha_de_ingreso_real<span class="hljs-keyword">FROM</span> tabEmployee<span class="hljs-keyword">WHERE</span> <span class="hljs-type">name</span> = {empleado}`</div></div>
3. **Determina si el empleado aplica para renovación:**
    
    
    - Debe haber ingresado **antes del último día del mes anterior**.
4. **Busca renovaciones validadas del empleado:**
    
    <div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs">  
    </div></div></div><div class="overflow-y-auto p-4" dir="ltr">`<span class="hljs-keyword">FROM</span> tabSolicitud de Renovaciones doc<span class="hljs-keyword">JOIN</span> tabTrabajadores pendiete de renovar tab<span class="hljs-keyword">WHERE</span>  doc.data_12 <span class="hljs-operator">=</span> <span class="hljs-operator"><</span>mes_actual_texto<span class="hljs-operator">></span>  <span class="hljs-keyword">AND</span> doc.año <span class="hljs-operator">=</span> <span class="hljs-operator"><</span>año<span class="hljs-operator">></span>  <span class="hljs-keyword">AND</span> tab.codigo <span class="hljs-operator">=</span> empleado  <span class="hljs-keyword">AND</span> tab.renueva <span class="hljs-operator">=</span> "Si"  <span class="hljs-keyword">AND</span> doc.estado_de_documento <span class="hljs-operator">=</span> "Validado"`</div></div>
5. **Si existe una renovación validada:**
    
    
    - Consulta MySQL2 → tabla `historial_procesos_app`
    - Revisa si el usuario **ya descargó su renovación**:
        
        <div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs">  
        </div></div></div><div class="overflow-y-auto p-4" dir="ltr">`<span class="hljs-attr">proceso</span> = <span class="hljs-string">"descargaContratoRenovacion"</span>`</div></div>
6. **Si no la descargó → bloquea ciertas funciones.**
7. **Si todo está conforme → indica que la renovación fue descargada.**

---

# 📥 Request

### Parámetro de ruta

<div class="_tableContainer_1rjym_1" id="bkmrk-campo-tipo-obligator"><div class="group _tableWrapper_1rjym_13 flex w-fit flex-col-reverse" tabindex="-1"><table class="w-fit min-w-(--thread-content-width)" data-end="2425" data-start="2277"><thead data-end="2321" data-start="2277"><tr data-end="2321" data-start="2277"><th data-col-size="sm" data-end="2285" data-start="2277">Campo</th><th data-col-size="sm" data-end="2292" data-start="2285">Tipo</th><th data-col-size="sm" data-end="2306" data-start="2292">Obligatorio</th><th data-col-size="sm" data-end="2321" data-start="2306">Descripción</th></tr></thead><tbody data-end="2425" data-start="2367"><tr data-end="2425" data-start="2367"><td data-col-size="sm" data-end="2378" data-start="2367">empleado</td><td data-col-size="sm" data-end="2387" data-start="2378">string</td><td data-col-size="sm" data-end="2391" data-start="2387">✔</td><td data-col-size="sm" data-end="2425" data-start="2391">ID del Employee dentro del ERP</td></tr></tbody></table>

</div></div>No tiene body.

---

# 📤 Response 200 – Ejemplos

### ✔ Caso 1 — No es día de validación

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"No es el día correcto para la renovación de contrato"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>### ✔ Caso 2 — Debe descargar renovación (bloqueo)

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-false%2C-%22"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">false</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Para poder registrar su marcación o realizar alguna solicitud, descargar su renovación de contrato"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>### ✔ Caso 3 — Renovación descargada correctamente

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-1"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Se ha descargado el contrato de trabajo"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>### ✔ Caso 4 — Error controlado

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22status%22%3A-true%2C-%22m-2"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"status"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Se ha descargado el contrato de trabajo"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>---

# ❗ Posibles errores

<div class="_tableContainer_1rjym_1" id="bkmrk-c%C3%B3digo-significado-s"><div class="group _tableWrapper_1rjym_13 flex w-fit flex-col-reverse" tabindex="-1"><table class="w-fit min-w-(--thread-content-width)" data-end="3376" data-start="3095"><thead data-end="3119" data-start="3095"><tr data-end="3119" data-start="3095"><th data-col-size="sm" data-end="3104" data-start="3095">Código</th><th data-col-size="md" data-end="3119" data-start="3104">Significado</th></tr></thead><tbody data-end="3376" data-start="3145"><tr data-end="3219" data-start="3145"><td data-col-size="sm" data-end="3160" data-start="3145">status:false</td><td data-col-size="md" data-end="3219" data-start="3160">El empleado tiene renovación pendiente y no la descargó</td></tr><tr data-end="3287" data-start="3220"><td data-col-size="sm" data-end="3234" data-start="3220">status:true</td><td data-col-size="md" data-end="3287" data-start="3234">No aplica validación o ya cumplió con la descarga</td></tr><tr data-end="3376" data-start="3288"><td data-col-size="sm" data-end="3300" data-start="3288">Excepción</td><td data-col-size="md" data-end="3376" data-start="3300">Se devuelve un mensaje genérico indicando que el contrato fue descargado</td></tr></tbody></table>

</div></div>---

# 📚 Tablas / Datos utilizados

### ERP - `tabEmployee`

Campos usados:

- `fecha_de_ingreso_real`

### ERP - `tabSolicitud de Renovaciones`

Campos usados:

- `data_12`
- `año`
- `estado_de_documento`

### ERP - `tabTrabajadores pendiete de renovar`

Campos usados:

- `codigo`
- `renueva`

### MySQL2 - tabla `historial_procesos_app`

Procesos revisados:

- `descargaContratoRenovacion`

---

# 🗃 Lógica en Pseudo-Código

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-if-day%28today%29-%3C-26%3A-"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%; height: 29.6px;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr style="height: 29.6px;"><td style="height: 29.6px;">`<span class="hljs-keyword">if</span> day(today) < <span class="hljs-number">26</span>:    <span class="hljs-keyword">return</span> OK(<span class="hljs-string">"No es el día correcto"</span>)empleado = queryERP(Employee <span class="hljs-keyword">where</span> name=empleado)<span class="hljs-keyword">if</span> empleado.ingreso < ultimo_dia_mes_anterior:    renov = queryERP(Solicitud de Renovaciones <span class="hljs-keyword">where</span>         codigo=empleado AND renueva=<span class="hljs-string">"Si"</span> AND estado=<span class="hljs-string">"Validado"</span>    )    <span class="hljs-keyword">if</span> renov exists:        registro = queryMySQL(historial_procesos <span class="hljs-keyword">where</span> proceso=<span class="hljs-string">"descargaContratoRenovacion"</span>)        <span class="hljs-keyword">if</span> registro vacío:            <span class="hljs-keyword">return</span> ERROR(<span class="hljs-string">"Debe descargar la renovación"</span>)<span class="hljs-keyword">return</span> OK(<span class="hljs-string">"Se ha descargado el contrato de trabajo"</span>)`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr"></div></div>

# Lista de Asistencias (1) - [getMarkingsApp]

## 🧾 Descripción

*Este servicio obtiene y consolida **todas las asistencias** de un empleado en un mes específico, calculando:*

- Porcentaje de asistencia del mes.
- Total de días asistidos.
- Permisos.
- Faltas.
- Feriados.
- Días de descanso.
- Marcaciones incompletas.
- Fechas únicas de asistencia.

Además, toma en cuenta:

- Fecha de ingreso del trabajador (para no contar días previos como faltas).
- Domingos y feriados declarados en *holidays.json*.
- Validación de límites según el mes actual.

*Es un endpoint fundamental para el módulo de **Control de Asistencias** dentro del aplicativo.*

---

# 🚀 Endpoint

### **POST /get-markings-app**

📥 Requiere parámetros obligatorios en el body:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22employee%22%3A-%22emp-0"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"employee"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"EMP-0001"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"month"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"02"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"anio"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"2025"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"fechaIngreso"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"2024-10-15"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>---

# 🔐 Seguridad

Requiere autenticación interna del sistema ERP mediante:

- `dbErp()` para consultas SQL internas.
- Acceso a archivo local `/public/recursos_humanos/holidays.json`.

---

# 🧠 Flujo del Servicio (resumen real)

1. **Recibe parámetros del empleado y mes a consultar.**
    
    employee, month, anio, fechaIngreso
2. **Calcula rango real del mes a evaluar**, tomando en cuenta:
    
    
    - Si es el mes actual.
    - Si el empleado ingresó después del día 1.
    - Días previos al ingreso del trabajador.
3. **Carga feriados y domingos del archivo JSON:**
    
    `/public/recursos_humanos/holidays.json`
4. **Determina cuántos días del mes son feriados o domingos dentro del rango permitido.**
5. **Valida campos obligatorios.**
6. **Consulta en el ERP todas las asistencias del empleado en el mes:**

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-from-tabattendance-w"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-keyword">FROM</span> tabAttendance<span class="hljs-keyword">WHERE</span> employee <span class="hljs-operator">=</span> <span class="hljs-operator"><</span>empleado<span class="hljs-operator">></span><span class="hljs-keyword">AND</span> attendance_date <span class="hljs-keyword">BETWEEN</span> <span class="hljs-number">1</span> y último día del mes<span class="hljs-keyword">AND</span> status <span class="hljs-keyword">IN</span> (<span class="hljs-string">'Present'</span>,<span class="hljs-string">'Marcacion Incompleta'</span>,<span class="hljs-string">'On Leave'</span>,<span class="hljs-string">'Absent'</span>,<span class="hljs-string">'Día de Descanso'</span>,<span class="hljs-string">'Feriado'</span>)`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>7. **Recorre todas las asistencias y clasifica:**
    
    
    - Present → Suma asistencia
    - On Leave → Permisos
    - Absent → Faltas
    - Feriado → Feriados
    - Día de Descanso → Descansos
    - Marcacion Incompleta → Marcaciones incompletas
8. **Calcula porcentaje de asistencia**, considerando:
    
    
    - Días previos al ingreso.
    - Si el mes es el actual → hasta el día de hoy.
    - Casos especiales de permisos dominicales.
9. **Construye respuesta final con totales y fechas.**

---

# 📥 Request Body

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22employee%22%3A-%22emp-0-1"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"employee"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"EMP-0001"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"month"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"03"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"anio"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"2025"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"fechaIngreso"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"2024-10-10"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>📌 **Todos son obligatorios.**

---

# 📤 Response 200 – Ejemplo

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22valor%22%3A-true%2C-%22ms"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"valor"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"LISTA DE ASISTENCIAS"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"data"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">{</span>    <span class="hljs-attr">"porcentage"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"92.55"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_aistidos"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"25"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_totales"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"27"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"permisos"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"1"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"faltas"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"0"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"marcacion_incompleta"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"1"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"fechas_asistidas"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span>      <span class="hljs-string">"2025-03-01"</span><span class="hljs-punctuation">,</span>      <span class="hljs-string">"2025-03-02"</span><span class="hljs-punctuation">,</span>      <span class="hljs-string">"2025-03-03"</span>    <span class="hljs-punctuation">]</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"feriados"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"1"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"descansos"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"4"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_permisos"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span>      <span class="hljs-string">"2025-03-08"</span>    <span class="hljs-punctuation">]</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_tardanzas"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span>      <span class="hljs-string">"2025-03-15"</span>    <span class="hljs-punctuation">]</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_faltas"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span><span class="hljs-punctuation">]</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_feriados"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span>      <span class="hljs-string">"2025-03-29"</span>    <span class="hljs-punctuation">]</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_descansos"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span>      <span class="hljs-string">"2025-03-02"</span><span class="hljs-punctuation">,</span>      <span class="hljs-string">"2025-03-09"</span>    <span class="hljs-punctuation">]</span>  <span class="hljs-punctuation">}</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>---

# ❗ Posibles Errores

### 1. Faltan parámetros obligatorios

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22valor%22%3A-false%2C-%22m"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"valor"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">false</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Complete todos los campos"</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>### 2. No existe asistencia registrada

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22valor%22%3A-true%2C-%22ms-1"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"valor"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">true</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"LISTA DE ASISTENCIAS"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"data"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">{</span>    <span class="hljs-attr">"porcentage"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"0"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_asistidos"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"0"</span><span class="hljs-punctuation">,</span>    <span class="hljs-attr">"dias_totales"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"0"</span><span class="hljs-punctuation">,</span>    ...  <span class="hljs-punctuation">}</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>### 3. Error interno inesperado

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22valor%22%3A-false%2C-%22m-1"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"valor"</span><span class="hljs-punctuation">:</span> <span class="hljs-literal"><span class="hljs-keyword">false</span></span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"msn"</span><span class="hljs-punctuation">:</span> <span class="hljs-string">"Error inesperado en el servicio"</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"data"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span><span class="hljs-punctuation">]</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>---

# 📚 Estructuras usadas

### **Attendance (tabAttendance)**

Campos consultados:

- `attendance_date`
- `status`
- `horas_trabajadas`
- `horas_extras`
- `name`

### **Archivo holidays.json**

Estructura:

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-%7B-%22sunday%22%3A-%5B%222025-0"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`<span class="hljs-punctuation">{</span>  <span class="hljs-attr">"Sunday"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span><span class="hljs-string">"2025-03-02"</span><span class="hljs-punctuation">,</span> <span class="hljs-string">"2025-03-09"</span><span class="hljs-punctuation">]</span><span class="hljs-punctuation">,</span>  <span class="hljs-attr">"Holidays"</span><span class="hljs-punctuation">:</span> <span class="hljs-punctuation">[</span><span class="hljs-string">"2025-03-29"</span><span class="hljs-punctuation">]</span><span class="hljs-punctuation">}</span>`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>---

# 🧩 Lógica en pseudo-código

<div class="contain-inline-size rounded-2xl relative bg-token-sidebar-surface-primary" id="bkmrk-input%3A-employee%2C-mon"><div class="sticky top-9"><div class="absolute end-0 bottom-0 flex h-9 items-center pe-2"><div class="bg-token-bg-elevated-secondary text-token-text-secondary flex items-center gap-4 rounded-sm px-2 font-sans text-xs"><table border="1" style="border-collapse: collapse; width: 100%;"><colgroup><col style="width: 99.881%;"></col></colgroup><tbody><tr><td>`input: employee, month, anio, fechaIngresovalidar campos requeridoscalcular fecha_inicio y fecha_fin según:    - mes actual    - fecha de ingreso del empleadocargar feriados y domingos (holidays.json)contar días dentro del rangoconsultar asistencias en ERP:    SELECT attendance_date, status    FROM tabAttendance    WHERE employee = employee    AND status IN (...)inicializar contadoresforeach asistencia in resultado:    clasificar según status    acumular días, permisos, faltas, descansos, feriadoscalcular porcentaje de asistenciareturn {    valor: true,    data: {...}}`</td></tr></tbody></table>

</div></div></div><div class="overflow-y-auto p-4" dir="ltr">  
</div></div>