Add xlsx support and enhance Trabajadores module with file upload functionality
- Updated package.json and package-lock.json to include xlsx dependency. - Enhanced AlumnosService to return UsuarioData type. - Modified CuestionarioRespondidoService to include event start and end dates in responses. - Updated TrabajadoresController to add file upload endpoint for processing Excel files. - Implemented file processing logic in TrabajadoresService to handle worker registration from Excel. - Created TrabajadorApiDocumentation for API documentation of the new file upload feature. - Refactored RegistroTrabajador entity to include carrera field and changed num_trabajador type.
This commit is contained in:
Generated
+105
-1
@@ -33,7 +33,8 @@
|
||||
"qrcode": "^1.5.4",
|
||||
"reflect-metadata": "^0.2.2",
|
||||
"rxjs": "^7.8.1",
|
||||
"typeorm": "^0.3.21"
|
||||
"typeorm": "^0.3.21",
|
||||
"xlsx": "^0.18.5"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@eslint/eslintrc": "^3.2.0",
|
||||
@@ -4085,6 +4086,15 @@
|
||||
"node": ">=0.4.0"
|
||||
}
|
||||
},
|
||||
"node_modules/adler-32": {
|
||||
"version": "1.3.1",
|
||||
"resolved": "https://registry.npmjs.org/adler-32/-/adler-32-1.3.1.tgz",
|
||||
"integrity": "sha512-ynZ4w/nUUv5rrsR8UUGoe1VC9hZj6V5hU9Qw1HlMDJGEJw5S7TfTErWTjMys6M7vr0YWcPqs3qAr4ss0nDfP+A==",
|
||||
"license": "Apache-2.0",
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/ajv": {
|
||||
"version": "6.12.6",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
|
||||
@@ -4870,6 +4880,19 @@
|
||||
],
|
||||
"license": "CC-BY-4.0"
|
||||
},
|
||||
"node_modules/cfb": {
|
||||
"version": "1.2.2",
|
||||
"resolved": "https://registry.npmjs.org/cfb/-/cfb-1.2.2.tgz",
|
||||
"integrity": "sha512-KfdUZsSOw19/ObEWasvBP/Ac4reZvAGauZhs6S/gqNhXhI7cKwvlH7ulj+dOEYnca4bm4SGo8C1bTAQvnTjgQA==",
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
"adler-32": "~1.3.0",
|
||||
"crc-32": "~1.2.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/chalk": {
|
||||
"version": "4.1.2",
|
||||
"resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz",
|
||||
@@ -5095,6 +5118,15 @@
|
||||
"node": ">= 0.12.0"
|
||||
}
|
||||
},
|
||||
"node_modules/codepage": {
|
||||
"version": "1.15.0",
|
||||
"resolved": "https://registry.npmjs.org/codepage/-/codepage-1.15.0.tgz",
|
||||
"integrity": "sha512-3g6NUTPd/YtuuGrhMnOMRjFc+LJw/bnMp3+0r/Wcz3IXUuCosKRJvMphm5+Q+bvTVGcJJuRvVLuYba+WojaFaA==",
|
||||
"license": "Apache-2.0",
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/collect-v8-coverage": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.2.tgz",
|
||||
@@ -5300,6 +5332,18 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"node_modules/crc-32": {
|
||||
"version": "1.2.2",
|
||||
"resolved": "https://registry.npmjs.org/crc-32/-/crc-32-1.2.2.tgz",
|
||||
"integrity": "sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ==",
|
||||
"license": "Apache-2.0",
|
||||
"bin": {
|
||||
"crc32": "bin/crc32.njs"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/create-jest": {
|
||||
"version": "29.7.0",
|
||||
"resolved": "https://registry.npmjs.org/create-jest/-/create-jest-29.7.0.tgz",
|
||||
@@ -6697,6 +6741,15 @@
|
||||
"node": ">= 0.6"
|
||||
}
|
||||
},
|
||||
"node_modules/frac": {
|
||||
"version": "1.1.2",
|
||||
"resolved": "https://registry.npmjs.org/frac/-/frac-1.1.2.tgz",
|
||||
"integrity": "sha512-w/XBfkibaTl3YDqASwfDUqkna4Z2p9cFSr1aHDt0WoMTECnRfBOv2WArlZILlqgWlmdIlALXGpM2AOhEk5W3IA==",
|
||||
"license": "Apache-2.0",
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/fresh": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/fresh/-/fresh-2.0.0.tgz",
|
||||
@@ -10536,6 +10589,18 @@
|
||||
"node": ">= 0.6"
|
||||
}
|
||||
},
|
||||
"node_modules/ssf": {
|
||||
"version": "0.11.2",
|
||||
"resolved": "https://registry.npmjs.org/ssf/-/ssf-0.11.2.tgz",
|
||||
"integrity": "sha512-+idbmIXoYET47hH+d7dfm2epdOMUDjqcB4648sTZ+t2JwoyBFL/insLfB/racrDmsKB3diwsDA696pZMieAC5g==",
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
"frac": "~1.1.2"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/stack-utils": {
|
||||
"version": "2.0.6",
|
||||
"resolved": "https://registry.npmjs.org/stack-utils/-/stack-utils-2.0.6.tgz",
|
||||
@@ -12126,6 +12191,24 @@
|
||||
"integrity": "sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==",
|
||||
"license": "ISC"
|
||||
},
|
||||
"node_modules/wmf": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/wmf/-/wmf-1.0.2.tgz",
|
||||
"integrity": "sha512-/p9K7bEh0Dj6WbXg4JG0xvLQmIadrner1bi45VMJTfnbVHsc7yIajZyoSoK60/dtVBs12Fm6WkUI5/3WAVsNMw==",
|
||||
"license": "Apache-2.0",
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/word": {
|
||||
"version": "0.3.0",
|
||||
"resolved": "https://registry.npmjs.org/word/-/word-0.3.0.tgz",
|
||||
"integrity": "sha512-OELeY0Q61OXpdUfTp+oweA/vtLVg5VDOXh+3he3PNzLGG/y0oylSOC1xRVj0+l4vQ3tj/bB1HVHv1ocXkQceFA==",
|
||||
"license": "Apache-2.0",
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/word-wrap": {
|
||||
"version": "1.2.5",
|
||||
"resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.5.tgz",
|
||||
@@ -12237,6 +12320,27 @@
|
||||
"dev": true,
|
||||
"license": "ISC"
|
||||
},
|
||||
"node_modules/xlsx": {
|
||||
"version": "0.18.5",
|
||||
"resolved": "https://registry.npmjs.org/xlsx/-/xlsx-0.18.5.tgz",
|
||||
"integrity": "sha512-dmg3LCjBPHZnQp5/F/+nnTa+miPJxUXB6vtk42YjBBKayDNagxGEeIdWApkYPOf3Z3pm3k62Knjzp7lMeTEtFQ==",
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
"adler-32": "~1.3.0",
|
||||
"cfb": "~1.2.1",
|
||||
"codepage": "~1.15.0",
|
||||
"crc-32": "~1.2.1",
|
||||
"ssf": "~0.11.2",
|
||||
"wmf": "~1.0.1",
|
||||
"word": "~0.3.0"
|
||||
},
|
||||
"bin": {
|
||||
"xlsx": "bin/xlsx.njs"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/xtend": {
|
||||
"version": "4.0.2",
|
||||
"resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz",
|
||||
|
||||
+2
-1
@@ -44,7 +44,8 @@
|
||||
"qrcode": "^1.5.4",
|
||||
"reflect-metadata": "^0.2.2",
|
||||
"rxjs": "^7.8.1",
|
||||
"typeorm": "^0.3.21"
|
||||
"typeorm": "^0.3.21",
|
||||
"xlsx": "^0.18.5"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@eslint/eslintrc": "^3.2.0",
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { Controller, Get, Param, NotFoundException } from '@nestjs/common';
|
||||
import { AlumnosService } from './alumnos.service';
|
||||
import { AlumnosService, UsuarioData } from './alumnos.service';
|
||||
import { ApiTags, ApiOperation, ApiParam, ApiResponse } from '@nestjs/swagger';
|
||||
import { AlumnoDto, ALUMNO_RESPONSES } from './alumnos.documentation';
|
||||
|
||||
@@ -14,7 +14,7 @@ export class AlumnosController {
|
||||
@ApiResponse(ALUMNO_RESPONSES[200])
|
||||
@ApiResponse(ALUMNO_RESPONSES[404])
|
||||
@ApiResponse(ALUMNO_RESPONSES[500])
|
||||
async getAlumnoByCuenta(@Param('cuenta') cuenta: string): Promise<AlumnoDto | null> {
|
||||
async getAlumnoByCuenta(@Param('cuenta') cuenta: string): Promise<UsuarioData | null> {
|
||||
const alumno = await this.alumnosService.findByCuenta(cuenta);
|
||||
if (!alumno) {
|
||||
throw new NotFoundException(`No se encontró alumno con número de cuenta ${cuenta}`);
|
||||
|
||||
@@ -3,6 +3,15 @@ import { InjectRepository } from '@nestjs/typeorm';
|
||||
import { Repository } from 'typeorm';
|
||||
import { RegistroAlumno } from './entities/registro-alumno.entity';
|
||||
|
||||
export type UsuarioData = {
|
||||
cuenta: string | null;
|
||||
nombre: string | null;
|
||||
apellidos: string | null;
|
||||
carrera: string | null;
|
||||
genero: string | null;
|
||||
rfc?: string | null; // Solo para trabajadores
|
||||
}
|
||||
|
||||
@Injectable()
|
||||
export class AlumnosService {
|
||||
constructor(
|
||||
@@ -10,9 +19,17 @@ export class AlumnosService {
|
||||
private registroAlumnoRepository: Repository<RegistroAlumno>,
|
||||
) {}
|
||||
|
||||
async findByCuenta(cuenta: string): Promise<RegistroAlumno | null> {
|
||||
return this.registroAlumnoRepository.findOne({
|
||||
async findByCuenta(cuenta: string): Promise<UsuarioData | null> {
|
||||
const alumno = await this.registroAlumnoRepository.findOne({
|
||||
where: { id_ncuenta: parseInt(cuenta, 10) },
|
||||
});
|
||||
|
||||
return {
|
||||
cuenta: alumno?.id_ncuenta.toString() || null,
|
||||
nombre: alumno?.nombre || null,
|
||||
apellidos: alumno?.apellidos || null,
|
||||
carrera: alumno?.carrera || null,
|
||||
genero: alumno?.genero || null,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -261,6 +261,12 @@ export class CuestionarioRespondidoService {
|
||||
nombreEvento: cuestionario.evento?.nombre_evento,
|
||||
correo: participante.correo,
|
||||
fechaRegistro: new Date().toLocaleString(),
|
||||
fechaInicioEvento: cuestionario.evento?.fecha_inicio
|
||||
? new Date(cuestionario.evento.fecha_inicio).toLocaleString()
|
||||
: undefined,
|
||||
fechaFinEvento: cuestionario.evento?.fecha_fin
|
||||
? new Date(cuestionario.evento.fecha_fin).toLocaleString()
|
||||
: undefined,
|
||||
}),
|
||||
adjuntos: [
|
||||
{
|
||||
|
||||
@@ -3,12 +3,27 @@ export function generarHtmlCorreoAsistencia({
|
||||
nombreEvento,
|
||||
correo,
|
||||
fechaRegistro,
|
||||
fechaInicioEvento,
|
||||
fechaFinEvento,
|
||||
}: {
|
||||
nombreForm: string;
|
||||
nombreEvento: string;
|
||||
correo: string;
|
||||
fechaRegistro: string;
|
||||
fechaInicioEvento?: string;
|
||||
fechaFinEvento?: string;
|
||||
}) {
|
||||
const horarioEvento = fechaInicioEvento && fechaFinEvento
|
||||
? `
|
||||
<div style="margin: 20px 0; padding: 12px; background-color: #e8f0fe; border-left: 4px solid #003d79;">
|
||||
<p style="margin: 0; font-size: 15px; color: #003d79;">
|
||||
<strong>🕒 Horario del evento:</strong><br/>
|
||||
${fechaInicioEvento} <strong>al</strong> ${fechaFinEvento}
|
||||
</p>
|
||||
</div>
|
||||
`
|
||||
: '';
|
||||
|
||||
return `
|
||||
<div style="font-family: Arial, sans-serif; max-width: 600px; margin: 0 auto; padding: 24px; border: 1px solid #ccc; border-radius: 8px; background-color: #f9f9f9;">
|
||||
<h1 style="color: #003d79; border-bottom: 2px solid #003d79; padding-bottom: 10px;">🎓 ¡Gracias por registrarte!</h1>
|
||||
@@ -32,6 +47,8 @@ export function generarHtmlCorreoAsistencia({
|
||||
<li><strong>Fecha de registro:</strong> ${fechaRegistro}</li>
|
||||
</ul>
|
||||
|
||||
${horarioEvento}
|
||||
|
||||
<p style="margin-top: 30px; font-size: 14px; color: #666;">
|
||||
Si tienes alguna duda, acude al módulo de información durante el evento.
|
||||
</p>
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
import { applyDecorators } from '@nestjs/common';
|
||||
import {
|
||||
ApiTags,
|
||||
ApiOperation,
|
||||
ApiConsumes,
|
||||
ApiBody,
|
||||
} from '@nestjs/swagger';
|
||||
|
||||
export class TrabajadorApiDocumentation {
|
||||
static ApiController = ApiTags('Trabajador');
|
||||
|
||||
static ApiCargarArchivo = applyDecorators(
|
||||
ApiOperation({ summary: 'Cargar archivo Excel con trabajadores' }),
|
||||
ApiConsumes('multipart/form-data'),
|
||||
ApiBody({
|
||||
description: 'Archivo Excel (.xls o .xlsx) con columnas: rfc, num_empleado, nombre, adscripcion, correo, AP1, AP2, Nombres, sexo',
|
||||
schema: {
|
||||
type: 'object',
|
||||
properties: {
|
||||
file: {
|
||||
type: 'string',
|
||||
format: 'binary',
|
||||
description: 'Archivo Excel con trabajadores a registrar',
|
||||
},
|
||||
},
|
||||
required: ['file'],
|
||||
},
|
||||
}),
|
||||
);
|
||||
}
|
||||
@@ -5,8 +5,8 @@ export class RegistroTrabajador {
|
||||
@PrimaryGeneratedColumn()
|
||||
id_trabajador: number;
|
||||
|
||||
@Column({ type: 'varchar', length: 20, unique: true, nullable: true })
|
||||
numero_trabajador: string;
|
||||
@Column({ type: 'int', unique: true, nullable: true })
|
||||
num_trabajador: number;
|
||||
|
||||
@Column({ type: 'varchar', length: 13, unique: true })
|
||||
rfc: string;
|
||||
@@ -19,4 +19,7 @@ export class RegistroTrabajador {
|
||||
|
||||
@Column({ type: 'char', length: 1 })
|
||||
genero: string;
|
||||
|
||||
@Column({ type: 'varchar', length: 100 })
|
||||
carrera: string;
|
||||
}
|
||||
|
||||
@@ -1,29 +1,64 @@
|
||||
import { Controller, Get, Post, Body, Patch, Param, Delete } from '@nestjs/common';
|
||||
import {
|
||||
Controller,
|
||||
Get,
|
||||
Post,
|
||||
Body,
|
||||
Patch,
|
||||
Param,
|
||||
Delete,
|
||||
UseInterceptors,
|
||||
UploadedFile,
|
||||
NotFoundException,
|
||||
} from '@nestjs/common';
|
||||
import { TrabajadoresService } from './trabajadores.service';
|
||||
import { CreateTrabajadoreDto } from './dto/create-trabajadore.dto';
|
||||
import { UpdateTrabajadoreDto } from './dto/update-trabajadore.dto';
|
||||
import { FileInterceptor } from '@nestjs/platform-express';
|
||||
import { diskStorage } from 'multer';
|
||||
import { extname } from 'path';
|
||||
import { TrabajadorApiDocumentation } from './docs/trabajadores.docs';
|
||||
|
||||
@Controller('trabajadores')
|
||||
@TrabajadorApiDocumentation.ApiController
|
||||
export class TrabajadoresController {
|
||||
constructor(private readonly trabajadoresService: TrabajadoresService) {}
|
||||
|
||||
@Post('cargar')
|
||||
@TrabajadorApiDocumentation.ApiCargarArchivo
|
||||
@UseInterceptors(
|
||||
FileInterceptor('file', {
|
||||
storage: diskStorage({
|
||||
destination: './uploads',
|
||||
filename: (_, file, callback) => {
|
||||
const uniqueName = `${Date.now()}${extname(file.originalname)}`;
|
||||
callback(null, uniqueName);
|
||||
},
|
||||
}),
|
||||
}),
|
||||
)
|
||||
async cargarArchivo(@UploadedFile() file: Express.Multer.File) {
|
||||
return this.trabajadoresService.procesarArchivo(file.path);
|
||||
}
|
||||
|
||||
@Post()
|
||||
create(@Body() createTrabajadoreDto: CreateTrabajadoreDto) {
|
||||
return this.trabajadoresService.create(createTrabajadoreDto);
|
||||
}
|
||||
|
||||
@Get()
|
||||
findAll() {
|
||||
return this.trabajadoresService.findAll();
|
||||
}
|
||||
|
||||
@Get(':id')
|
||||
findOne(@Param('id') id: string) {
|
||||
return this.trabajadoresService.findOne(+id);
|
||||
@Get(':rfc')
|
||||
findByRfc(@Param('rfc') rfc: string) {
|
||||
const trabajador = this.trabajadoresService.findByRfc(rfc);
|
||||
if (!trabajador) {
|
||||
throw new NotFoundException(`No se encontró trabajador con RFC ${rfc}`);
|
||||
}
|
||||
return trabajador;
|
||||
}
|
||||
|
||||
@Patch(':id')
|
||||
update(@Param('id') id: string, @Body() updateTrabajadoreDto: UpdateTrabajadoreDto) {
|
||||
update(
|
||||
@Param('id') id: string,
|
||||
@Body() updateTrabajadoreDto: UpdateTrabajadoreDto,
|
||||
) {
|
||||
return this.trabajadoresService.update(+id, updateTrabajadoreDto);
|
||||
}
|
||||
|
||||
|
||||
@@ -5,9 +5,11 @@ import { TypeOrmModule } from '@nestjs/typeorm';
|
||||
import { RegistroTrabajador } from './entities/trabajadore.entity';
|
||||
|
||||
@Module({
|
||||
imports: [TypeOrmModule.forFeature([RegistroTrabajador], 'alumnosConnection')],
|
||||
|
||||
imports: [
|
||||
TypeOrmModule.forFeature([RegistroTrabajador], 'alumnosConnection'),
|
||||
],
|
||||
controllers: [TrabajadoresController],
|
||||
providers: [TrabajadoresService],
|
||||
exports: [TrabajadoresService],
|
||||
})
|
||||
export class TrabajadoresModule {}
|
||||
|
||||
@@ -1,9 +1,91 @@
|
||||
import { Injectable } from '@nestjs/common';
|
||||
import { CreateTrabajadoreDto } from './dto/create-trabajadore.dto';
|
||||
import { UpdateTrabajadoreDto } from './dto/update-trabajadore.dto';
|
||||
import { InjectRepository } from '@nestjs/typeorm';
|
||||
import { RegistroTrabajador } from './entities/trabajadore.entity';
|
||||
import { Repository } from 'typeorm';
|
||||
import * as fs from 'fs';
|
||||
import * as XLSX from 'xlsx';
|
||||
import { UsuarioData } from 'src/alumnos/alumnos.service';
|
||||
|
||||
@Injectable()
|
||||
export class TrabajadoresService {
|
||||
constructor(
|
||||
@InjectRepository(RegistroTrabajador, 'alumnosConnection')
|
||||
private readonly trabajadorRepo: Repository<RegistroTrabajador>,
|
||||
) {}
|
||||
|
||||
async procesarArchivo(
|
||||
filePath: string,
|
||||
): Promise<{ insertados: number; omitidos: number }> {
|
||||
const workbook = XLSX.readFile(filePath);
|
||||
const sheetName = workbook.SheetNames[0];
|
||||
const data: any[] = XLSX.utils.sheet_to_json(workbook.Sheets[sheetName]);
|
||||
|
||||
let insertados = 0;
|
||||
let omitidos = 0;
|
||||
|
||||
for (const row of data) {
|
||||
const rfc = (row['rfc'] || '').trim();
|
||||
|
||||
if (!rfc) {
|
||||
omitidos++;
|
||||
continue; // RFC es obligatorio
|
||||
}
|
||||
|
||||
const numTrabajadorRaw = row['num_empleado'];
|
||||
const numTrabajador = Number.isFinite(Number(numTrabajadorRaw))
|
||||
? Number(numTrabajadorRaw)
|
||||
: undefined;
|
||||
|
||||
const where: any[] = [{ rfc }];
|
||||
if (numTrabajador !== undefined) {
|
||||
where.push({ num_trabajador: numTrabajador });
|
||||
}
|
||||
|
||||
const existe = await this.trabajadorRepo.findOne({ where });
|
||||
|
||||
if (existe) {
|
||||
omitidos++;
|
||||
continue;
|
||||
}
|
||||
|
||||
const nuevo = this.trabajadorRepo.create({
|
||||
rfc,
|
||||
num_trabajador: numTrabajador,
|
||||
nombre: (row['Nombres'] || '').trim(),
|
||||
apellidos:
|
||||
`${(row['AP1'] || '').trim()} ${(row['AP2'] || '').trim()}`.trim(),
|
||||
genero: (row['sexo'] || '').trim().substring(0, 1).toUpperCase(),
|
||||
carrera: (row['adscripcion'] || '').trim(),
|
||||
});
|
||||
|
||||
await this.trabajadorRepo.save(nuevo);
|
||||
insertados++;
|
||||
}
|
||||
|
||||
fs.unlinkSync(filePath); // Limpia archivo temporal
|
||||
|
||||
return { insertados, omitidos };
|
||||
}
|
||||
|
||||
async findByRfc(rfc: string): Promise<UsuarioData | null> {
|
||||
const trabajador = await this.trabajadorRepo.findOne({
|
||||
where: { rfc: rfc.trim().toUpperCase() },
|
||||
});
|
||||
|
||||
return {
|
||||
cuenta: trabajador?.num_trabajador?.toString() || null,
|
||||
nombre: trabajador?.nombre || null,
|
||||
apellidos: trabajador
|
||||
? `${trabajador.apellidos}`.trim()
|
||||
: null,
|
||||
carrera: trabajador?.carrera || null,
|
||||
genero: trabajador?.genero || null,
|
||||
rfc: trabajador?.rfc || null, // Incluye RFC en el retorno
|
||||
}
|
||||
}
|
||||
|
||||
create(createTrabajadoreDto: CreateTrabajadoreDto) {
|
||||
return 'This action adds a new trabajadore';
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user