lecoffre-back/src/app/api/customer/AuthController.ts
2023-11-27 17:36:46 +01:00

181 lines
5.2 KiB
TypeScript

import { Response, Request } from "express";
import { Controller, Post } from "@ControllerPattern/index";
import ApiController from "@Common/system/controller-pattern/ApiController";
import { Service } from "typedi";
import CustomersService, {
InvalidPasswordError,
InvalidTotpCodeError,
NotRegisteredCustomerError,
PasswordAlreadySetError,
SmsNotExpiredError,
TotpCodeExpiredError,
} from "@Services/customer/CustomersService/CustomersService";
import AuthService from "@Services/common/AuthService/AuthService";
import { Customer } from "le-coffre-resources/dist/SuperAdmin";
@Controller()
@Service()
export default class AuthController extends ApiController {
constructor(private customerService: CustomersService, private authService: AuthService) {
super();
}
@Post("/api/v1/customer/auth/mail/verify-sms")
protected async mailVerifySms(req: Request, response: Response) {
const email = req.body["email"];
if (!email) {
this.httpBadRequest(response, "Email is required");
return;
}
try {
const customer = await this.customerService.verifyEmail2FASms(email);
if (!customer) {
this.httpNotFoundRequest(response, "Customer not found");
return;
}
this.httpSuccess(response, { partialPhoneNumber: customer.contact?.cell_phone_number.replace(/\s/g, "").slice(-4) });
} catch (error) {
if (error instanceof SmsNotExpiredError) {
this.httpTooEarlyRequest(response, error.message);
return;
}
console.log(error);
this.httpInternalError(response);
}
}
@Post("/api/v1/customer/auth/login")
protected async login(req: Request, response: Response) {
const email = req.body["email"];
const totpCode = req.body["totpCode"];
const password = req.body["password"];
if (!email) {
this.httpBadRequest(response, "email is required");
return;
}
if (!totpCode) {
this.httpBadRequest(response, "totpCode is required");
return;
}
if (!password) {
this.httpBadRequest(response, "password is required");
return;
}
try {
const customer = await this.customerService.login(email, totpCode, password);
if (!customer) {
this.httpBadRequest(response, "Customer not found");
return;
}
const customerHydrated = Customer.hydrate<Customer>(customer);
const payload = await this.authService.getCustomerJwtPayload([customerHydrated]);
const accessToken = this.authService.generateAccessToken(payload);
const refreshToken = this.authService.generateRefreshToken(payload);
this.httpSuccess(response, { accessToken, refreshToken });
} catch (error) {
if (error instanceof TotpCodeExpiredError || error instanceof NotRegisteredCustomerError) {
this.httpBadRequest(response, error.message);
return;
}
if (error instanceof InvalidTotpCodeError || error instanceof InvalidPasswordError) {
this.httpUnauthorized(response, error.message);
return;
}
console.log(error);
this.httpInternalError(response);
return;
}
}
@Post("/api/v1/customer/auth/set-password")
protected async setPassword(req: Request, response: Response) {
const email = req.body["email"];
const totpCode = req.body["totpCode"];
const password = req.body["password"];
if (!email) {
this.httpBadRequest(response, "Email is required");
return;
}
if (!totpCode) {
this.httpBadRequest(response, "Sms code is required");
return;
}
if (!password) {
this.httpBadRequest(response, "Password is required");
return;
}
try {
const customer = await this.customerService.setFirstPassword(email, totpCode, password);
if (!customer) {
this.httpBadRequest(response, "Customer not found");
return;
}
const customerHydrated = Customer.hydrate<Customer>(customer);
const payload = await this.authService.getCustomerJwtPayload([customerHydrated]);
const accessToken = this.authService.generateAccessToken(payload);
const refreshToken = this.authService.generateRefreshToken(payload);
this.httpSuccess(response, { accessToken, refreshToken });
} catch (error) {
if (error instanceof TotpCodeExpiredError || error instanceof PasswordAlreadySetError) {
this.httpBadRequest(response, error.message);
return;
}
if (error instanceof InvalidTotpCodeError) {
this.httpUnauthorized(response, error.message);
return;
}
console.log(error);
this.httpInternalError(response);
return;
}
}
@Post("/api/v1/customer/auth/verify-totp-code")
protected async verifyTotpCode(req: Request, response: Response) {
const totpCode = req.body["totpCode"];
const email = req.body["email"];
if (!totpCode) {
this.httpBadRequest(response, "totpCode is required");
return;
}
if (!email) {
this.httpBadRequest(response, "email is required");
return;
}
try {
const code = await this.customerService.verifyTotpCode(totpCode, email);
if (!code) {
this.httpNotFoundRequest(response, "Customer not found");
return;
}
this.httpSuccess(response, {
validCode: true,
reason: code.reason,
});
} catch (error) {
if (error instanceof InvalidTotpCodeError || error instanceof TotpCodeExpiredError) {
this.httpUnauthorized(response, error.message);
return;
}
console.log(error);
this.httpInternalError(response);
}
}
}