Untitled

mail@pastecode.io avatar
unknown
plain_text
2 years ago
42 kB
5
Indexable
Never
let {
  HttpUtils,
  STATUS,
} = require("quickwork-adapter-cli-server/http-library");

const {
  ContentTypes,
  HTTPMethods,
  contextResponse,
  errorResponse,
  successResponse,
  request,
} = HttpUtils;

let requestWithPromise = require("request");

let crypto = require("crypto");

const WEBHOOK_BASE_URL = "https://fad2-103-120-238-49.ngrok.io/notify";

const DB_CONTEXT_BASE_URL = "https://internal-context.quickwork.co";

const EMAIL_REGEX =
  /^(([^<>()[\]\\.,;:\s@"]+(\.[^<>()[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
const PHONE_REGEX = /^[+]?[(]?[0-9]{3}[)]?[-\s.]?[0-9]{3}[-\s.]?[0-9]{4,6}$/im;

let app = {
  title: "WhatsApp by textlocal",
  categories: ["Messaging", "Phone & SMS"],
  description: "",
  version: "1",
  alias: "whatsapp_by_textlocal",
  config: { authType: "api_key" },
  webhook_verification_required: true,
  webhook_ack_required: true,
  dbContextUrl: `${DB_CONTEXT_BASE_URL}/context/whatsapp_by_textlocal`,
  connection: {
    input_fields: () => [
      {
        key: "apiKey",
        name: "API key",
        controlType: "password",
        required: true,
        type: "string",
        hintText:
          "To get the API key of the app specified, go to <b>Dashboard</b> and click the <b>Settings</b> icon beside the app name. Scroll down the window and look for the API key under the </b>Request</b> code snippet.",
        helpText:
          "To get the API key of the app specified, go to <b>Dashboard</b> and click the <b>Settings</b> icon beside the app name. Scroll down the window and look for the API key under the </b>Request</b> code snippet.",
        isExtendedSchema: false,
      },
      {
        key: "appId",
        name: "App ID",
        hintText: "App ID",
        helpText: "App ID",
        required: true,
        isExtendedSchema: false,
        type: "string",
        controlType: "text",
      },
    ],

    authorization: {
      type: "api_key",

      credentials: (connection) => {
        let api = connection.input["apiKey"];

        let headers = {};
        headers["key"] = api;
        return headers;
      },
    },
  },
  actions: {
    send_template_message: {
      description: "Send template message",
      hint: "Send a <b>template message</b> via <b>WhatsApp by textlocal</b>",

      input_fields: () => [
        {
          key: "number",
          name: "Phone number",
          hintText: `User’s phone number on which you want to send the location. Unless you are setting the country code explicitly, the number must be in <a href = "en.wikipedia.org/wiki/E.164" target = "_blank">E.164</a> format. E.g., 916898234211. comma separated multiple numbers are allowed`,
          helpText: `User’s phone number on which you want to send the location. Unless you are setting the country code explicitly, the number must be in <a href = "en.wikipedia.org/wiki/E.164" target = "_blank">E.164</a> format. E.g., 916898234211. comma separated multiple numbers are allowed`,
          required: true,
          type: "string",
          controlType: "text",
          isExtendedSchema: false,
        },
        {
          key: "templateType",
          name: "Template type",
          hintText: "Template type default is text template",
          helpText: "Template type",
          required: false,
          isExtendedSchema: true,
          type: "string",
          controlType: "select",
          pickList: [
            ["Text", "text"],
            ["Image", "image"],
            ["Video", "video"],
            ["Document", "document"],
          ],
        },
        {
          key: "templateID",
          name: "Template ID",
          hintText: "The ID of the template that you want to send",
          helpText: "The ID of the template that you want to send",
          required: true,
          isExtendedSchema: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "params",
          name: "Params",
          hintText: "",
          helpText: "",
          required: false,
          isExtendedSchema: false,
          type: "array",
          controlType: "array",
          as: "object",
          properties: [
            {
              key: "value",
              name: "Value",
              hintText: "Enter the value for template value",
              helpText: "Enter the value for template value",
              required: true,
              isExtendedSchema: false,
              type: "string",
              controlType: "text",
            },
          ],
        },
      ],
      extendedSchema: async (connection, input) => {
        try {
          let extendedInput = [];
          let extendedOutput = [];
          let helpText = "";

          if (input.templateType !== "text") {
            extendedInput.push(
              {
                key: "fileUrl",
                name: "fileUrl",
                hintText: "fileUrl",
                helpText: "fileUrl",
                required: false,
                isExtendedSchema: false,
                type: "string",
                controlType: "text",
              },
              {
                key: "filename",
                name: "filename",
                hintText: "filename",
                helpText: "filename",
                required: false,
                isExtendedSchema: false,
                type: "string",
                controlType: "text",
              }
            );
          }

          return successResponse({
            input: extendedInput,
            output: extendedOutput,
            helpText,
          });
        } catch (error) {
          console.log(error);
          return errorResponse(error.message);
        }
      },

      execute: async (connection, input) => {
        try {
          let url = `https://api.imiconnect.io/resources/v1/messaging`;

          console.log("inputs are " + JSON.stringify(input, null, 3));
          let postBody = {
            appid: connection.input.appId,
            deliverychannel: "whatsapp",
            message: {
              template: input.templateID,
              parameters: {},
            },
            destination: [
              {
                waid: input.number.replace(/\s/g, "").split(","),
              },
            ],
          };

          if (input.params)
            input.params.forEach((param, index) => {
              postBody.message.parameters["variable" + (index + 1)] =
                param.value;
            });

          if (input.templateType !== "text") {
            postBody.message.parameters[input.templateType] = {
              link: input.fileUrl,
              filename: input.filename,
            };
          }

          console.log(
            "SEND TEMPLATE POSTBODY--------- " +
              JSON.stringify(postBody, null, 3)
          );
          let headers = app.connection.authorization.credentials(connection);
          const response = await HttpUtils.request(
            url,
            headers,
            null,
            HttpUtils.HTTPMethods.POST,
            postBody,
            HttpUtils.ContentTypes.JSON
          );

          console.log(
            "SEND TEMPLATE RESPONSE ---------" +
              JSON.stringify(response.body, null, 3)
          );
          if (response.success == true) {
            return successResponse(response.body);
          } else {
            return HttpUtils.errorResponse(response.body, response.statusCode);
          }
        } catch (error) {
          console.log(error);
          return HttpUtils.errorResponse(error.message);
        }
      },

      output_fields: () => [
        {
          key: "response",
          name: "Response",
          hintText: "Response",
          helpText: "Response",
          isExtendedSchema: false,
          required: false,
          type: "array",
          controlType: "array",
          as: "object",
          properties: [
            {
              key: "code",
              name: "Code",
              hintText: "Code",
              helpText: "Code",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
            {
              key: "transid",
              name: "Transid",
              hintText: "Transid",
              helpText: "Transid",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
            {
              key: "description",
              name: "Description",
              hintText: "Description",
              helpText: "Description",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
            {
              key: "correlationid",
              name: "Correlationid",
              hintText: "Correlationid",
              helpText: "Correlationid",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
          ],
        },
      ],
    },
    send_message: {
      description: "Send message",
      hint: "Send <b>message</b> via <b>WhatsApp by textlocal</b>",

      input_fields: () => [
        {
          key: "number",
          name: "Phone number",
          hintText: `User’s phone number on which you want to send the location. Unless you are setting the country code explicitly, the number must be in <a href = "en.wikipedia.org/wiki/E.164" target = "_blank">E.164</a> format. E.g., 916898234211. comma separated multiple numbers are allowed`,
          helpText: `User’s phone number on which you want to send the location. Unless you are setting the country code explicitly, the number must be in <a href = "en.wikipedia.org/wiki/E.164" target = "_blank">E.164</a> format. E.g., 916898234211. comma separated multiple numbers are allowed`,
          required: true,
          type: "string",
          controlType: "text",
          isExtendedSchema: false,
        },
        {
          key: "message",
          name: "message",
          hintText: "message",
          helpText: "message",
          required: true,
          isExtendedSchema: false,
          type: "string",
          controlType: "text",
        },
      ],

      execute: async (connection, input) => {
        try {
          let url = `https://api.imiconnect.io/resources/v1/messaging`;

          let postBody = {
            appid: connection.input.appId,
            deliverychannel: "whatsapp",
            channels: {
              "OTT-Messaging": {
                wa: {
                  type: "text",
                  text: {
                    body: input.message,
                  },
                },
              },
            },
            destination: [
              {
                waid: input.number.replace(/\s/g, "").split(","),
              },
            ],
          };

          console.log(
            "SEND MESSAGE POSTBODY--------- " +
              JSON.stringify(postBody, null, 3)
          );
          let headers = app.connection.authorization.credentials(connection);
          const response = await HttpUtils.request(
            url,
            headers,
            null,
            HttpUtils.HTTPMethods.POST,
            postBody,
            HttpUtils.ContentTypes.JSON
          );

          console.log(
            "SEND MESSAGE RESPONSE ---------" +
              JSON.stringify(response.body, null, 3)
          );
          if (response.success == true) {
            return successResponse(response.body);
          } else {
            return HttpUtils.errorResponse(response.body, response.statusCode);
          }
        } catch (error) {
          console.log(error);
          return HttpUtils.errorResponse(error.message);
        }
      },

      output_fields: () => [
        {
          key: "response",
          name: "Response",
          hintText: "Response",
          helpText: "Response",
          isExtendedSchema: false,
          required: false,
          type: "array",
          controlType: "array",
          as: "object",
          properties: [
            {
              key: "code",
              name: "Code",
              hintText: "Code",
              helpText: "Code",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
            {
              key: "transid",
              name: "Transid",
              hintText: "Transid",
              helpText: "Transid",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
            {
              key: "description",
              name: "Description",
              hintText: "Description",
              helpText: "Description",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
            {
              key: "correlationid",
              name: "Correlationid",
              hintText: "Correlationid",
              helpText: "Correlationid",
              isExtendedSchema: false,
              required: false,
              type: "string",
              controlType: "text",
            },
          ],
        },
      ],
    },
  },

  // webhook_ack: async (params, headers, body, res) => {
  //   return {
  //     body: "",
  //     responseHeaders: {
  //       "Content-Type": "application/x-www-form-urlencoded",
  //     },
  //   };
  // },

  webhook_keys: (params, headers, payload) => {
    try {
      console.log(
        "INSIDE WEBHOOK KEYS **************** " + JSON.stringify(payload)
      );
      console.log(
        "INSIDE WEBHOOK KEYS ----------- >" + JSON.stringify(headers)
      );
      if (headers["qw-userId"] && headers["qw-path"]) {
        console.log("RETURN FROM KEYS--->");
        console.log(
          new Buffer.from(
            `${headers["qw-userId"]}:${headers["qw-path"]}`
          ).toString("base64")
        );

        return new Buffer.from(
          `${headers["qw-userId"]}:${headers["qw-path"]}`
        ).toString("base64");
      }

      return undefined;
    } catch (error) {
      return undefined;
    }
  },

  triggers: {
    get_text_messages: {
      description: "New text message",
      hint: "Triggers when a <b>new text message is received</b> via <b>WhatsApp By textlocal</b>",
      type: "static_webhook",
      input_fields: () => [
        {
          key: "webhook_name",
          name: "Event",
          hintText: "Give name to your text event",
          helpText: "Give name to your text event",
          required: true,
          type: "string",
          controlType: "text",
          isExtendedSchema: true,
        },
      ],
      webhook_notification: async (
        connection,
        input,
        payload,
        params,
        headers
      ) => {
        try {
          (" **************** INSIDE NOTIFICATION TEXT TRIGGER **************** ");
          console.log(JSON.stringify(payload, null, 3));
          if (payload) {
            return HttpUtils.successResponse({ events: payload });
          }
        } catch (error) {
          console.log(error);
          return HttpUtils.errorResponse(error.message);
        }
      },
      extendedSchema: async (connection, input) => {
        console.log("INSIDE ES");
        let userAccountId = connection.userAccountId;
        let extendedInput = [],
          extendedOutput = [],
          helpText = "";

        const getHelpText = () => {
          if (input.webhook_name) {
            // let secret = "sk_" + cyrb53(connection.input.AuthenticationToken);
            let webhookUrl = `${WEBHOOK_BASE_URL}/${userAccountId}/${connection.input.appId}`;

            let webhookUrlTag = `<a id="webhook-url" href="${webhookUrl}" target="_blank">${webhookUrl}</a>`;

            return `${webhookUrlTag}<br>
              In your app settings, set up your <b>Callback URL</b> to the above URL.`;
          } else {
            return `Enter Webhook Name to get webhook url`;
          }
        };

        try {
          if (input.webhook_name) {
            helpText = getHelpText();
          }

          console.log(helpText);

          return HttpUtils.successResponse({
            input: extendedInput,
            output: extendedOutput,
            helpText,
          });
        } catch (error) {
          return HttpUtils.errorResponse(error.message);
        }
      },
      webhook_key: (connection, input) => {
        try {
          console.log("INSIDE WEBHOOK KEY");
          // let secret = "sk_" + cyrb53(connection.input.AuthenticationToken);

          console.log("RETURN FROM KEY--->");
          console.log(
            new Buffer.from(
              `${connection.userAccountId}:${connection.input.appId}`
            ).toString("base64")
          );

          return new Buffer.from(
            `${connection.userAccountId}:${connection.input.appId}`
          ).toString("base64");
        } catch (error) {
          console.log(error);
          return undefined;
        }
      },

      output_fields: () => [
        {
          key: "channel",
          name: "Channel",
          hintText: "Channel",
          helpText: "Channel",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "appId",
          name: "App Id",
          hintText: "App Id",
          helpText: "App Id",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "event",
          name: "Event",
          hintText: "Event",
          helpText: "Event",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "waid",
          name: "Waid",
          hintText: "Waid",
          helpText: "Waid",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "message",
          name: "Message",
          hintText: "Message",
          helpText: "Message",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "attachments",
          name: "Attachments",
          hintText: "Attachments",
          helpText: "Attachments",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "system",
          name: "System",
          hintText: "System",
          helpText: "System",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "location",
          name: "Location",
          hintText: "Location",
          helpText: "Location",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "ts",
          name: "Ts",
          hintText: "Ts",
          helpText: "Ts",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
        {
          key: "tid",
          name: "Tid",
          hintText: "Tid",
          helpText: "Tid",
          isExtendedSchema: false,
          required: false,
          type: "string",
          controlType: "text",
        },
      ],
    },
  },
  test: async (connection) => {
    // return successResponse({ success: true });
    try {
      let url = `https://api.imiconnect.io/resources/v1/messaging`;

      let postBody = {
        appid: connection.input.appId,
        deliverychannel: "whatsapp",
        channels: {
          "OTT-Messaging": {
            wa: {
              type: "text",
              text: {
                body: "hello",
              },
            },
          },
        },
        destination: [
          {
            waid: [91918],
          },
        ],
      };

      console.log(
        "SEND MESSAGE POSTBODY--------- " + JSON.stringify(postBody, null, 3)
      );
      let headers = app.connection.authorization.credentials(connection);
      const response = await request(
        url,
        headers,
        null,
        HttpUtils.HTTPMethods.POST,
        postBody,
        HttpUtils.ContentTypes.JSON
      );

      console.log("TEST RESPONSE " + JSON.stringify(response, null, 3));

      if (
        response.body.response &&
        response.body.response.description &&
        response.body.response.description === "Invalid app ID"
      ) {
        return errorResponse(response.body.response.description);
      }
      if (
        response.body.response &&
        response.body.response.description &&
        response.body.response.description === "Authentication failed."
      ) {
        return errorResponse(response.body.response.description);
      }

      if (response.body.response.description === "Invalid JSON") {
        return errorResponse("Authentication failed.", 400);
      }

      console.log("f" + JSON.stringify(response, null, 3));
      if (response.success === true) {
        return successResponse({ success: true });
      }
      return errorResponse(response.body, response.statusCode);
    } catch (error) {
      console.log(error);
      return errorResponse(error.message);
    }
  },
  objectDefinitions: {},
  pickLists: {},
};

const contextHandler = async (
  contextObject,
  connection,
  input,
  event,
  triggerType
) => {
  try {
    let validTextResult = validateEventText(event, contextObject);

    if (validTextResult.success == true) {
      return validTextResult;
    } else {
      let sendRetryHelpResponse = await app.actions.send_message.execute(
        connection,
        {
          number: event.senderId,
          message: validTextResult.answer,
          hideMessageContentInAgentDashboard: JSON.parse(contextObject.input)
            .hideMessageContentInAgentDashboard,
        }
      );

      if (sendRetryHelpResponse.success == true) {
        if (
          sendRetryHelpResponse.response &&
          typeof sendRetryHelpResponse.response == "string"
        ) {
          sendRetryHelpResponse.response = JSON.parse(
            sendRetryHelpResponse.response
          );
        }
        validTextResult["retryHelpMessageId"] =
          sendRetryHelpResponse.response &&
          sendRetryHelpResponse.response.messageId;
        return validTextResult;
      } else {
        return {
          success: false,
          answer: "Could not send Retry Help Message to User",
        };
      }
    }
  } catch (error) {
    console.log(error);
    return {
      success: false,
      answer: error.message,
    };
  }
};

const validateEventText = (event, contextObject) => {
  let data = undefined;
  try {
    switch (JSON.parse(contextObject.input).answerType) {
      case "string":
        if (event.text) {
          data = {
            success: true,
            answer: event.text,
          };
        }
        break;
      case "number":
        if (!isNaN(event.text)) {
          data = {
            success: true,
            answer: event.text,
          };
        }
        break;
      case "email":
        if (EMAIL_REGEX.test(event.text.toLowerCase())) {
          data = {
            success: true,
            answer: event.text,
          };
        }
        break;

      case "phone":
        if (PHONE_REGEX.test(event.text)) {
          data = {
            success: true,
            answer: event.text,
          };
        }
        break;

      case "imageUpload":
        if (event.url && event.type == "image") {
          data = {
            success: true,
            answer: { fileUrl: event.url },
          };
        }
        break;
      case "file":
        if (event.url && event.type == "file") {
          data = {
            success: true,
            answer: { fileUrl: event.url },
          };
        }
        break;

      case "video":
        if (event.url && event.type == "video") {
          data = {
            success: true,
            answer: { fileUrl: event.url },
          };
        }
        break;

      case "audio":
        if (event.url && event.type == "audio") {
          data = {
            success: true,
            answer: { fileUrl: event.url },
          };
        }
        break;

      case "any_media":
        if (
          event.url &&
          event.type &&
          ["image", "file", "video", "audio"].includes(event.type)
        ) {
          data = {
            success: true,
            answer: { fileUrl: event.url },
          };
        }
        break;

      case "location":
        if (event.type == "location" && event.latitude && event.longitude) {
          data = {
            success: true,
            answer: { latitude: event.latitude, longitude: event.longitude },
          };
        }
        break;

      case "contacts":
        if (event.type == "contacts" && event.contacts) {
          data = {
            success: true,
            answer: { contacts: event.contacts },
          };
        }
        break;

      case "matchRegularExpression":
        {
          let parsedInput = JSON.parse(contextObject.input);
          let rgEx = parsedInput.regularExpression;
          let flags = parsedInput.regularExpressionFlags || undefined;
          let regularExpression = new RegExp(rgEx, flags);
          if (
            event.text &&
            typeof event.text == "string" &&
            regularExpression.test(event.text)
          ) {
            data = {
              success: true,
              answer: event.text,
            };
          }
        }

        break;
      case "buttonTemplate":
        {
          let contextData = JSON.parse(contextObject.data);

          let sentQuestionId = contextData.sentQuestionId;
          let questionMessageId = contextData.questionMessageId;
          if (
            questionMessageId &&
            event.context &&
            event.context.gsId &&
            questionMessageId === event.context.gsId
          ) {
            data = {
              success: true,
              answer: {
                text: event.text,
                type: event.payloadType,
                context: event.context,
              },
            };
          }

          if (
            sentQuestionId &&
            event.context &&
            event.context.gsId &&
            sentQuestionId === event.context.gsId
          ) {
            data = {
              success: true,
              answer: {
                text: event.text,
                type: event.payloadType,
                context: event.context,
              },
            };
          }
        }

        break;

      default:
        data = {
          success: false,
          answer: JSON.parse(contextObject.input).retryHelp,
        };
    }

    if (!data) {
      data = {
        success: false,
        answer: JSON.parse(contextObject.input).retryHelp,
      };
    }

    return data;
  } catch (error) {
    console.log(error);
    if (!data) {
      data = {
        success: false,
        answer: JSON.parse(contextObject.input).retryHelp,
      };
    }
    return data;
  }
};

// eslint-disable-next-line no-unused-vars
const getFileContentType = async (url) => {
  return new Promise((resolve, reject) => {
    try {
      let req = requestWithPromise
        .get(url)
        .on("response", (response) => {
          let contentType = undefined;
          if (response.headers["content-type"]) {
            contentType = response.headers["content-type"];
          }

          if (response.headers["Content-Type"]) {
            contentType = response.headers["Content-Type"];
          }

          if (contentType) {
            resolve({
              success: true,
              data: contentType,
            });
          } else {
            resolve({ success: false, data: "no content type found in url" });
          }
          req.abort();
        })
        .on("error", (error) => {
          resolve({
            success: false,
            data: "no content type found in url" + error.message,
          });
        });
    } catch (error) {
      resolve({
        success: false,
        statusCode: STATUS.INTERNAL_SERVER_ERROR.CODE,
        data: error.message,
      });
    }
  });
};

const locationAnswer = [
  {
    key: "latitude",
    name: "Latitude",
    helpText: "Latitude",
    hintText: "Latitude",
    required: true,
    isExtendedSchema: false,
    controlType: "text",
    type: "number",
  },
  {
    key: "longitude",
    name: "Longitude",
    helpText: "Longitude",
    hintText: "Longitude",
    required: true,
    isExtendedSchema: false,
    controlType: "text",
    type: "number",
  },
];

const contactAnswer = [
  {
    key: "contacts",
    name: "Contacts",
    hintText: "Contacts",
    helpText: "Contacts",
    isExtendedSchema: false,
    required: false,
    type: "array",
    controlType: "array",
    as: "object",
    properties: [
      {
        key: "addresses",
        name: "Addresses",
        hintText: "Addresses",
        helpText: "Addresses",
        isExtendedSchema: false,
        required: false,
        type: "array",
        controlType: "array",
        as: "object",
        properties: [
          {
            key: "country_code",
            name: "Country Code",
            hintText: "Country Code",
            helpText: "Country Code",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "street",
            name: "Street",
            hintText: "Street",
            helpText: "Street",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "type",
            name: "Type",
            hintText: "Type",
            helpText: "Type",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
        ],
      },
      {
        key: "emails",
        name: "Emails",
        hintText: "Emails",
        helpText: "Emails",
        isExtendedSchema: false,
        required: false,
        type: "array",
        controlType: "array",
        as: "object",
        properties: [
          {
            key: "email",
            name: "Email",
            hintText: "Email",
            helpText: "Email",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "type",
            name: "Type",
            hintText: "Type",
            helpText: "Type",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
        ],
      },
      {
        key: "name",
        name: "Name",
        hintText: "Name",
        helpText: "Name",
        isExtendedSchema: false,
        required: false,
        type: "object",
        controlType: "object",
        properties: [
          {
            key: "first_name",
            name: "First Name",
            hintText: "First Name",
            helpText: "First Name",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "formatted_name",
            name: "Formatted Name",
            hintText: "Formatted Name",
            helpText: "Formatted Name",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "last_name",
            name: "Last Name",
            hintText: "Last Name",
            helpText: "Last Name",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "middle_name",
            name: "Middle Name",
            hintText: "Middle Name",
            helpText: "Middle Name",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "prefix",
            name: "Prefix",
            hintText: "Prefix",
            helpText: "Prefix",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
        ],
      },
      {
        key: "org",
        name: "Org",
        hintText: "Org",
        helpText: "Org",
        isExtendedSchema: false,
        required: false,
        type: "object",
        controlType: "object",
        properties: [
          {
            key: "company",
            name: "Company",
            hintText: "Company",
            helpText: "Company",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "title",
            name: "Title",
            hintText: "Title",
            helpText: "Title",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
        ],
      },
      {
        key: "phones",
        name: "Phones",
        hintText: "Phones",
        helpText: "Phones",
        isExtendedSchema: false,
        required: false,
        type: "array",
        controlType: "array",
        as: "object",
        properties: [
          {
            key: "phone",
            name: "Phone",
            hintText: "Phone",
            helpText: "Phone",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "type",
            name: "Type",
            hintText: "Type",
            helpText: "Type",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "wa_id",
            name: "Wa Id",
            hintText: "Wa Id",
            helpText: "Wa Id",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
        ],
      },
      {
        key: "urls",
        name: "Urls",
        hintText: "Urls",
        helpText: "Urls",
        isExtendedSchema: false,
        required: false,
        type: "array",
        controlType: "array",
        as: "object",
        properties: [
          {
            key: "type",
            name: "Type",
            hintText: "Type",
            helpText: "Type",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
          {
            key: "url",
            name: "Url",
            hintText: "Url",
            helpText: "Url",
            isExtendedSchema: false,
            required: false,
            type: "string",
            controlType: "text",
          },
        ],
      },
    ],
  },
];

const textAnswer = [
  {
    key: "answer",
    name: "Answer",
    helpText: "Answer",
    hintText: "Answer",
    type: "string",
    controlType: "text",
    required: false,
    isExtendedSchema: false,
  },
];

const BUTTON_TEMPLATE_ANSWER = [
  {
    key: "text",
    name: "Text",
    hintText: "Text",
    helpText: "Text",
    required: false,
    isExtendedSchema: false,
    type: "string",
    controlType: "text",
  },
  {
    key: "type",
    name: "Type",
    hintText: "Type",
    helpText: "Type",
    required: false,
    isExtendedSchema: false,
    type: "string",
    controlType: "text",
  },
  {
    key: "context",
    name: "Context",
    hintText: "Context",
    helpText: "Context",
    required: false,
    isExtendedSchema: false,
    type: "object",
    controlType: "object",
    properties: [
      {
        key: "id",
        name: "Id",
        hintText: "Id",
        helpText: "Id",
        required: false,
        isExtendedSchema: false,
        type: "string",
        controlType: "text",
      },
      {
        key: "gsId",
        name: "GSID",
        hintText: "GSID",
        helpText: "GSID",
        required: false,
        isExtendedSchema: false,
        type: "string",
        controlType: "text",
      },
    ],
  },
];

const mediaAnswer = [
  {
    key: "fileUrl",
    name: "File Url",
    helpText: "File Url",
    hintText: "File Url",
    type: "string",
    controlType: "text",
    required: false,
    isExtendedSchema: false,
  },
  {
    key: "caption",
    name: "Caption",
    hintText: "Caption",
    helpText: "Caption",
    isExtendedSchema: false,
    required: false,
    type: "string",
    controlType: "text",
  },
  {
    key: "type",
    name: "Type",
    hintText: "Type",
    helpText: "Type",
    isExtendedSchema: false,
    required: false,
    type: "string",
    controlType: "text",
  },
  {
    key: "contentType",
    name: "Content Type",
    hintText: "Content Type",
    helpText: "Content Type",
    isExtendedSchema: false,
    required: false,
    type: "string",
    controlType: "text",
  },
];

const regularExpressionField = {
  key: "regularExpression",
  name: "Regular expression",
  hintText: `Enter regular expression you want to match the answer with. Eg regex: <b>abc+</b> for ab followed by one or more c<br><b>Note</b>: Do not use literal notation in regular expression ie /ab+c/ but use ab+c`,
  helpText: `Enter regular expression you want to match the answer with. Eg regex: <b>abc+</b> for ab followed by one or more c<br><b>Note</b>: Do not use literal notation in regular expression ie /ab+c/ but use ab+c`,
  type: "string",
  controlType: "text",
  required: true,
  isExtendedSchema: false,
};

const regularExpressionFlagsField = {
  key: "regularExpressionFlags",
  name: "Regular expression flags",
  hintText: `Flags to add in the <b>Regular expression</b>. Supported flags are: d (indices), g (global match), i (ignore case), m (multiline), s ("dotAll"), u (unicode) and y (sticky). E.g., <b>gi</b> will use the following <b>flags global</b> match and <b>ignore case</b.`,
  helpText: `Flags to add in the <b>Regular expression</b>. Supported flags are: d (indices), g (global match), i (ignore case), m (multiline), s ("dotAll"), u (unicode) and y (sticky). E.g., <b>gi</b> will use the following <b>flags global</b> match and <b>ignore case</b.`,
  required: false,
  isExtendedSchema: false,
  type: "string",
  controlType: "text",
};

const HIDE_MESSAGE_CONTENT_IN_AGENT_DASHBOARD = {
  key: "hideMessageContentInAgentDashboard",
  name: "Hide Question Content in Quickwork Agent Dashboard ?",
  helpText:
    "If selected Yes, Hidden message will appear in Quickwork Agent Dashboard",
  hintText:
    "If selected Yes, Hidden message will appear in Quickwork Agent Dashboard",
  required: false,
  isExtendedSchema: false,
  type: "boolean",
  controlType: "select",
  pickList: [
    ["Yes", true],
    ["No", false],
  ],
};

const HIDE_ANSWER_IN_DASHBOARD = {
  key: "hideAnswerInDashboard",
  name: "Hide User's answer in Quickwork Agent Dashboard ?",
  helpText:
    "If selected Yes, Hidden message will appear in Quickwork Agent Dashboard",
  hintText:
    "If selected Yes, Hidden message will appear in Quickwork Agent Dashboard",
  required: false,
  isExtendedSchema: false,
  type: "boolean",
  controlType: "select",
  pickList: [
    ["Yes", true],
    ["No", false],
  ],
};

const isValidJsonString = (str) => {
  try {
    let json = JSON.parse(str);
    if (typeof json == "object") {
      if (json) {
        return true;
      }
      return false;
    } else {
      return false;
    }
  } catch (e) {
    return false;
  }
};

module.exports = app;