end-user.js 10 KB
"use strict";

/**
 * end-user controller
 */

const { factories } = require("@strapi/strapi");

const { getService } = require("@strapi/plugin-users-permissions/server/utils");
const utils = require("@strapi/utils");
const { sanitize } = utils;
const { ValidationError } = utils.errors;
module.exports = factories.createCoreController(
  "api::end-user.end-user",
  ({ strapi: Strapi }) => ({
    // Method 1: Creating an entirely custom action
    // async finishEndUserOtpVerification(ctx) {
    //   (await strapi.service) <
    //     PostService >
    //     "api::post.post".exampleService({});
    //   try {
    //     ctx.body = "ok";
    //   } catch (err) {
    //     ctx.body = err;
    //   }
    // },

    // Method 1: Creating an entirely custom action
    async finishEndUserOtpVerification(ctx) {
      const { mobileNo, oneTimePassword } = ctx.request.body;
      // console.log(">>>>>> One", ctx.request.body);
      // 1. Identify the end-user record using the above.
      const endUser = await strapi.query("api::end-user.end-user").findOne({
        populate: ["user"],
        where: {
          $and: [{ publishedAt: { $null: true } }, { mobileNo: mobileNo }],
        },
      });

      if (!endUser) {
        throw new ValidationError("Invalid mobile number.");
      }
      // console.log(" >>>> two ", endUser);
      // 2. Then identify the user record using step 1.
      // 3. Verify otp.
      const user = await strapi
        .query("plugin::users-permissions.user")
        .findOne({
          where: {
            $and: [
              { id: endUser.user.id },
              { oneTimePassword: oneTimePassword },
            ],
          },
        });
      if (!user || user.blocked) {
        throw new ValidationError("Code provided is not valid.");
      }

      try {
        console.log("inside try", user.email);
        const spretoLeadData = await strapi
          .service("api::end-user.end-user")
          .sendLeadToSperto({ ...endUser, email: user.email }, "Y");
        // console.log("spretoLeadData.data", spretoLeadData.data);
        ctx.request.body.httpRequestIsVerifiedHeaders = JSON.stringify(
          spretoLeadData.headers
        );

        ctx.request.body.httpRequestIsVerifiedMethod =
          spretoLeadData.config.method;
        ctx.request.body.httpRequestIsVerifiedUrl = spretoLeadData.config.url;
        ctx.request.body.httpsRequestIsVerifiedBody =
          spretoLeadData.config.data;
        ctx.request.body.httpResposneIsVerifiedBody = JSON.stringify(
          spretoLeadData.data
        );
        ctx.request.body.thirdPartyApiError = false;
      } catch (error) {
        console.log(error);
        ctx.request.body.httpRequestIsVerifiedHeaders = JSON.stringify(
          error.config.headers
        );
        ctx.request.body.httpRequestIsVerifiedMethod = error.config.method;
        ctx.request.body.httpRequestIsVerifiedUrl = error.config.url;
        ctx.request.body.httpsRequestIsVerifiedBody = error.config.data;
        ctx.request.body.httpResposneIsVerifiedBody = JSON.stringify(
          error.message
        );
        ctx.request.body.thirdPartyApiError = true;
      }

      // 4. stamp otp in user to null.
      await getService("user").edit(user.id, {
        oneTimePassword: null,
        password: oneTimePassword,
      });

      // 5. change from draft to published.
      await strapi.entityService.update("api::end-user.end-user", endUser.id, {
        data: {
          publishedAt: new Date(),
          httpRequestIsVerifiedHeaders:
            ctx.request.body.httpRequestIsVerifiedHeaders,
          httpsRequestIsVerifiedBody:
            ctx.request.body.httpsRequestIsVerifiedBody,
          httpRequestIsVerifiedUrl: ctx.request.body.httpRequestIsVerifiedUrl,
          httpRequestIsVerifiedMethod:
            ctx.request.body.httpRequestIsVerifiedMethod,
          httpResposneIsVerifiedBody:
            ctx.request.body.httpResposneIsVerifiedBody,
        },
      });

      // TODO: at this point we might have to invoke a Hiranandani API to send the newly registered user there.
      ctx.send({ ok: true, message: "user registered" });
    },

    // Wrapping a core action (leaves core logic in place)
    async create(ctx) {
      // console.log("ctx.request.body", ctx.request.body);
      try {
        const spretoLeadData = await strapi
          .service("api::end-user.end-user")
          .sendLeadToSperto(ctx.request.body.data, "N");
        // console.log("spretoLeadData.data", spretoLeadData.data);
        ctx.request.body.data.httpRequestHeaders = JSON.stringify(
          spretoLeadData.headers
        );
        ctx.request.body.data.httpRequestMethod = spretoLeadData.config.method;
        ctx.request.body.data.httpRequestUrl = spretoLeadData.config.url;
        ctx.request.body.data.httpsRequestBody = spretoLeadData.config.data;
        ctx.request.body.data.httpResposneBody = JSON.stringify(
          spretoLeadData.data
        );
        ctx.request.body.data.thirdPartyApiError = false;
      } catch (error) {
        ctx.request.body.data.httpRequestHeaders = JSON.stringify(
          error.config.headers
        );
        ctx.request.body.data.httpRequestMethod = error.config.method;
        ctx.request.body.data.httpRequestUrl = error.config.url;
        ctx.request.body.data.httpsRequestBody = error.config.data;
        ctx.request.body.data.httpResposneBody = JSON.stringify(error.message);
        ctx.request.body.data.thirdPartyApiError = true;
      }
      const currentUser = ctx.state.user;
      // 2. check if the current user already has an existing business listing (existingEndUser) against their name.
      const existingEndUser = await strapi.entityService.findMany(
        "api::end-user.end-user",
        {
          fields: ["id"],
          filters: { mobileNo: ctx.request.body.data.mobileNo },
        }
      );

      const oneTimePassword = Math.floor(100000 + Math.random() * 900000);

      const emailToSend = {
        oneTimePassword: oneTimePassword,
        to: ctx.request.body.data.email,
        from: `contact@hiranandani.net`,
        // replyTo: undefined,
        subject: `Your Request for One Time Password`,
        text: `Hello ${"Jay Mehta"}, Your one time password to login to your end user portal is ${oneTimePassword}`,
        html: `<p>Dear ${ctx.request.body.data.fullName},
        Your OTP for Hiranandani Exclusive website login is <strong>${oneTimePassword}</strong> . Valid for 10 minutes. Please do not
        share this OTP.
        
        Regards,
        Hiranandani Team.`,
      };

      // NOTE: Update the user before sending the email so an Admin can generate the link if the email fails

      await strapi.entityService.update(
        "plugin::users-permissions.user",
        currentUser.id,
        {
          data: {
            oneTimePassword: `${oneTimePassword}`,
          },
        }
      );
      ctx.request.body.data = { ...ctx.request.body.data, emailToSend };
      console.log("ctx.request.body.data", ctx.request.body.data);
      // Send an email to the user.
      // await strapi.plugin("email").service("email").send(emailToSend).sendOTPToSpreto({...ctx.request.body.data,body: emailToSend });
      try {
        const spretoOTP = await strapi
          .service("api::end-user.end-user")
          .sendOTPToSpreto(ctx.request.body.data);
        console.log("spretoOTP>>>>>>>>", spretoOTP);
        ctx.request.body.data.httpRequestEmailHeaders = JSON.stringify(
          spretoOTP.spertoEmailResponse.headers
        );
        ctx.request.body.data.httpRequestEmailMethod =
          spretoOTP.spertoEmailResponse.config.method;
        ctx.request.body.data.httpRequestEmailUrl =
          spretoOTP.spertoEmailResponse.config.url;
        ctx.request.body.data.httpsRequestEmailBody =
          spretoOTP.spertoEmailResponse.config.data;
        ctx.request.body.data.httpResposneEmailBody = JSON.stringify(
          spretoOTP.spertoEmailResponse.data
        );

        ctx.request.body.data.httpSMSRequestHeaders = JSON.stringify(
          spretoOTP.spertoEmailResponse.headers
        );
        ctx.request.body.data.httpSMSRequestMethod =
          spretoOTP.spertoEmailResponse.config.method;
        ctx.request.body.data.httpSMSRequestUrl =
          spretoOTP.spertoEmailResponse.config.url;
        ctx.request.body.data.httpsSMSRequestBody =
          spretoOTP.spertoEmailResponse.config.data;
        ctx.request.body.data.httpSMSResposneBody = JSON.stringify(
          spretoOTP.spertoEmailResponse.data
        );

        ctx.request.body.data.thirdPartyApiError = false;
      } catch (error) {
        ctx.request.body.data.httpRequestEmailHeaders = JSON.stringify(
          error.config.headers
        );
        ctx.request.body.data.httpRequestEmailMethod = error.config.method;
        ctx.request.body.data.httpRequestEmailUrl = error.config.url;
        ctx.request.body.data.httpsRequestEmailBody = error.config.data;
        ctx.request.body.data.httpResposneEmailBody = JSON.stringify(
          error.message
        );

        ctx.request.body.data.httpSMSRequestHeaders = JSON.stringify(
          error.config.headers
        );
        ctx.request.body.data.httpSMSRequestMethod = error.config.method;
        ctx.request.body.data.httpSMSRequestUrl = error.config.url;
        ctx.request.body.data.httpsSMSRequestBody = error.config.data;
        ctx.request.body.data.httpSMSResposneBody = JSON.stringify(
          error.message
        );
        ctx.request.body.data.thirdPartyApiError = true;
      }

      // TODO: Send SMS.

      if (existingEndUser && existingEndUser.length !== 0) {
        console.log(`Found existing end user: `);
        console.log(existingEndUser);

        // This makes sure that we are updating the existing business listing only.
        ctx.params.id = existingEndUser[0].id;
        return super.update(ctx);
      } else {
        // We make sure that the newly created listing is created against the current business owner.
        ctx.request.body.data["user"] = currentUser.id;

        // Now go ahead and create the listing.
        return await super.create(ctx);
      }
    },
  })
);