nuevo operador listo

This commit is contained in:
lemuel 2022-10-15 23:51:56 -05:00
parent 132d1b18d9
commit b383da979f
11 changed files with 190 additions and 207 deletions

View File

@ -77,10 +77,8 @@ export class AuthController {
@Get('validar-token') @Get('validar-token')
@UseGuards(AuthGuard('jwt')) @UseGuards(AuthGuard('jwt'))
@ApiOperation({ @ApiOperation({ description: 'Endpoint utilizado para validar un token.' })
description: 'Endpoint utilizado para validar un token.',
})
validarToken() { validarToken() {
return true; return { valido: true };
} }
} }

View File

@ -4,10 +4,14 @@ import {
UnauthorizedException, UnauthorizedException,
} from '@nestjs/common'; } from '@nestjs/common';
import { JwtService } from '@nestjs/jwt'; import { JwtService } from '@nestjs/jwt';
import { Operador } from '../operador/entity/operador.entity';
import { BcryptService } from '../bcrypt/bcrypt.service'; import { BcryptService } from '../bcrypt/bcrypt.service';
import { ModuloService } from '../modulo/modulo.service'; import { ModuloService } from '../modulo/modulo.service';
import { OperadorService } from '../operador/operador.service'; import { OperadorService } from '../operador/operador.service';
import { UsuarioService } from '../usuario/usuario.service'; import { UsuarioService } from '../usuario/usuario.service';
import { JwtPayloadAdmin } from './dto/jwt-payload-admin';
import { JwtPayloadOperador } from './dto/jwt-payload-operador';
import { JwtPayloadUsuario } from './dto/jwt-payload-usuario';
@Injectable() @Injectable()
export class AuthService { export class AuthService {
@ -20,19 +24,23 @@ export class AuthService {
) {} ) {}
loginAdmin(admin: string, password: string) { loginAdmin(admin: string, password: string) {
return this.operadorService.informacionAdmin(admin).then((data) => { return this.operadorService.findInfoOperadorAdmin(admin).then((admin) => {
if ( this.validacionBasica(admin, password);
!data.operador ||
!this.bcryptService.comparar(password, data.password) const JwtPayload: JwtPayloadAdmin = {
) Operador: {
throw new BadRequestException( id_operador: admin.id_operador,
'Usuario y/o password incorrectos, ingresa unas credenciales válidas.', operador: admin.operador,
); nombre: admin.nombre,
if (!data.activo) institucion: {
throw new UnauthorizedException( id_institucion: admin.institucion.id_institucion,
'Esta cuenta se encuentra desactivada.', },
); tipoUsuario: {
return { token: this.jwtService.sign(data.operador) }; id_tipo_usuario: admin.tipoUsuario.id_tipo_usuario,
},
},
};
return { token: this.jwtService.sign(JwtPayload) };
}); });
} }
@ -40,22 +48,27 @@ export class AuthService {
const modulo = await this.moduloService.findInfoModuloById(id_modulo); const modulo = await this.moduloService.findInfoModuloById(id_modulo);
return this.operadorService return this.operadorService
.informacionOperador(modulo.institucion, operador) .findInfoOperador(modulo.institucion, operador)
.then((data) => { .then((operador) => {
if ( this.validacionBasica(operador, password);
!data.operador ||
!this.bcryptService.comparar(password, data.password) const JwtPayload: JwtPayloadOperador = {
) Operador: {
throw new BadRequestException( id_operador: operador.id_operador,
'Usuario y/o password incorrectos, ingresa unas credenciales válidas.', operador: operador.operador,
); nombre: operador.nombre,
if (!data.activo) institucion: {
throw new UnauthorizedException( id_institucion: operador.institucion.id_institucion,
'Esta cuenta se encuentra desactivada.', },
); tipoUsuario: {
if (data.operador.tipoUsuario.id_tipo_usuario === 4) id_tipo_usuario: operador.tipoUsuario.id_tipo_usuario,
data.operador.id_modulo = modulo.id_modulo; },
return { token: this.jwtService.sign(data.operador) }; },
};
if (operador.tipoUsuario.id_tipo_usuario === 4)
JwtPayload.Modulo.id_modulo = modulo.id_modulo;
return { token: this.jwtService.sign(JwtPayload) };
}); });
} }
@ -75,4 +88,13 @@ export class AuthService {
return { token: this.jwtService.sign(data.usuario) }; return { token: this.jwtService.sign(data.usuario) };
}); });
} }
private validacionBasica(operador: Operador, password: string) {
if (!operador || !this.bcryptService.comparar(password, operador.password))
throw new BadRequestException(
'Usuario y/o password incorrectos, ingresa unas credenciales válidas.',
);
if (!operador.activo)
throw new UnauthorizedException('Esta cuenta se encuentra desactivada.');
}
} }

View File

@ -1,11 +1,9 @@
export class JwtPayload { export interface JwtPayloadAdmin {
nombre: string; Operador: {
id_operador: number;
id_operador: number; nombre: string;
operador: string;
institucion: { id_institucion: number }; institucion: { id_institucion: number };
tipoUsuario: { id_tipo_usuario: number };
operador: string; };
tipoUsuario: { id_tipo_usuario: number };
} }

View File

@ -1,13 +1,10 @@
export class JwtPayload { export interface JwtPayloadOperador {
nombre: string; Operador: {
id_operador: number;
id_modulo: number; nombre: string;
operador: string;
id_operador: number; institucion: { id_institucion: number };
tipoUsuario: { id_tipo_usuario: number };
institucion: { id_institucion: number }; };
Modulo?: { id_modulo: number };
operador: string;
tipoUsuario: { id_tipo_usuario: number };
} }

View File

@ -1,18 +1,8 @@
export class JwtPayload { export interface JwtPayloadUsuario {
nombre: string; Usuario: {
id_usuario: number;
id_usuario: number; nombre: string;
usuario: string;
instituciones: { tipoUsuario: { id_tipo_usuario: number };
id_institucion_usuario: number; };
institucionCarrera: {
id_institucion_carrera: number;
institucion: { id_institucion: number };
carrera: { id_carrera: number };
};
}[];
tipoUsuario: { id_tipo_usuario: number };
usuario: string;
} }

View File

@ -1,26 +0,0 @@
export class JwtPayload {
nombre: string;
tipoUsuario: { id_tipo_usuario: number };
id_modulo?: number;
id_operador?: number;
id_usuario?: number;
operador?: string;
usuario?: string;
institucion?: { id_institucion: number };
instituciones?: {
id_institucion_usuario: number;
institucionCarrera: {
id_institucion_carrera: number;
institucion: { id_institucion: number };
carrera: { id_carrera: number };
};
}[];
}

View File

@ -8,7 +8,9 @@ import { UsuarioService } from '../../usuario/usuario.service';
import { Modulo } from '../../modulo/entity/modulo.entity'; import { Modulo } from '../../modulo/entity/modulo.entity';
import { Operador } from '../../operador/entity/operador.entity'; import { Operador } from '../../operador/entity/operador.entity';
import { Usuario } from '../../usuario/entity/usuario.entity'; import { Usuario } from '../../usuario/entity/usuario.entity';
import { JwtPayload } from '../dto/jwt-payload'; import { JwtPayloadAdmin } from '../dto/jwt-payload-admin';
import { JwtPayloadOperador } from '../dto/jwt-payload-operador';
import { JwtPayloadUsuario } from '../dto/jwt-payload-usuario';
@Injectable() @Injectable()
export class JwtStrategyService extends PassportStrategy(Strategy) { export class JwtStrategyService extends PassportStrategy(Strategy) {
@ -24,32 +26,32 @@ export class JwtStrategyService extends PassportStrategy(Strategy) {
}); });
} }
async validate(payload: JwtPayload) { async validate(
payload: JwtPayloadAdmin | JwtPayloadOperador | JwtPayloadUsuario,
) {
const user: { modulo?: Modulo; usuario?: Usuario; operador?: Operador } = const user: { modulo?: Modulo; usuario?: Usuario; operador?: Operador } =
{}; {};
if (payload.id_usuario) if ('Usuario' in payload)
await this.usuarioService await this.usuarioService
.findById(payload.id_usuario, true, true) .findById(payload.Usuario.id_usuario, true, true)
.then((usuario) => (user.usuario = usuario)); .then((usuario) => (user.usuario = usuario));
else if (payload.id_operador) else if ('Operador' in payload)
await this.operadorService await this.operadorService
.findInfoOperadorById(payload.id_operador) .findInfoOperadorById(payload.Operador.id_operador)
.then(async (operador) => { .then(async (operador) => {
if (!operador.activo) if (!operador.activo)
throw new ForbiddenException('Esta cuenta esta desactivada.'); throw new ForbiddenException('Esta cuenta esta desactivada.');
/*
if (operador.tipoUsuario.id_tipo_usuario === 4) { if (operador.tipoUsuario.id_tipo_usuario === 4) {
if (payload.id_modulo) if ('Modulo' in payload)
await this.moduloService await this.moduloService
.findById(payload.id_modulo) .findInfoModuloById(payload.Modulo.id_modulo)
.then((modulo) => (user.modulo = modulo)); .then((modulo) => (user.modulo = modulo));
else else
throw new ForbiddenException( throw new ForbiddenException(
'Credenciales no válidas, inicia sesión de nuevo.', 'Credenciales no válidas, inicia sesión de nuevo.',
); );
} }
*/
user.operador = operador; user.operador = operador;
}); });
return user; return user;

View File

@ -32,15 +32,11 @@ export class Operador {
@Column({ type: String, nullable: false, length: 60 }) @Column({ type: String, nullable: false, length: 60 })
password: string; password: string;
@ManyToOne(() => Institucion, (institucion) => institucion.operadores, { @ManyToOne(() => Institucion, (institucion) => institucion.operadores)
eager: true,
})
@JoinColumn({ name: 'id_institucion' }) @JoinColumn({ name: 'id_institucion' })
institucion: Institucion; institucion: Institucion;
@ManyToOne(() => TipoUsuario, (tipoUsuario) => tipoUsuario.operadores, { @ManyToOne(() => TipoUsuario, (tipoUsuario) => tipoUsuario.operadores)
eager: true,
})
@JoinColumn({ name: 'id_tipo_usuario' }) @JoinColumn({ name: 'id_tipo_usuario' })
tipoUsuario: TipoUsuario; tipoUsuario: TipoUsuario;

View File

@ -18,7 +18,10 @@ import { TipoUsuario } from '../../../tipo-usuario/entity/tipo-usuario.entity';
.addSelect('tu.tipo_usuario', 'tipo_usuario') .addSelect('tu.tipo_usuario', 'tipo_usuario')
.from(Operador, 'o') .from(Operador, 'o')
.innerJoin(Institucion, 'i', 'i.id_institucion = o.id_institucion') .innerJoin(Institucion, 'i', 'i.id_institucion = o.id_institucion')
.innerJoin(TipoUsuario, 'tu', 'tu.id_tipo_usuario = o.id_tipo_usuario'), .innerJoin(TipoUsuario, 'tu', 'tu.id_tipo_usuario = o.id_tipo_usuario')
.orderBy('institucion')
.addOrderBy('tipo_usuario')
.addOrderBy('operador'),
}) })
export class FullInformacionOperadorView { export class FullInformacionOperadorView {
@ViewColumn() @ViewColumn()

View File

@ -130,7 +130,22 @@ export class OperadorController {
const admin: Operador = req.user.operador; const admin: Operador = req.user.operador;
this.validarUsuarioService.validarSuperAdminAdmin(admin); this.validarUsuarioService.validarSuperAdminAdmin(admin);
return this.operadorService.findAll(query); return this.operadorService.findFullInfoOperadorAll(query);
}
@Serealize(OperadorOutputDto)
@Get('catalogo')
@UseGuards(AuthGuard('jwt'))
@ApiOperation({
description:
'Endpoint que retorna todo el catálogo de operadores de una institucion.',
})
@ApiBearerAuth('jwt')
catalogo(@Request() req) {
const admin: Operador = req.user.operador;
this.validarUsuarioService.validarSuperAdminAdmin(admin);
return this.operadorService.findAllByInstitucion(admin);
} }
@Put('update-password') @Put('update-password')

View File

@ -4,7 +4,7 @@ import {
NotFoundException, NotFoundException,
} from '@nestjs/common'; } from '@nestjs/common';
import { InjectRepository } from '@nestjs/typeorm'; import { InjectRepository } from '@nestjs/typeorm';
import { Between, Repository } from 'typeorm'; import { Between, FindOptionsWhere, Like, Not, Repository } from 'typeorm';
import { Institucion } from '../institucion/entity/institucion.entity'; import { Institucion } from '../institucion/entity/institucion.entity';
import { Operador } from './entity/operador.entity'; import { Operador } from './entity/operador.entity';
import { FullInformacionOperadorView } from './entity/views/full-informacion-operador.view'; import { FullInformacionOperadorView } from './entity/views/full-informacion-operador.view';
@ -44,23 +44,16 @@ export class OperadorService {
throw new ConflictException( throw new ConflictException(
'No se puede asignar un tipo de usuario distinto a admin y operador', 'No se puede asignar un tipo de usuario distinto a admin y operador',
); );
// Ver que ningún admin tenga este usuario // Ver si existe un admin con ese usaurio
return this.repository return this.findInfoOperadorAdmin(operador)
.findOne({
select: ['id_operador'],
where: {
operador,
tipoUsuario: { id_tipo_usuario: Between(2, 3) },
},
})
.then((existeAdmin) => { .then((existeAdmin) => {
// Error si lo hay // Error si lo hay
if (existeAdmin) if (existeAdmin)
throw new ConflictException( throw new ConflictException(
'Ya existe un admin con ese nombre, intenta de nuevo con otro.', 'Ya existe un admin con ese nombre, intenta de nuevo con otro.',
); );
// Ver que no haya un operador en esta institución con este usuario // Ver que haya un operador en esta institución con este usuario
return this.repository.findOne({ where: { institucion, operador } }); return this.findInfoOperador(institucion, operador);
}) })
.then(async (existeOperador) => { .then(async (existeOperador) => {
// Error si lo hay // Error si lo hay
@ -104,7 +97,14 @@ export class OperadorService {
})); }));
} }
async findAll(filtros: { findAllByInstitucion(operador: Operador) {
return this.repository.find({
select: ['id_operador', 'operador'],
where: { institucion: operador.institucion },
});
}
async findFullInfoOperadorAll(filtros: {
pagina: string; pagina: string;
id_institucion?: string; id_institucion?: string;
id_tipo_usuario?: string; id_tipo_usuario?: string;
@ -120,30 +120,74 @@ export class OperadorService {
parseInt(filtros.id_tipo_usuario), parseInt(filtros.id_tipo_usuario),
) )
: null; : null;
const query = this.repository const busqueda: FindOptionsWhere<FullInformacionOperadorView> = {};
.createQueryBuilder('o')
.innerJoinAndSelect('o.institucion', 'i')
.innerJoinAndSelect('o.tipoUsuario', 'tu')
.where('id_operador != 1 AND id_operador != 2')
.orderBy('i.institucion')
.addOrderBy('tu.tipo_usuario')
.addOrderBy('o.operador')
.take(25)
.skip((parseInt(filtros.pagina) - 1) * 25);
if (filtros.operador) if (filtros.operador) busqueda.operador = Like(`${filtros.operador}%`);
query.andWhere('operador LIKE :operador', { if (institucion) busqueda.id_institucion = institucion.id_institucion;
operador: `${filtros.operador}%`, if (tipoUsuario) busqueda.id_tipo_usuario = tipoUsuario.id_tipo_usuario;
return this.fullInformacionOperadorView
.findAndCount({
where: [
busqueda,
{ id_tipo_usuario: Not(1) },
{ id_tipo_usuario: Not(2) },
],
take: 25,
skip: (parseInt(filtros.pagina) - 1) * 25,
})
.then((infoOperadores) => {
const operadores: Operador[] = [];
for (let i = 0; i < infoOperadores[0].length; i++)
operadores.push(
this.repository.create({
id_operador: infoOperadores[0][i].id_operador,
activo: infoOperadores[0][i].activo,
nombre: infoOperadores[0][i].nombre,
operador: infoOperadores[0][i].operador,
institucion: {
id_institucion: infoOperadores[0][i].id_operador,
institucion: infoOperadores[0][i].institucion,
},
tipoUsuario: {
id_tipo_usuario: infoOperadores[0][i].id_tipo_usuario,
tipo_usuario: infoOperadores[0][i].tipo_usuario,
},
}),
);
return [operadores];
}); });
if (institucion) }
query.andWhere('i.id_institucion = :id_institucion', {
id_institucion: institucion.id_institucion, findInfoOperador(institucion: Institucion, operador: string) {
}); return this.repository.findOne({
if (tipoUsuario) select: {
query.andWhere('tu.id_tipo_usuario = :id_tipo_usuario', { id_operador: true,
id_tipo_usuario: tipoUsuario.id_tipo_usuario, activo: true,
}); nombre: true,
return query.getManyAndCount(); password: true,
institucion: { id_institucion: true },
tipoUsuario: { id_tipo_usuario: true },
},
where: { operador, institucion },
});
}
findInfoOperadorAdmin(admin: string) {
return this.repository.findOne({
select: {
id_operador: true,
activo: true,
nombre: true,
password: true,
institucion: { id_institucion: true },
tipoUsuario: { id_tipo_usuario: true },
},
where: {
operador: admin,
tipoUsuario: { id_tipo_usuario: Between(2, 3) },
},
});
} }
findInfoOperadorById(id_operador: number) { findInfoOperadorById(id_operador: number) {
@ -164,62 +208,6 @@ export class OperadorService {
}); });
} }
informacionAdmin(admin: string) {
return this.fullInformacionOperadorView
.findOne({
where: {
operador: admin,
id_tipo_usuario: Between(2, 3),
},
})
.then((admin) => {
if (!admin) return { operador: null, activo: null, password: null };
return {
operador: {
id_operador: admin.id_operador,
nombre: admin.nombre,
operador: admin.operador,
institucion: admin.id_institucion
? { id_institucion: admin.id_institucion }
: null,
tipoUsuario: { id_tipo_usuario: admin.id_tipo_usuario },
},
activo: admin.activo,
password: admin.password,
};
});
}
informacionOperador(institucion: Institucion, operador: string) {
return this.fullInformacionOperadorView
.findOne({
where: { operador, id_institucion: institucion.id_institucion },
})
.then((operador) => {
if (!operador) return { operador: null, activo: null, password: null };
const o: {
id_operador: number;
nombre: string;
operador: string;
institucion: { id_institucion: number };
tipoUsuario: { id_tipo_usuario: number };
id_modulo?: number;
} = {
id_operador: operador.id_operador,
nombre: operador.nombre,
operador: operador.operador,
institucion: { id_institucion: operador.id_institucion },
tipoUsuario: { id_tipo_usuario: operador.id_tipo_usuario },
};
return {
operador: o,
activo: operador.activo,
password: operador.password,
};
});
}
passwordReset(admin: Operador, id_operador: number, password?: string) { passwordReset(admin: Operador, id_operador: number, password?: string) {
return this.findInfoOperadorById(id_operador) return this.findInfoOperadorById(id_operador)
.then((operador) => { .then((operador) => {