diff --git a/src/dto/numero-inventario.dto.ts b/src/dto/numero-inventario.dto.ts index 055ee31..5519c88 100644 --- a/src/dto/numero-inventario.dto.ts +++ b/src/dto/numero-inventario.dto.ts @@ -1,9 +1,6 @@ import { IsNumberString, IsString } from 'class-validator'; export class NumeroInventarioDto { - @IsNumberString() - id_institucion: string; - @IsString() numero_inventario: string; } diff --git a/src/equipo/equipo.controller.ts b/src/equipo/equipo.controller.ts index 6c8c6a1..4421e7a 100644 --- a/src/equipo/equipo.controller.ts +++ b/src/equipo/equipo.controller.ts @@ -43,11 +43,6 @@ export class EquipoController { 'Endpoint que retorna la información de un equipo por su número de inventario de una institución.', }) @ApiBearerAuth('jwt') - @ApiQuery({ - description: 'Id de la institución.', - name: 'id_institucion', - type: 'string', - }) @ApiQuery({ description: 'El número de inventario del equipo que se busca.', name: 'numero_inventario', @@ -58,10 +53,7 @@ export class EquipoController { this.validarUsuarioService.validarAdminOperador(operador); return this.equipoService - .findFullInfoByNumeroInventario( - parseInt(query.id_institucion), - query.numero_inventario, - ) + .findFullInfoByNumeroInventario(operador, query.numero_inventario) .then((equipo) => { if ( operador.tipoUsuario.id_tipo_usuario > 2 && diff --git a/src/equipo/equipo.service.ts b/src/equipo/equipo.service.ts index a961ba6..f885cb5 100644 --- a/src/equipo/equipo.service.ts +++ b/src/equipo/equipo.service.ts @@ -316,86 +316,77 @@ export class EquipoService { busquedaReseteo.id_tipo_entrada = tipoEntrada.id_tipo_entrada; } // Busaca un equipo - return ( - this.informacionEquipoPrestamoView - .findOne({ where: busqueda }) - .then((infoEquipo) => { - // Si no hay uno busca a todos los quipos que cumplan las mismas - // condiciones pero que ya hayan sido prestados - if (!infoEquipo) - return this.informacionEquipoPrestamoView - .find({ where: busquedaReseteo }) - .then(async (infoEquipos) => { - // Los pasamos a no prestados para resetear los equipos - for (let i = 0; i < infoEquipos.length; i++) - await this.repository.save( - this.repository.create({ - id_equipo: infoEquipos[i].id_equipo, - prestado: false, - }), - ); - // Trata de buscar otro - return this.informacionEquipoPrestamoView.findOne({ - where: busqueda, - }); - }) - .then((infoEquipo) => { - // Si no hay saca error - if (!infoEquipo) - throw new ConflictException( - 'No hay un equipo de cómputo que cumpla con las caracteríasticas solicitadas o ya no hay equipos disponibles en este momento. Intenta más tarde o cambia las características.', - ); - return infoEquipo; + return this.informacionEquipoPrestamoView + .findOne({ where: busqueda }) + .then(async (infoEquipo) => { + // Si no hay uno busca a todos los quipos que cumplan las mismas + // condiciones pero que ya hayan sido prestados + if (!infoEquipo) + await this.informacionEquipoPrestamoView + .find({ where: busquedaReseteo }) + .then(async (infoEquipos) => { + // Los pasamos a no prestados para resetear los equipos + for (let i = 0; i < infoEquipos.length; i++) + await this.repository.save( + this.repository.create({ + id_equipo: infoEquipos[i].id_equipo, + prestado: false, + }), + ); + // Trata de buscar otro + return this.informacionEquipoPrestamoView.findOne({ + where: busqueda, }); - return infoEquipo; - }) - .then((infoEquipo) => { - // Esta variable debe estar siempre en null antes de asignar el equipo - if (infoEquipo.u) - throw new ConflictException( - 'Ocurrio un error al tratar de asignarte un equipo de cómputo, intenta de nuevo.', - ); - // Actualizo el status del equipo a apartado y gurado el id del usaurio - // al que se asignó - return this.repository.save( - this.repository.create({ - id_equipo: infoEquipo.id_equipo, - u: id_usuario, - status: { id_status: 2 }, - }), + }) + .then((infoEquipoAux) => { + // Si no hay saca error + if (!infoEquipoAux) + throw new ConflictException( + 'No hay un equipo de cómputo que cumpla con las caracteríasticas solicitadas o ya no hay equipos disponibles en este momento. Intenta más tarde o cambia las características.', + ); + infoEquipo = infoEquipoAux; + }); + // Esta variable debe estar siempre en null antes de asignar el equipo + if (infoEquipo.u) + throw new ConflictException( + 'Ocurrio un error al tratar de asignarte un equipo de cómputo, intenta de nuevo.', ); - }) - // Una vez actualizado lo busco de nuvo - .then((equipo) => this.findById(equipo.id_equipo)) - .then((equipo) => { - // Si el campo u no coincide con el id_usaurio saca error - if (equipo.u != id_usuario) - throw new ConflictException( - 'Ocurrio un error al tratar de asignarte un equipo de cómputo, intenta de nuevo.', - ); - return equipo; - }) - ); + // Actualizo el status del equipo a apartado y gurado el id del usaurio + // al que se asignó + return this.repository.save( + this.repository.create({ + id_equipo: infoEquipo.id_equipo, + u: id_usuario, + status: { id_status: 2 }, + }), + ); + }) + .then((equipo) => this.findById(equipo.id_equipo)) // Una vez actualizado lo busco de nuevo + .then((equipo) => { + // Si el campo u no coincide con el id_usaurio saca error + if (equipo.u != id_usuario) + throw new ConflictException( + 'Ocurrió un error al tratar de asignarte un equipo de cómputo, intenta de nuevo.', + ); + return equipo; + }); } findFullInfoByNumeroInventario( - id_institucion: number, + operador: Operador, numero_inventario: string, ) { - return this.institucionService - .findById(id_institucion) - .then((institucion) => - this.fullInformacionEquipoView.findOne({ - where: { - id_institucion: institucion.id_institucion, - numero_inventario, - }, - }), - ) + return this.fullInformacionEquipoView + .findOne({ + where: { + id_institucion: operador.institucion.id_institucion, + numero_inventario, + }, + }) .then(async (infoEquipo) => { if (!infoEquipo) throw new NotFoundException( - 'No existe un equipo de cómputo con este número de inventario.', + 'No existe un equipo de cómputo con este número de inventario en esta institución.', ); // Busco todos los programas de este equipo diff --git a/src/institucion-usuario/institucion-usuario.service.ts b/src/institucion-usuario/institucion-usuario.service.ts index 0b3e3a2..6aa3c7c 100644 --- a/src/institucion-usuario/institucion-usuario.service.ts +++ b/src/institucion-usuario/institucion-usuario.service.ts @@ -1,6 +1,6 @@ import { ConflictException, Injectable } from '@nestjs/common'; import { InjectRepository } from '@nestjs/typeorm'; -import { Repository } from 'typeorm'; +import { FindOptionsWhere, Repository } from 'typeorm'; import { Institucion } from 'src/institucion/entity/institucion.entity'; import { InstitucionCarrera } from '../institucion-carrera/entity/institucion-carrera.entity'; import { InstitucionUsuario } from './entity/institucion-usuario.entity'; @@ -82,9 +82,17 @@ export class InstitucionUsuarioService { }); } - findFullInfoAllByUsuario(usuario: Usuario) { + findFullInfoAllByUsuario(usuario: Usuario, activosSinMulta = true) { + const busqueda: FindOptionsWhere = { + id_usuario: usuario.id_usuario, + }; + + if (activosSinMulta) { + busqueda.activo = 1; + busqueda.multa = 0; + } return this.fullInformacionInstitucionUsuarioView - .find({ where: { id_usuario: usuario.id_usuario, activo: 1, multa: 0 } }) + .find({ where: busqueda }) .then((infoInstitucionesUsuario) => { const institucionesUsuario: InstitucionUsuario[] = []; diff --git a/src/multa/multa.service.ts b/src/multa/multa.service.ts index f227c82..90d6510 100644 --- a/src/multa/multa.service.ts +++ b/src/multa/multa.service.ts @@ -1,7 +1,7 @@ import * as moment from 'moment'; import { ConflictException, Injectable } from '@nestjs/common'; import { InjectRepository } from '@nestjs/typeorm'; -import { DeepPartial, FindOptionsWhere, Like, Repository } from 'typeorm'; +import { FindOptionsWhere, Like, Repository } from 'typeorm'; import { Multa } from './entity/multa.entity'; import { FullInformacionMultaView } from './entity/views/full-informacion-multa.view'; import { InformacionMultaView } from './entity/views/informacion-multa.view'; @@ -39,6 +39,7 @@ export class MultaService { retraso?: number, id_institucion_infraccion?: number, ) { + console.log('hola1'); const ahora = moment(); const prestamo = typeof id_prestamo === 'number' @@ -48,51 +49,59 @@ export class MultaService { typeof id_operador === 'number' ? await this.operadorService.findById(id_operador) : id_operador; - const data: DeepPartial = { + // Creo registro de multa + const nuevaMulta = this.repository.create({ descripcion, fecha_inicio: ahora.toDate(), operadorMulta: operador, prestamo, - }; + }); let institucionInfraccion = id_institucion_infraccion ? await this.institucionInfraccionService.findById( id_institucion_infraccion, ) : null; + // Valido que este prestamo no haya sido cancelado poer el usuario u operador if (prestamo.cancelado_operador || prestamo.cancelado_usuario) throw new ConflictException( 'No se puede multar a un usuario con un préstamo que fue cancelado.', ); + // Si no se mando un id_institucion_infraccion if (!institucionInfraccion) { + // Si tampoco se mando retraso saco error if (!retraso) throw new ConflictException( 'No se mandó ningún motivo para multar a este alumno.', ); + // Asigno institucionInfraccion "Sin multa" por default institucionInfraccion = await this.institucionInfraccionService.findSinInfraccion( operador.institucion, ); } + // Busco una multa con este préstamo return this.repository .findOne({ where: { prestamo } }) .then((existeMulta) => { + // Si existe saco error if (existeMulta) throw new ConflictException( 'Ya existe una multa asignada a este préstamo.', ); + // Si hay retraso lo agrego a la multa if (retraso) { - data.retraso = true; + nuevaMulta.retraso = true; ahora.add(retraso * operador.institucion.dias_multa_retraso, 'd'); } - if (institucionInfraccion) { - data.institucionInfraccion = institucionInfraccion; - ahora.add(institucionInfraccion.dias_multa, 'd'); - } - data.fecha_fin = ahora.toDate(); - return this.repository.save(this.repository.create(data)); + nuevaMulta.institucionInfraccion = institucionInfraccion; + ahora.add(institucionInfraccion.dias_multa, 'd'); + nuevaMulta.fecha_fin = ahora.toDate(); + // Guardo la información + return this.repository.save(nuevaMulta); }) .then((_) => + // Actualizo multas del usuario this.institucionUsuarioService.updateMulta( operador.institucion.id_institucion, prestamo.usuario.id_usuario, diff --git a/src/prestamo/dto/input/cancelar-usuario.dto.ts b/src/prestamo/dto/input/cancelar-usuario.dto.ts deleted file mode 100644 index eb70c6e..0000000 --- a/src/prestamo/dto/input/cancelar-usuario.dto.ts +++ /dev/null @@ -1,6 +0,0 @@ -import { IsInt } from 'class-validator'; - -export class CancelarUsuarioDto { - @IsInt() - id_prestamo: number; -} diff --git a/src/prestamo/dto/input/historial.dto.ts b/src/prestamo/dto/input/historial.dto.ts index 03cccdc..2ab9a1b 100644 --- a/src/prestamo/dto/input/historial.dto.ts +++ b/src/prestamo/dto/input/historial.dto.ts @@ -49,6 +49,14 @@ export class HistorialDto { @IsOptional() id_modulo?: string; + @IsNumberString() + @IsOptional() + id_operador_entrega?: string; + + @IsNumberString() + @IsOptional() + id_operador_regreso?: string; + @IsNumberString() @IsOptional() id_prestamo?: string; diff --git a/src/prestamo/prestamo.controller.ts b/src/prestamo/prestamo.controller.ts index ff92635..71854d2 100644 --- a/src/prestamo/prestamo.controller.ts +++ b/src/prestamo/prestamo.controller.ts @@ -23,11 +23,9 @@ import { Operador } from '../operador/entity/operador.entity'; import { Usuario } from '../usuario/entity/usuario.entity'; import { Modulo } from '../modulo/entity/modulo.entity'; import { IdEquipoPaginaDto } from '../dto/input/id-equipo-pagina.dto'; -import { IdUsuarioDto } from '../dto/input/id-usuario.dto'; import { IdUsuarioPaginaDto } from '../dto/input/id-usuario-pagina.dto'; import { NumeroInventarioDto } from '../dto/numero-inventario.dto'; import { ActivosDto } from './dto/input/activos.dto'; -import { CancelarUsuarioDto } from './dto/input/cancelar-usuario.dto'; import { CancelarOperadorDto } from './dto/input/cancelar-operador.dto'; import { HistorialDto } from './dto/input/historial.dto'; import { IdPrestamoDto } from './dto/input/id-prestamo.dto'; @@ -117,7 +115,7 @@ export class PrestamoController { const operador: Operador = req.user.operador; this.validarUsuarioService.validarAdminOperador(operador); - return this.prestamoService.findFullInfoPrestamoAll(query); + return this.prestamoService.findAll(query); } @Serealize(MessageOutputDto) @@ -155,11 +153,11 @@ export class PrestamoController { description: 'La variable id_prestamo es obligatoria.', examples: { ejemplo: { value: { id_prestamo: 1 } } }, }) - cancelarUsuario(@Request() req, @Body() body: CancelarUsuarioDto) { + cancelarUsuario(@Request() req) { const usuario: Usuario = req.user.usuario; this.validarUsuarioService.validarUsuario(usuario); - return this.prestamoService.cancelarUsuario(usuario, body.id_prestamo); + return this.prestamoService.cancelarUsuario(usuario); } @Serealize(EquipoMinOutputDto) @@ -257,7 +255,7 @@ export class PrestamoController { const operador: Operador = req.user.operador; this.validarUsuarioService.validarOperador(operador); - return this.prestamoService.findFullInfoPrestamoAll(query); + return this.prestamoService.findAll(query); } @Serealize(PrestamosEquipoOutputDto) @@ -376,18 +374,11 @@ export class PrestamoController { 'Endpoint que retorna un préstamo activo por el id del usuario.', }) @ApiBearerAuth('jwt') - @ApiQuery({ - description: 'Id del usuario.', - name: 'id_usuario', - type: 'string', - }) - prestamoIdUsuario(@Request() req, @Query() query: IdUsuarioDto) { + prestamoIdUsuario(@Request() req) { const usuario: Usuario = req.user.usuario; this.validarUsuarioService.validarUsuario(usuario); - return this.prestamoService.prestamoInfoByIdUsuario( - parseInt(query.id_usuario), - ); + return this.prestamoService.prestamoInfoByUsuario(usuario); } @Serealize(PrestamoEquipoOutputDto) @@ -397,12 +388,6 @@ export class PrestamoController { description: 'Endpoint que retorna un préstamo activo por el número de inventario de un equipo.', }) - @ApiBearerAuth('jwt') - @ApiQuery({ - description: 'Id de la institución.', - name: 'id_institucion', - type: 'string', - }) @ApiQuery({ description: 'El número de inventario del equipo.', name: 'numero_inventario', @@ -416,7 +401,7 @@ export class PrestamoController { this.validarUsuarioService.validarAdminOperador(operador); return this.prestamoService.prestamoInfoByNumeroInventario( - parseInt(query.id_institucion), + operador, query.numero_inventario, ); } diff --git a/src/prestamo/prestamo.module.ts b/src/prestamo/prestamo.module.ts index 2c7994f..8d293a5 100644 --- a/src/prestamo/prestamo.module.ts +++ b/src/prestamo/prestamo.module.ts @@ -14,6 +14,7 @@ import { InstitucionDiaModule } from '../institucion-dia/institucion-dia.module' import { InstitucionProgramaModule } from '../institucion-programa/institucion-programa.module'; import { InstitucionTipoCarritoModule } from '../institucion-tipo-carrito/institucion-tipo-carrito.module'; import { InstitucionTipoEntradaModule } from '../institucion-tipo-entrada/institucion-tipo-entrada.module'; +import { InstitucionUsuarioModule } from '../institucion-usuario/institucion-usuario.module'; import { OperadorModule } from '../operador/operador.module'; import { ModuloModule } from '../modulo/modulo.module'; import { MultaModule } from '../multa/multa.module'; @@ -29,6 +30,7 @@ import { ValidarUsuarioModule } from '../validar-usuario/validar-usuario.module' InstitucionProgramaModule, InstitucionTipoCarritoModule, InstitucionTipoEntradaModule, + InstitucionUsuarioModule, ModuloModule, forwardRef(() => MultaModule), OperadorModule, diff --git a/src/prestamo/prestamo.service.ts b/src/prestamo/prestamo.service.ts index 41bb318..46b1bfa 100644 --- a/src/prestamo/prestamo.service.ts +++ b/src/prestamo/prestamo.service.ts @@ -33,6 +33,7 @@ import { InstitucionDiaService } from '../institucion-dia/institucion-dia.servic import { InstitucionProgramaService } from '../institucion-programa/institucion-programa.service'; import { InstitucionTipoCarritoService } from '../institucion-tipo-carrito/institucion-tipo-carrito.service'; import { InstitucionTipoEntradaService } from '../institucion-tipo-entrada/institucion-tipo-entrada.service'; +import { InstitucionUsuarioService } from '../institucion-usuario/institucion-usuario.service'; import { ModuloService } from '../modulo/modulo.service'; import { MultaService } from '../multa/multa.service'; import { OperadorService } from '../operador/operador.service'; @@ -56,6 +57,7 @@ export class PrestamoService { private institucionProgramaService: InstitucionProgramaService, private institucionTipoCarritoService: InstitucionTipoCarritoService, private institucionTipoEntradaService: InstitucionTipoEntradaService, + private institucionUsuarioService: InstitucionUsuarioService, private moduloService: ModuloService, @Inject(forwardRef(() => MultaService)) private multaService: MultaService, @@ -70,7 +72,7 @@ export class PrestamoService { motivo: string, ) { const ahora = moment(); - const prestamo = await this.findInfoPrestamoById(id_prestamo); + const prestamo = await this.findById(id_prestamo); this.validacionBasicaPrestamo(prestamo); this.validacionOperadorPrestamo(prestamo, operadorRegreso); @@ -80,41 +82,45 @@ export class PrestamoService { prestamo.operadorRegreso = operadorRegreso; prestamo.equipo.u = null; prestamo.equipo.status.id_status = 6; - return this.equipoService - .updateStatus(prestamo.equipo, operadorRegreso, motivo) - .then((_) => this.repository.save(prestamo)) - .then((_) => { - this.appGateway.actualizarUsuario(prestamo.usuario.id_usuario); - this.appGateway.actualizarOperador( - operadorRegreso.institucion.id_institucion, - ); - return { message: 'Se canceló correctamente este préstamo.' }; - }); + // Guardo cambios en el equipo, y envio el motivo de cancelación + return ( + this.equipoService + .updateStatus(prestamo.equipo, operadorRegreso, motivo) + // Guardo cambios del prestamo + .then((_) => this.repository.save(prestamo)) + .then((_) => { + // Actualizo interfaz de usaurios + this.appGateway.actualizarUsuario(prestamo.usuario.id_usuario); + this.appGateway.actualizarOperador( + operadorRegreso.institucion.id_institucion, + ); + return { message: 'Se canceló correctamente este préstamo.' }; + }) + ); } - async cancelarUsuario(usuario: Usuario, id_prestamo: number) { + async cancelarUsuario(usuario: Usuario) { const ahora = moment(); - const prestamo = await this.findInfoPrestamoById(id_prestamo); + const prestamo = await this.prestamoInfoByUsuario(usuario); this.validacionBasicaPrestamo(prestamo); + // Saco error en status de equipo 3 if (prestamo.equipo.status.id_status === 3) throw new ConflictException( - 'No puedes cancelar este préstamo una vez se te entregó el equipo.', - ); - if (usuario.id_usuario != prestamo.usuario.id_usuario) - throw new ConflictException( - 'No puedes cancelar este préstamo porque no te pretenece.', + 'No puedes cancelar este préstamo una vez que se te entregó el equipo.', ); prestamo.activo = false; prestamo.fecha_entrega = ahora.toDate(); prestamo.cancelado_usuario = true; prestamo.equipo.u = null; prestamo.equipo.status.id_status = 1; + // Guardo cambios en el equipo return this.equipoService .updateStatus(prestamo.equipo) - .then((_) => this.repository.save(prestamo)) + .then((_) => this.repository.save(prestamo)) // Guardo cambios del prestamo .then((_) => { - this.appGateway.actualizarUsuario(prestamo.usuario.id_usuario); + // Actualizo interfaz de usaurios + this.appGateway.actualizarUsuario(usuario.id_usuario); this.appGateway.actualizarOperador( prestamo.equipo.carrito.modulo.institucion.id_institucion, ); @@ -157,21 +163,25 @@ export class PrestamoService { ) : null; + // Valido que no sea domingo if (ahora.weekday() === 0) throw new ConflictException('No hay servicio los días domingo.'); - this.validarInstitucionUsuario(usuario.instituciones, modulo); + // Valido si ese día se encuentra activo if (!institucionDia.activo) throw new ConflictException( 'El día de hoy no hay servicio de préstamo de equipos.', ); + // Si ahora es menor a horaMin significa que aun no inicio el horario de serivicio if (ahora < horaMin) throw new ConflictException( `El servicio inicia a las ${institucionDia.hora_inicio} el día de hoy.`, ); + // Si ahora es mayor o igual a horaExtra significa que ya acabo la hora de servicio if (ahora >= horaExtra) throw new ConflictException( `El servicio terminó a las ${institucionDia.hora_extra} el día de hoy.`, ); + // Recorro el array de horasExcepcion del día en cuestión for (let i = 0; i < institucionDia.horasExcepcion.length; i++) { const horaFin = moment( `${ahoraStr} ${institucionDia.horasExcepcion[i].hora_fin}`, @@ -180,18 +190,30 @@ export class PrestamoService { `${ahoraStr} ${institucionDia.horasExcepcion[i].hora_inicio}`, ); + // Si ahora esta entre horaInicio y horaFin significa que no hay servicio de préstamos + // temporalmente if (ahora > horaInicio && ahora < horaFin) throw new ConflictException( - `Se suspendió temporalmente el servicio de ${institucionDia.horasExcepcion[i].hora_inicio} a ${institucionDia.horasExcepcion[i].hora_fin}.`, + `Se suspendió el servicio de préstamo temporalmente de ${institucionDia.horasExcepcion[i].hora_inicio} a ${institucionDia.horasExcepcion[i].hora_fin}.`, ); } - return this.informacionPrestamoView - .findOne({ where: { activo: 1, id_usuario: usuario.id_usuario } }) + // Busco instituciones activas y sin multa de este usuario + return this.institucionUsuarioService + .findFullInfoAllByUsuario(usuario, false) + .then((instituciones) => { + this.validarInstitucionUsuario(instituciones, modulo); + // Busco un prestamo activo con el id del usuario que realiza la acción + return this.informacionPrestamoView.findOne({ + where: { activo: 1, id_usuario: usuario.id_usuario }, + }); + }) .then((existePrestamo) => { + // Saco error si lo encuentra if (existePrestamo) throw new ConflictException( 'Este usuario ya tiene un préstamo activo.', ); + // Busco un equipo con las caracteríasticas solicitadas return this.equipoService.findEquipo( usuario.id_usuario, modulo, @@ -201,6 +223,7 @@ export class PrestamoService { ); }) .then((equipo) => + // Genero el registro y lo guardo this.repository.save( this.repository.create({ equipo, @@ -215,6 +238,7 @@ export class PrestamoService { ), ) .then((prestamo) => { + // Actualizo la interfaz del operador this.appGateway.actualizarOperador(modulo.institucion.id_institucion); return prestamo; }); @@ -223,21 +247,27 @@ export class PrestamoService { async desactivarPrestamos() { const ahora = moment(); + // Busco todos los préstamos activos y que esten apartadoss return this.informacionPrestamoView .find({ where: { activo: 1, id_status: 2 } }) .then(async (infoPrestamo) => { + // Recorro el array for (let i = 0; i < infoPrestamo.length; i++) { const prestamo = this.viewToPrestamo(infoPrestamo[i]); + // Si la resta ahora - hora_max_recoger es mayor a 0 significa que ya pasó + // el tiempo limite para recoger el equipo de cómputo if (ahora.diff(moment(prestamo.hora_max_recoger)) > 0) { prestamo.activo = false; prestamo.cancelado_operador = true; prestamo.equipo.u = null; prestamo.equipo.status.id_status = 1; + // Guardo los cambios del préstamo await this.repository .save(prestamo) .then((_) => this.equipoService.updateStatus(prestamo.equipo)) .then((_) => { + // Actualizo las interfazes del los usuarios this.appGateway.actualizarOperador( prestamo.equipo.carrito.modulo.institucion.id_institucion, ); @@ -255,7 +285,7 @@ export class PrestamoService { ) { const ahora = moment(); const ahoraStr = ahora.format('YYYY-MM-DD'); - const prestamo = await this.findInfoPrestamoById(id_prestamo); + const prestamo = await this.findById(id_prestamo); const institucionDia = await this.institucionDiaService.findByInstitucionDia( operadorEntrega.institucion, @@ -270,6 +300,8 @@ export class PrestamoService { this.validacionBasicaPrestamo(prestamo); this.validacionOperadorPrestamo(prestamo, operadorEntrega, modulo); + // Si el equipo esta en status 3 ya no se puede ejecutar este endpoint de nuevo + // con este préstamo if (prestamo.equipo.status.id_status === 3) throw new ConflictException( 'Ya se entregó el equipo de cómputo al usuario.', @@ -282,10 +314,12 @@ export class PrestamoService { prestamo.operadorEntrega = operadorEntrega; prestamo.equipo.prestado = true; prestamo.equipo.status.id_status = 3; - return this.repository - .save(prestamo) - .then((_) => this.equipoService.updateStatus(prestamo.equipo)) + // Guardo los cambios del equipo + return this.equipoService + .updateStatus(prestamo.equipo) + .then((_) => this.repository.save(prestamo)) // Guardo los cambios del préstamo .then((_) => { + // Actualizo la interfaz de los usuarios this.appGateway.actualizarUsuario(prestamo.usuario.id_usuario); this.appGateway.actualizarOperador( prestamo.equipo.carrito.modulo.institucion.id_institucion, @@ -294,140 +328,7 @@ export class PrestamoService { }); } - async findAllByIdEquipo(id_equipo: number, pagina: number) { - return this.fullInformacionPrestamoView - .findAndCount({ - where: { id_equipo }, - order: { id_prestamo: 'DESC' }, - skip: (pagina - 1) * 25, - take: 25, - }) - .then((infoPrestamos) => { - const prestamos: Prestamo[] = []; - for (let i = 0; i < infoPrestamos[0].length; i++) - prestamos.push( - this.repository.create({ - id_prestamo: infoPrestamos[0][i].id_prestamo, - activo: infoPrestamos[0][i].activo === 1, - cancelado_operador: infoPrestamos[0][i].cancelado_operador === 1, - cancelado_usuario: infoPrestamos[0][i].cancelado_usuario === 1, - fecha_entrega: infoPrestamos[0][i].fecha_entrega, - fecha_inicio: infoPrestamos[0][i].fecha_inicio, - hora_fin: infoPrestamos[0][i].hora_fin, - hora_inicio: infoPrestamos[0][i].hora_inicio, - hora_max_recoger: infoPrestamos[0][i].hora_max_recoger, - usuario: { - id_usuario: infoPrestamos[0][i].id_usuario, - nombre: infoPrestamos[0][i].nombre, - usuario: infoPrestamos[0][i].usuario, - tipoUsuario: { - id_tipo_usuario: infoPrestamos[0][i].id_tipo_usuario, - }, - }, - operadorEntrega: { - id_operador: infoPrestamos[0][i].id_operador_entrega, - operador: infoPrestamos[0][i].operador_entrega, - }, - operadorRegreso: { - id_operador: infoPrestamos[0][i].id_operador_regreso, - operador: infoPrestamos[0][i].operador_regreso, - }, - }), - ); - return [prestamos, infoPrestamos[1]]; - }); - } - - findAllByIdUsuario(id_usuario: number, pagina: number) { - return this.usuarioService - .findById(id_usuario) - .then((usuario) => - this.fullInformacionPrestamoView.findAndCount({ - where: { id_usuario: usuario.id_usuario }, - order: { id_prestamo: 'DESC' }, - skip: (pagina - 1) * 25, - take: 25, - }), - ) - .then((infoPrestamos) => { - const prestamos: Prestamo[] = []; - - for (let i = 0; i < infoPrestamos[0].length; i++) - prestamos.push( - this.repository.create({ - id_prestamo: infoPrestamos[0][i].id_prestamo, - activo: infoPrestamos[0][i].activo === 1, - cancelado_operador: infoPrestamos[0][i].cancelado_operador === 1, - cancelado_usuario: infoPrestamos[0][i].cancelado_usuario === 1, - fecha_entrega: infoPrestamos[0][i].fecha_entrega, - fecha_inicio: infoPrestamos[0][i].fecha_inicio, - hora_fin: infoPrestamos[0][i].hora_fin, - hora_inicio: infoPrestamos[0][i].hora_inicio, - hora_max_recoger: infoPrestamos[0][i].hora_max_recoger, - equipo: { - id_equipo: infoPrestamos[0][i].id_equipo, - equipo: infoPrestamos[0][i].equipo, - numero_inventario: infoPrestamos[0][i].numero_inventario, - carrito: { - id_carrito: infoPrestamos[0][i].id_carrito, - carrito: infoPrestamos[0][i].carrito, - modulo: { - id_modulo: infoPrestamos[0][i].id_modulo, - modulo: infoPrestamos[0][i].modulo, - institucion: { - id_institucion: infoPrestamos[0][i].id_institucion, - institucion: infoPrestamos[0][i].institucion, - }, - }, - tipoCarrito: { - id_tipo_carrito: infoPrestamos[0][i].id_tipo_carrito, - tipo_carrito: infoPrestamos[0][i].tipo_carrito, - }, - }, - }, - operadorEntrega: { - id_operador: infoPrestamos[0][i].id_operador_entrega, - operador: infoPrestamos[0][i].operador_entrega, - }, - operadorRegreso: { - id_operador: infoPrestamos[0][i].id_operador_regreso, - operador: infoPrestamos[0][i].operador_regreso, - }, - }), - ); - return [prestamos, infoPrestamos[1]]; - }); - } - - findById(id_prestamo: number) { - return this.repository - .createQueryBuilder('p') - .innerJoinAndSelect('p.equipo', 'e') - .innerJoinAndSelect('p.usuario', 'u') - .innerJoinAndSelect('e.carrito', 'c') - .innerJoinAndSelect('e.programas', 'ps') - .innerJoinAndSelect('e.status', 's') - .innerJoinAndSelect('e.tiposEntradas', 'tes') - .innerJoinAndSelect('u.instituciones', 'is') - .innerJoinAndSelect('c.modulo', 'm') - .innerJoinAndSelect('c.tipoCarrito', 'tc') - .innerJoinAndSelect('ps.programa', 'pr') - .innerJoinAndSelect('tes.tipoEntrada', 'te') - .innerJoinAndSelect('is.institucionCarrera', 'ic') - .innerJoinAndSelect('ic.carrera', 'ca') - .innerJoinAndSelect('ic.institucion', 'in') - .innerJoinAndSelect('m.institucion', 'i') - .where('p.id_prestamo = :id_prestamo', { - id_prestamo, - }) - .getOne() - .then((prestamo) => { - if (!prestamo) throw new NotFoundException('No existe este préstamo.'); - return prestamo; - }); - } - - async findFullInfoPrestamoAll(filtros: { + async findAll(filtros: { pagina?: string; activo?: string | boolean; cancelado_operador?: string; @@ -570,7 +471,112 @@ export class PrestamoService { }); } - findInfoPrestamoById(id_prestamo: number) { + findAllByIdEquipo(id_equipo: number, pagina: number) { + return this.fullInformacionPrestamoView + .findAndCount({ + where: { id_equipo }, + order: { id_prestamo: 'DESC' }, + skip: (pagina - 1) * 25, + take: 25, + }) + .then((infoPrestamos) => { + const prestamos: Prestamo[] = []; + for (let i = 0; i < infoPrestamos[0].length; i++) + prestamos.push( + this.repository.create({ + id_prestamo: infoPrestamos[0][i].id_prestamo, + activo: infoPrestamos[0][i].activo === 1, + cancelado_operador: infoPrestamos[0][i].cancelado_operador === 1, + cancelado_usuario: infoPrestamos[0][i].cancelado_usuario === 1, + fecha_entrega: infoPrestamos[0][i].fecha_entrega, + fecha_inicio: infoPrestamos[0][i].fecha_inicio, + hora_fin: infoPrestamos[0][i].hora_fin, + hora_inicio: infoPrestamos[0][i].hora_inicio, + hora_max_recoger: infoPrestamos[0][i].hora_max_recoger, + usuario: { + id_usuario: infoPrestamos[0][i].id_usuario, + nombre: infoPrestamos[0][i].nombre, + usuario: infoPrestamos[0][i].usuario, + tipoUsuario: { + id_tipo_usuario: infoPrestamos[0][i].id_tipo_usuario, + }, + }, + operadorEntrega: { + id_operador: infoPrestamos[0][i].id_operador_entrega, + operador: infoPrestamos[0][i].operador_entrega, + }, + operadorRegreso: { + id_operador: infoPrestamos[0][i].id_operador_regreso, + operador: infoPrestamos[0][i].operador_regreso, + }, + }), + ); + return [prestamos, infoPrestamos[1]]; + }); + } + + findAllByIdUsuario(id_usuario: number, pagina: number) { + return this.usuarioService + .findById(id_usuario) + .then((usuario) => + this.fullInformacionPrestamoView.findAndCount({ + where: { id_usuario: usuario.id_usuario }, + order: { id_prestamo: 'DESC' }, + skip: (pagina - 1) * 25, + take: 25, + }), + ) + .then((infoPrestamos) => { + const prestamos: Prestamo[] = []; + + for (let i = 0; i < infoPrestamos[0].length; i++) + prestamos.push( + this.repository.create({ + id_prestamo: infoPrestamos[0][i].id_prestamo, + activo: infoPrestamos[0][i].activo === 1, + cancelado_operador: infoPrestamos[0][i].cancelado_operador === 1, + cancelado_usuario: infoPrestamos[0][i].cancelado_usuario === 1, + fecha_entrega: infoPrestamos[0][i].fecha_entrega, + fecha_inicio: infoPrestamos[0][i].fecha_inicio, + hora_fin: infoPrestamos[0][i].hora_fin, + hora_inicio: infoPrestamos[0][i].hora_inicio, + hora_max_recoger: infoPrestamos[0][i].hora_max_recoger, + equipo: { + id_equipo: infoPrestamos[0][i].id_equipo, + equipo: infoPrestamos[0][i].equipo, + numero_inventario: infoPrestamos[0][i].numero_inventario, + carrito: { + id_carrito: infoPrestamos[0][i].id_carrito, + carrito: infoPrestamos[0][i].carrito, + modulo: { + id_modulo: infoPrestamos[0][i].id_modulo, + modulo: infoPrestamos[0][i].modulo, + institucion: { + id_institucion: infoPrestamos[0][i].id_institucion, + institucion: infoPrestamos[0][i].institucion, + }, + }, + tipoCarrito: { + id_tipo_carrito: infoPrestamos[0][i].id_tipo_carrito, + tipo_carrito: infoPrestamos[0][i].tipo_carrito, + }, + }, + }, + operadorEntrega: { + id_operador: infoPrestamos[0][i].id_operador_entrega, + operador: infoPrestamos[0][i].operador_entrega, + }, + operadorRegreso: { + id_operador: infoPrestamos[0][i].id_operador_regreso, + operador: infoPrestamos[0][i].operador_regreso, + }, + }), + ); + return [prestamos, infoPrestamos[1]]; + }); + } + + findById(id_prestamo: number) { return this.informacionPrestamoView .findOne({ where: { id_prestamo } }) .then((infoPrestamo) => { @@ -580,10 +586,7 @@ export class PrestamoService { }); } - findInfoPrestamoByNumeroInventario( - institucion: Institucion, - numero_inventario: string, - ) { + findByNumeroInventario(institucion: Institucion, numero_inventario: string) { return this.informacionPrestamoView .findOne({ where: { @@ -646,9 +649,9 @@ export class PrestamoService { }); } - prestamoInfoByIdUsuario(id_usuario: number) { + prestamoInfoByUsuario(usuario: Usuario) { return this.prestamoInformacionView - .findOne({ where: { activo: 1, id_usuario } }) + .findOne({ where: { activo: 1, id_usuario: usuario.id_usuario } }) .then((infoPrestamo) => { if (!infoPrestamo) throw new NotFoundException( @@ -688,17 +691,11 @@ export class PrestamoService { } prestamoInfoByNumeroInventario( - id_institucion: number, + operador: Operador, numero_inventario: string, ) { - return this.institucionService - .findById(id_institucion) - .then((institucion) => - this.equipoService.findByNumeroInventario( - institucion, - numero_inventario, - ), - ) + return this.equipoService + .findByNumeroInventario(operador.institucion, numero_inventario) .then((equipo) => this.prestamoInformacionView.findOne({ where: { activo: 1, id_equipo: equipo.id_equipo }, @@ -750,27 +747,36 @@ export class PrestamoService { modulo?: Modulo, ) { const ahora = moment(); + // La resta ahora - hora_fin nos da la cantidad de tiempo que se paso el usuario + // en entregar el equipo a tiempo. Si es negativa es que fue antes de la hora_fin const tardanza = Math.trunc(ahora.diff(moment(prestamo.hora_fin)) / 60000); + // Minutos que se tardo entre el tiempo configurable de la institución const semanasCastigo = Math.trunc( tardanza / operadorRegreso.institucion.tiempo_entrega, ); this.validacionBasicaPrestamo(prestamo); this.validacionOperadorPrestamo(prestamo, operadorRegreso, modulo); + // No se puede regresar el equipo si aun no se entrega if (prestamo.equipo.status.id_status === 2) throw new ConflictException( 'Aún no se ha entregado el equipo de cómputo al usuario.', ); if (id_institucion_infraccion && !descripcion) throw new ConflictException('No se mandó la descripción de lo ocurrido.'); + console.log('HOLA'); prestamo.activo = false; prestamo.fecha_entrega = ahora.toDate(); prestamo.operadorRegreso = operadorRegreso; prestamo.equipo.u = null; prestamo.equipo.status.id_status = id_status; + // Si semanasCastigo es mayor a 0 significa que hay multa if (semanasCastigo > 0) { const mensajeTardanza = `El usaurio se tardó: ${tardanza} minutos en entregar el equipo de cómputo.`; + // Si se mando id_institucion_infraccion significa que ademas de entregar tarde, + // el usuario daño el equipo, por lo tanto tenemos que agregar la descripción del daño + // a motivo, y mandar la id_institucion_infraccion if (id_institucion_infraccion) await this.multaService.create( prestamo, @@ -779,6 +785,7 @@ export class PrestamoService { semanasCastigo, id_institucion_infraccion, ); + // Multa normal else await this.multaService.create( prestamo, @@ -787,6 +794,8 @@ export class PrestamoService { semanasCastigo, ); } else if (id_institucion_infraccion) + // De lo contrario, si se mandó id_institucion_infraccion significa que + // el usuario solo solo daño el equipo await this.multaService.create( prestamo, operadorRegreso, @@ -794,6 +803,8 @@ export class PrestamoService { null, id_institucion_infraccion, ); + console.log('hola'); + // Guardo los cambios del préstamo return this.repository .save(prestamo) .then((_) => @@ -804,13 +815,12 @@ export class PrestamoService { ), ) .then((_) => { + // Actualizo la interfaz del usuario this.appGateway.actualizarUsuario(prestamo.usuario.id_usuario); this.appGateway.actualizarOperador( operadorRegreso.institucion.id_institucion, ); - return { - message: 'Se regresó el equipo de cómputo.', - }; + return { message: 'Se regresó el equipo de cómputo.' }; }); } @@ -823,7 +833,8 @@ export class PrestamoService { id_institucion_infraccion?: number, modulo?: Modulo, ) { - return this.findInfoPrestamoById(id_prestamo).then((prestamo) => + // Busco el prestamo por id prestamo y luego regreso el equipo + return this.findById(id_prestamo).then((prestamo) => this.regresar( prestamo, operador, @@ -845,7 +856,9 @@ export class PrestamoService { id_institucion_infraccion?: number, modulo?: Modulo, ) { - return this.findInfoPrestamoByNumeroInventario( + // Busco el prestamo por número de inventario y la institución del operador + // luego regreso el equipo + return this.findByNumeroInventario( operador.institucion, numero_inventario, ).then((prestamo) => @@ -862,14 +875,17 @@ export class PrestamoService { } validacionBasicaPrestamo(prestamo: Prestamo) { + // Valido si el préstamo fue cancelado por el usuario if (prestamo.cancelado_usuario) throw new ConflictException( 'Este préstamo fue cancelado por el usuario.', ); + // Valido si el préstamo fue cancelado por el operador if (prestamo.cancelado_operador) throw new ConflictException( 'Este préstamo fue cancelado por un operador.', ); + // Valido si el préstamo esta inactivo if (!prestamo.activo) throw new ConflictException('Este préstamo ya no se encuentra activo.'); }