feat: Adapt migration from Dialogflow to Redis-based bot and optimize bot access using Redis
parent
ad89d3ccdb
commit
bc93d3a9d6
|
@ -0,0 +1,176 @@
|
||||||
|
import { Request, Response } from "express";
|
||||||
|
import BotIsOnQueue from "../helpers/BotIsOnQueue";
|
||||||
|
import GetDefaultWhatsApp from "../helpers/GetDefaultWhatsApp";
|
||||||
|
import { getIO } from "../libs/socket";
|
||||||
|
import { getWbot } from "../libs/wbot";
|
||||||
|
import Ticket from "../models/Ticket";
|
||||||
|
import ContactByCustomField from "../services/HitServices/ShowContactByCustomFieldValueService";
|
||||||
|
import ShowQueueService from "../services/QueueService/ShowQueueService";
|
||||||
|
import CreateTicketService from "../services/TicketServices/CreateTicketService";
|
||||||
|
import ShowTicketService from "../services/TicketServices/ShowTicketService";
|
||||||
|
import UpdateTicketService from "../services/TicketServices/UpdateTicketService";
|
||||||
|
import SendWhatsAppMessage from "../services/WbotServices/SendWhatsAppMessage";
|
||||||
|
|
||||||
|
import { Op, where, Sequelize } from "sequelize";
|
||||||
|
import ShowTicketServiceByContactId from "../services/TicketServices/ShowTicketServiceByContactId";
|
||||||
|
import hitPortalMonitoring from "../helpers/HitPortalMonitoring";
|
||||||
|
import FindOrCreateTicketServiceBot from "../services/TicketServices/FindOrCreateTicketServiceBot";
|
||||||
|
import Contact from "../models/Contact";
|
||||||
|
|
||||||
|
// type IndexQuery = {
|
||||||
|
// centro_custo: string;
|
||||||
|
// };
|
||||||
|
|
||||||
|
export const hit = async (req: Request, res: Response): Promise<Response> => {
|
||||||
|
console.log("req.body: ", req.body);
|
||||||
|
|
||||||
|
if (req.headers["auth"] === "0424bd59b807674191e7d77572075f33") {
|
||||||
|
let contact = null;
|
||||||
|
|
||||||
|
try {
|
||||||
|
contact = await ContactByCustomField(req.body["centro_custo"]);
|
||||||
|
} catch (error) {
|
||||||
|
console.log("There was an error on try get centro_custo info: ", error);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!contact) {
|
||||||
|
return res.status(200).json({ message: "Ok" });
|
||||||
|
}
|
||||||
|
|
||||||
|
if (req.body["action"] === "atdfechou") {
|
||||||
|
console.log("FECHOU");
|
||||||
|
|
||||||
|
try {
|
||||||
|
console.log("atdfechou ----------> THE CONTACT: ", contact);
|
||||||
|
|
||||||
|
let data = req.body;
|
||||||
|
let str = "";
|
||||||
|
let str2 = "";
|
||||||
|
|
||||||
|
str = `*Cliente*: ${contact["contact.name"]}`;
|
||||||
|
|
||||||
|
let historico = data["historico"];
|
||||||
|
|
||||||
|
for (const key in historico) {
|
||||||
|
const hist = Object.keys(historico[key]);
|
||||||
|
|
||||||
|
hist.forEach((keys, index) => {
|
||||||
|
str2 += `*${keys}*: ${historico[key][keys]}\n`;
|
||||||
|
});
|
||||||
|
|
||||||
|
str2 += "\n";
|
||||||
|
}
|
||||||
|
|
||||||
|
await statuschange(
|
||||||
|
req,
|
||||||
|
res,
|
||||||
|
contact,
|
||||||
|
`*Olá. Somos a TI Espaçolaser.*\nO chamado da sua loja ${contact["contact.name"]} foi fechado pela operadora. Abaixo seguem informações sobre o incidente.\n\n*Situação do chamado na Operadora*\n\n*Incidente:*\n\n ${str}\n\n*Atualizações*:\n\n${str2}`,
|
||||||
|
false
|
||||||
|
);
|
||||||
|
} catch (error) {
|
||||||
|
console.log(`Error on try sending the monitor message closed: `, error);
|
||||||
|
}
|
||||||
|
} else if (req.body["action"] === "atdatualizou") {
|
||||||
|
console.log("status: atdatualizou --------------> contact: ", contact);
|
||||||
|
|
||||||
|
await statuschange(
|
||||||
|
req,
|
||||||
|
res,
|
||||||
|
contact,
|
||||||
|
`*Olá. Somos a TI Espaçolaser.*\nAtualização do chamado para sua loja ${contact["contact.name"]}. Abaixo seguem informações sobre o incidente para que possam acompanhar.\n\n`
|
||||||
|
);
|
||||||
|
} else if (req.body["action"] === "atdabriu") {
|
||||||
|
console.log("PASS 1");
|
||||||
|
|
||||||
|
await statuschange(
|
||||||
|
req,
|
||||||
|
res,
|
||||||
|
contact,
|
||||||
|
`*Olá. Somos a TI Espaçolaser.*\nIdentificamos em nossos monitoramentos que há um problema na internet da sua loja ${contact["contact.name"]} e já estamos resolvendo. Abaixo seguem informações sobre o incidente para que possam acompanhar.\n\n`
|
||||||
|
);
|
||||||
|
console.log("PASS 2");
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
res.status(401).json({ message: "Token Inválido!" });
|
||||||
|
}
|
||||||
|
|
||||||
|
return res.status(200).json({ message: "Ok" });
|
||||||
|
};
|
||||||
|
|
||||||
|
async function sendMessageHitMonitoring(msg: string, ticket: Ticket) {
|
||||||
|
if (msg && msg.length > 0) {
|
||||||
|
console.log("MESSAGE WILL BE SENT!");
|
||||||
|
|
||||||
|
await SendWhatsAppMessage({ body: msg, ticket });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async function statuschange(
|
||||||
|
req: Request,
|
||||||
|
res: Response,
|
||||||
|
contact: any,
|
||||||
|
header_msg: string,
|
||||||
|
request: boolean = true
|
||||||
|
) {
|
||||||
|
try {
|
||||||
|
const botInfo = await BotIsOnQueue("botqueue");
|
||||||
|
|
||||||
|
let ticket: any = await ShowTicketServiceByContactId(contact.contactId);
|
||||||
|
|
||||||
|
console.log("PASS 01");
|
||||||
|
|
||||||
|
if (!ticket.dataValues.id) {
|
||||||
|
const defaultWhatsapp = await GetDefaultWhatsApp({});
|
||||||
|
|
||||||
|
let _contact: any = await Contact.findByPk(contact.contactId);
|
||||||
|
|
||||||
|
let ticket_obj: any = await FindOrCreateTicketServiceBot(
|
||||||
|
_contact,
|
||||||
|
defaultWhatsapp.id!,
|
||||||
|
0
|
||||||
|
);
|
||||||
|
|
||||||
|
ticket = ticket_obj.ticket;
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log("PASS 02");
|
||||||
|
|
||||||
|
let _response: string;
|
||||||
|
|
||||||
|
if (request) {
|
||||||
|
let response = await hitPortalMonitoring(req.body["centro_custo"]);
|
||||||
|
|
||||||
|
if (!response || response.length == 0) {
|
||||||
|
console.log(
|
||||||
|
"Empty result from hit portal monitoring. Centro_de_custo: ",
|
||||||
|
req.body["centro_custo"]
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
_response = `${header_msg} *Situação do chamado na Operadora*\n\n*Incidente*:\n\n ${response[0].header}\n${response[0].body}`;
|
||||||
|
} else {
|
||||||
|
_response = header_msg;
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log("PASS 03");
|
||||||
|
|
||||||
|
if (ticket.id && ticket.status == "pending") {
|
||||||
|
await sendMessageHitMonitoring(_response, ticket);
|
||||||
|
} else if (ticket.id && ticket.userId == botInfo.userIdBot) {
|
||||||
|
let queue = await ShowQueueService(botInfo.botQueueId);
|
||||||
|
|
||||||
|
await UpdateTicketService({
|
||||||
|
ticketData: { queueId: queue.id },
|
||||||
|
ticketId: ticket.id
|
||||||
|
});
|
||||||
|
|
||||||
|
ticket = await ShowTicketService(ticket.id);
|
||||||
|
|
||||||
|
await sendMessageHitMonitoring(_response, ticket);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.log(`Error on try sending the message monitor: `, error);
|
||||||
|
}
|
||||||
|
}
|
|
@ -60,9 +60,11 @@ export const store = async (req: Request, res: Response): Promise<Response> => {
|
||||||
" | quotedMsg: ",
|
" | quotedMsg: ",
|
||||||
quotedMsg,
|
quotedMsg,
|
||||||
" | params: ",
|
" | params: ",
|
||||||
params
|
params, ' | body: ', JSON.stringify(body, null, 6)
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
const { phoneNumberId, whatsappId } = ticket;
|
const { phoneNumberId, whatsappId } = ticket;
|
||||||
|
|
||||||
if (phoneNumberId) {
|
if (phoneNumberId) {
|
||||||
|
|
|
@ -0,0 +1,57 @@
|
||||||
|
const fsPromises = require("fs/promises");
|
||||||
|
const fs = require("fs");
|
||||||
|
import axios from "axios";
|
||||||
|
import * as https from "https";
|
||||||
|
|
||||||
|
const endPointQuery = async (
|
||||||
|
url: string,
|
||||||
|
method: string,
|
||||||
|
param: string = ""
|
||||||
|
) => {
|
||||||
|
let response: any = null;
|
||||||
|
|
||||||
|
try {
|
||||||
|
const httpsAgent = new https.Agent({ rejectUnauthorized: false });
|
||||||
|
|
||||||
|
if (method == "get") {
|
||||||
|
// const url = 'https://sos.espacolaser.com.br/api/whatsapp/ticket/R32656'
|
||||||
|
response = await axios.get(url, {
|
||||||
|
httpsAgent,
|
||||||
|
headers: {
|
||||||
|
"x-access-token":
|
||||||
|
"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOnsiaWQiOjEsInJvbGUiOiJjbGllbnQiLCJob3N0Ijoic29zLmVzcGFjb2xhc2VyLmNvbS5iciIsInRlbmFudCI6ImVzcGFjb2xhc2VyIiwibmFtZSI6IlNFTlNSLklUIiwiY29tcGFueSI6eyJpZCI6NDR9fSwiZGF0ZSI6MTY2MTI2MjY0MywiaWF0IjoxNjYxMjYyNjQzLCJleHAiOjE3NDc2NjI2NDN9.zf91OmRs4_C7B8OlVpLLrQMiRBYc7edP4qAdH_hqxpk",
|
||||||
|
Origin: "espacolaser"
|
||||||
|
}
|
||||||
|
});
|
||||||
|
console.log(
|
||||||
|
`TEST URL CLIENT GET ROUTE: ${url} | STATUS CODE: ${response.status}`
|
||||||
|
);
|
||||||
|
} else if (method == "post") {
|
||||||
|
// const url = 'http://177.107.193.124:8095/labs/zabbix-frontend/api/api.php'
|
||||||
|
|
||||||
|
response = await axios.post(
|
||||||
|
url,
|
||||||
|
{
|
||||||
|
auth: "0424bd59b807674191e7d77572075f33",
|
||||||
|
jsonrpc: "2.0",
|
||||||
|
method: "chamado.ematendimento",
|
||||||
|
"params[ccusto]": param,
|
||||||
|
id: "101"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
httpsAgent,
|
||||||
|
headers: { "Content-Type": "multipart/form-data" }
|
||||||
|
}
|
||||||
|
);
|
||||||
|
console.log(
|
||||||
|
`TEST URL CLIENT POST ROUTE: ${url} | STATUS CODE: ${response.status}`
|
||||||
|
);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error(`Erro ao consultar endpoint ${url}: ${error}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
return response;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default endPointQuery;
|
|
@ -0,0 +1,68 @@
|
||||||
|
|
||||||
|
const fsPromises = require("fs/promises");
|
||||||
|
const fs = require('fs')
|
||||||
|
|
||||||
|
import endPointQuery2 from './EndpointQuery2'
|
||||||
|
import WhatsQueueIndex from "./WhatsQueueIndex";
|
||||||
|
|
||||||
|
|
||||||
|
const hitPortalMonitoring = async (centro_de_custo: string) => {
|
||||||
|
|
||||||
|
let msg_endpoint: any = []
|
||||||
|
|
||||||
|
let response2 = await endPointQuery2('http://177.107.193.124:8095/labs/zabbix-frontend/api/api.php', 'post', centro_de_custo.trim())
|
||||||
|
|
||||||
|
if (response2 && response2.data.result) {
|
||||||
|
|
||||||
|
response2 = response2.data.result;
|
||||||
|
|
||||||
|
for (let i = 0; i < response2.length; i++) {
|
||||||
|
|
||||||
|
let data = ''
|
||||||
|
let sub_data = '*Atualizações:*\n\n'
|
||||||
|
|
||||||
|
const properties: any = Object.entries(response2[i]);
|
||||||
|
|
||||||
|
for (let x = 0; x < properties.length; x++) {
|
||||||
|
|
||||||
|
if (typeof (properties[x][1]) != 'object') {
|
||||||
|
|
||||||
|
data += `*${properties[x][0]}*: ${properties[x][1].replace(/(\r\n|\n|\r)/gm, "")}\n`
|
||||||
|
|
||||||
|
}
|
||||||
|
else if (typeof (properties[x][1]) == 'object') {
|
||||||
|
|
||||||
|
const sub_properties = properties[x][1];
|
||||||
|
|
||||||
|
for (let k = 0; k < sub_properties.length; k++) {
|
||||||
|
|
||||||
|
const inner_properties: any = Object.entries(sub_properties[k]);
|
||||||
|
|
||||||
|
for (let y = 0; y < inner_properties.length; y++) {
|
||||||
|
|
||||||
|
sub_data += `*${inner_properties[y][0]}*: ${inner_properties[y][1].replace(/(\r\n|\n|\r)/gm, "")}\n`
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
sub_data += '\n'
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
msg_endpoint.push({ header: data, body: sub_data })
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
msg_endpoint = null
|
||||||
|
}
|
||||||
|
|
||||||
|
return msg_endpoint
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
export default hitPortalMonitoring
|
|
@ -2,20 +2,25 @@ const Redis = require("ioredis");
|
||||||
const redis = new Redis(process.env.REDIS_URI);
|
const redis = new Redis(process.env.REDIS_URI);
|
||||||
|
|
||||||
type WhatsappData = {
|
type WhatsappData = {
|
||||||
whatsappId: string;
|
whatsappId: string | number;
|
||||||
contactId: string;
|
contactId: string | number;
|
||||||
identifier: string;
|
identifier: string;
|
||||||
value?: string;
|
value?: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
export async function set(key: string, value: string) {
|
export async function set(key: string, value: string, expire: boolean = false) {
|
||||||
await redis.set(key, JSON.stringify(value));
|
await redis.set(key, JSON.stringify(value));
|
||||||
|
|
||||||
|
if (expire) await redis.expire(key, 300);
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function get(key: string) {
|
export async function get(key: string) {
|
||||||
const value: any = await redis.get(key);
|
const value: any = await redis.get(key);
|
||||||
return JSON.parse(value);
|
return JSON.parse(value);
|
||||||
}
|
}
|
||||||
|
export async function del(key: string) {
|
||||||
|
await redis.del(key);
|
||||||
|
}
|
||||||
|
|
||||||
export async function createObject({
|
export async function createObject({
|
||||||
whatsappId,
|
whatsappId,
|
||||||
|
@ -51,8 +56,8 @@ export async function updateObject({
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function findObject(
|
export async function findObject(
|
||||||
whatsappId: string,
|
whatsappId: string | number,
|
||||||
contactId: string,
|
contactId: string | number,
|
||||||
identifier: string
|
identifier: string
|
||||||
) {
|
) {
|
||||||
const key = `whatsappId:${whatsappId}:contactId:${contactId}:identifier:${identifier}`;
|
const key = `whatsappId:${whatsappId}:contactId:${contactId}:identifier:${identifier}`;
|
||||||
|
|
|
@ -0,0 +1,9 @@
|
||||||
|
import express from "express";
|
||||||
|
|
||||||
|
import * as HitController from "../controllers/HitController"
|
||||||
|
|
||||||
|
const hitRoutes = express.Router();
|
||||||
|
|
||||||
|
hitRoutes.post("/espacolaser/incidente", HitController.hit);
|
||||||
|
|
||||||
|
export default hitRoutes;
|
|
@ -13,6 +13,7 @@ import quickAnswerRoutes from "./quickAnswerRoutes";
|
||||||
import reportRoutes from "./reportRoutes";
|
import reportRoutes from "./reportRoutes";
|
||||||
import schedulingNotifiyRoutes from "./SchedulingNotifyRoutes";
|
import schedulingNotifiyRoutes from "./SchedulingNotifyRoutes";
|
||||||
import statusChatEndRoutes from "./statusChatEndRoutes";
|
import statusChatEndRoutes from "./statusChatEndRoutes";
|
||||||
|
import hitRoutes from "./hitRoutes";
|
||||||
import wbotMonitorRoutes from "./wbotMonitorRoutes";
|
import wbotMonitorRoutes from "./wbotMonitorRoutes";
|
||||||
|
|
||||||
const routes = Router();
|
const routes = Router();
|
||||||
|
@ -32,6 +33,7 @@ routes.use(quickAnswerRoutes);
|
||||||
routes.use(schedulingNotifiyRoutes);
|
routes.use(schedulingNotifiyRoutes);
|
||||||
routes.use(reportRoutes);
|
routes.use(reportRoutes);
|
||||||
routes.use(statusChatEndRoutes);
|
routes.use(statusChatEndRoutes);
|
||||||
|
routes.use(hitRoutes);
|
||||||
routes.use(wbotMonitorRoutes);
|
routes.use(wbotMonitorRoutes);
|
||||||
|
|
||||||
export default routes;
|
export default routes;
|
||||||
|
|
|
@ -0,0 +1,20 @@
|
||||||
|
import { raw } from "express";
|
||||||
|
import AppError from "../../errors/AppError";
|
||||||
|
import ContactCustomField from "../../models/ContactCustomField";
|
||||||
|
|
||||||
|
const ShowContactCustomFieldService = async (contactId: number | string): Promise<ContactCustomField[]> => {
|
||||||
|
|
||||||
|
const queue = await ContactCustomField.findAll({
|
||||||
|
where: { contactId: contactId },
|
||||||
|
raw: true
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
// if (!queue) {
|
||||||
|
// throw new AppError("ERR_CONTACT_CUSTOM_FIELD_NOT_FOUND");
|
||||||
|
// }
|
||||||
|
|
||||||
|
return queue;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default ShowContactCustomFieldService;
|
|
@ -0,0 +1,27 @@
|
||||||
|
|
||||||
|
import Contact from "../../models/Contact";
|
||||||
|
import ContactCustomField from "../../models/ContactCustomField";
|
||||||
|
|
||||||
|
const ContactByCustomField = async (value: string | number): Promise<any> => {
|
||||||
|
|
||||||
|
const contact = await ContactCustomField.findOne({
|
||||||
|
where: { value },
|
||||||
|
raw: true,
|
||||||
|
attributes: ['id', 'value', 'contactId'],
|
||||||
|
|
||||||
|
include: [
|
||||||
|
{
|
||||||
|
model: Contact,
|
||||||
|
required: true,
|
||||||
|
attributes: ['id', 'name', 'number'],
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
],
|
||||||
|
|
||||||
|
});
|
||||||
|
|
||||||
|
return contact;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default ContactByCustomField;
|
|
@ -0,0 +1,73 @@
|
||||||
|
import Ticket from "../../models/Ticket";
|
||||||
|
import AppError from "../../errors/AppError";
|
||||||
|
import Contact from "../../models/Contact";
|
||||||
|
import User from "../../models/User";
|
||||||
|
import Queue from "../../models/Queue";
|
||||||
|
|
||||||
|
import Message from "../../models/Message";
|
||||||
|
import { userInfo } from "os";
|
||||||
|
|
||||||
|
import { Op, where } from "sequelize";
|
||||||
|
|
||||||
|
import { Sequelize } from "sequelize";
|
||||||
|
import moment from "moment";
|
||||||
|
|
||||||
|
import { startOfDay, endOfDay, parseISO, getDate } from "date-fns";
|
||||||
|
import { string } from "yup/lib/locale";
|
||||||
|
|
||||||
|
//Report by user, startDate, endDate
|
||||||
|
const ShowTicketMessage = async (
|
||||||
|
ticketId: string | number,
|
||||||
|
onlyNumber: boolean = false,
|
||||||
|
fromMe?: boolean,
|
||||||
|
limit?: number,
|
||||||
|
regexp?: string
|
||||||
|
): Promise<Message[]> => {
|
||||||
|
let where_clause = {};
|
||||||
|
|
||||||
|
if (onlyNumber) {
|
||||||
|
where_clause = {
|
||||||
|
ticketId: ticketId,
|
||||||
|
fromMe: fromMe ? fromMe : 0,
|
||||||
|
//body: {[Op.regexp]: '^[0-9]*$'},
|
||||||
|
// body: {[Op.regexp]: '^[0-3]$'},
|
||||||
|
body: { [Op.regexp]: regexp }
|
||||||
|
};
|
||||||
|
} else {
|
||||||
|
where_clause = {
|
||||||
|
ticketId: ticketId,
|
||||||
|
fromMe: fromMe ? fromMe : 0
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
const ticket = await Message.findAll({
|
||||||
|
where: where_clause,
|
||||||
|
limit: limit ? limit : 10000,
|
||||||
|
raw: true,
|
||||||
|
attributes: [
|
||||||
|
"body",
|
||||||
|
"read",
|
||||||
|
"mediaType",
|
||||||
|
"fromMe",
|
||||||
|
"mediaUrl",
|
||||||
|
[
|
||||||
|
Sequelize.fn(
|
||||||
|
"DATE_FORMAT",
|
||||||
|
Sequelize.col("createdAt"),
|
||||||
|
"%d/%m/%Y %H:%i:%s"
|
||||||
|
),
|
||||||
|
"createdAt"
|
||||||
|
]
|
||||||
|
],
|
||||||
|
|
||||||
|
order: [["createdAt", "DESC"]]
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!ticket) {
|
||||||
|
throw new AppError("ERR_NO_TICKET_FOUND", 404);
|
||||||
|
}
|
||||||
|
|
||||||
|
return ticket;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default ShowTicketMessage;
|
|
@ -0,0 +1,44 @@
|
||||||
|
import Ticket from "../../models/Ticket";
|
||||||
|
import AppError from "../../errors/AppError";
|
||||||
|
import Contact from "../../models/Contact";
|
||||||
|
import User from "../../models/User";
|
||||||
|
import Queue from "../../models/Queue";
|
||||||
|
|
||||||
|
import { Op } from "sequelize";
|
||||||
|
|
||||||
|
const ShowTicketServiceByContactId = async (contactId: string | number): Promise<Ticket> => {
|
||||||
|
|
||||||
|
const ticket = await Ticket.findOne({
|
||||||
|
|
||||||
|
where: { contactId, [Op.or]: [{ status: 'open' }, { status: 'pending' }] },
|
||||||
|
|
||||||
|
include: [
|
||||||
|
{
|
||||||
|
model: Contact,
|
||||||
|
as: "contact",
|
||||||
|
attributes: ["id", "name", "number", "profilePicUrl", "useQueues"],
|
||||||
|
include: ["extraInfo"]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
model: User,
|
||||||
|
as: "user",
|
||||||
|
attributes: ["id", "name"]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
model: Queue,
|
||||||
|
as: "queue",
|
||||||
|
attributes: ["id", "name", "color"],
|
||||||
|
}
|
||||||
|
]
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!ticket) {
|
||||||
|
|
||||||
|
return new Ticket
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
return ticket;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default ShowTicketServiceByContactId;
|
|
@ -68,6 +68,9 @@ import { splitDateTime } from "../../helpers/SplitDateTime";
|
||||||
//
|
//
|
||||||
|
|
||||||
import { updateTicketCacheByTicketId } from "../../helpers/TicketCache";
|
import { updateTicketCacheByTicketId } from "../../helpers/TicketCache";
|
||||||
|
|
||||||
|
import endPointQuery from "../../helpers/EndpointQuery2";
|
||||||
|
|
||||||
import {
|
import {
|
||||||
insertMessageContactCache,
|
insertMessageContactCache,
|
||||||
getLastId
|
getLastId
|
||||||
|
@ -81,6 +84,7 @@ import {
|
||||||
} from "../../helpers/WhatsappIdMultiSessionControl";
|
} from "../../helpers/WhatsappIdMultiSessionControl";
|
||||||
import AppError from "../../errors/AppError";
|
import AppError from "../../errors/AppError";
|
||||||
import { setMessageAsRead } from "../../helpers/SetMessageAsRead";
|
import { setMessageAsRead } from "../../helpers/SetMessageAsRead";
|
||||||
|
import FindOrCreateTicketServiceBot from "../TicketServices/FindOrCreateTicketServiceBot";
|
||||||
import { getSettingValue } from "../../helpers/WhaticketSettings";
|
import { getSettingValue } from "../../helpers/WhaticketSettings";
|
||||||
|
|
||||||
import { Op } from "sequelize";
|
import { Op } from "sequelize";
|
||||||
|
@ -88,7 +92,15 @@ import { Op } from "sequelize";
|
||||||
import SettingTicket from "../../models/SettingTicket";
|
import SettingTicket from "../../models/SettingTicket";
|
||||||
import mostRepeatedPhrase from "../../helpers/MostRepeatedPhrase";
|
import mostRepeatedPhrase from "../../helpers/MostRepeatedPhrase";
|
||||||
import ListWhatsAppsNumber from "../WhatsappService/ListWhatsAppsNumber";
|
import ListWhatsAppsNumber from "../WhatsappService/ListWhatsAppsNumber";
|
||||||
import { createObject, findObject, get } from "../../helpers/RedisClient";
|
import {
|
||||||
|
createObject,
|
||||||
|
del,
|
||||||
|
findObject,
|
||||||
|
get,
|
||||||
|
set
|
||||||
|
} from "../../helpers/RedisClient";
|
||||||
|
import ShowContactCustomFieldService from "../ContactServices/ShowContactCustomFieldsService";
|
||||||
|
import ShowTicketService from "../TicketServices/ShowTicketService"
|
||||||
|
|
||||||
var lst: any[] = getWhatsappIds();
|
var lst: any[] = getWhatsappIds();
|
||||||
|
|
||||||
|
@ -197,73 +209,6 @@ const verifyMediaMessage = async (
|
||||||
return newMessage;
|
return newMessage;
|
||||||
};
|
};
|
||||||
|
|
||||||
// const verifyMediaMessage = async (
|
|
||||||
// msg: any,
|
|
||||||
// ticket: Ticket,
|
|
||||||
// contact: Contact,
|
|
||||||
// media: any,
|
|
||||||
// quotedMsg?: any
|
|
||||||
// ): Promise<Message | any> => {
|
|
||||||
// // const quotedMsg = await verifyQuotedMessage(msg);
|
|
||||||
|
|
||||||
// // const media = await msg.downloadMedia();
|
|
||||||
|
|
||||||
// if (!media) {
|
|
||||||
// throw new Error("ERR_WAPP_DOWNLOAD_MEDIA");
|
|
||||||
// }
|
|
||||||
|
|
||||||
// console.log(
|
|
||||||
// "MEDIA.FILENAME: ",
|
|
||||||
// media.fileName,
|
|
||||||
// " | msg.fromMe: ",
|
|
||||||
// msg.fromMe
|
|
||||||
// );
|
|
||||||
|
|
||||||
// if (!media.filename) {
|
|
||||||
// console.log("No file name -----------------------------------------");
|
|
||||||
|
|
||||||
// const ext = media.mimetype.split("/")[1].split(";")[0];
|
|
||||||
// media.filename = `${new Date().getTime()}.${ext}`;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// try {
|
|
||||||
// // await writeFileAsync(
|
|
||||||
// // join(__dirname, "..", "..", "..", "public", media.filename),
|
|
||||||
// // media.data,
|
|
||||||
// // "base64"
|
|
||||||
// // );
|
|
||||||
|
|
||||||
// console.log("FROM wbotMessageListener.ts media.filename: ", media.filename);
|
|
||||||
|
|
||||||
// await writeFileAsync(
|
|
||||||
// join(__dirname, "..", "..", "..", "..", "..", "public", media.filename),
|
|
||||||
// media.data,
|
|
||||||
// "base64"
|
|
||||||
// );
|
|
||||||
// } catch (err) {
|
|
||||||
// Sentry.captureException(err);
|
|
||||||
// logger.error(`There was an error: wbotMessageLitener.ts: ${err}`);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// const messageData = {
|
|
||||||
// id: msg.id.id,
|
|
||||||
// ticketId: ticket.id,
|
|
||||||
// contactId: msg.fromMe ? undefined : contact.id,
|
|
||||||
// body: msg.body || media.filename,
|
|
||||||
// fromMe: msg.fromMe,
|
|
||||||
// read: msg.fromMe,
|
|
||||||
// mediaUrl: media.filename,
|
|
||||||
// mediaType: media.mimetype.split("/")[0],
|
|
||||||
// quotedMsgId: quotedMsg
|
|
||||||
// // quotedMsgId: quotedMsg?.id
|
|
||||||
// };
|
|
||||||
|
|
||||||
// await ticket.update({ lastMessage: msg.body || media.filename });
|
|
||||||
// const newMessage = await CreateMessageService({ messageData });
|
|
||||||
|
|
||||||
// return newMessage;
|
|
||||||
// };
|
|
||||||
|
|
||||||
const verifyMessage = async (
|
const verifyMessage = async (
|
||||||
msg: any,
|
msg: any,
|
||||||
ticket: Ticket,
|
ticket: Ticket,
|
||||||
|
@ -287,6 +232,374 @@ const verifyMessage = async (
|
||||||
await CreateMessageService({ messageData });
|
await CreateMessageService({ messageData });
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const queryEndPointHit = async (centro_de_custo: string) => {
|
||||||
|
let msg_endpoint: any = [];
|
||||||
|
|
||||||
|
let response2 = await endPointQuery(
|
||||||
|
"http://177.107.193.124:8095/labs/zabbix-frontend/api/api.php",
|
||||||
|
"post",
|
||||||
|
centro_de_custo.trim()
|
||||||
|
);
|
||||||
|
|
||||||
|
if (response2 && response2.data.result) {
|
||||||
|
response2 = response2.data.result;
|
||||||
|
|
||||||
|
for (let i = 0; i < response2.length; i++) {
|
||||||
|
let data = "";
|
||||||
|
let sub_data = "*Atualizações:*\n\n";
|
||||||
|
|
||||||
|
const properties: any = Object.entries(response2[i]);
|
||||||
|
|
||||||
|
for (let x = 0; x < properties.length; x++) {
|
||||||
|
if (typeof properties[x][1] != "object") {
|
||||||
|
data += `*${properties[x][0]}*: ${properties[x][1].replace(
|
||||||
|
/(\r\n|\n|\r)/gm,
|
||||||
|
""
|
||||||
|
)}\n`;
|
||||||
|
} else if (typeof properties[x][1] == "object") {
|
||||||
|
const sub_properties = properties[x][1];
|
||||||
|
|
||||||
|
for (let k = 0; k < sub_properties.length; k++) {
|
||||||
|
const inner_properties: any = Object.entries(sub_properties[k]);
|
||||||
|
|
||||||
|
for (let y = 0; y < inner_properties.length; y++) {
|
||||||
|
sub_data += `*${inner_properties[y][0]}*: ${inner_properties[
|
||||||
|
y
|
||||||
|
][1].replace(/(\r\n|\n|\r)/gm, "")}\n`;
|
||||||
|
}
|
||||||
|
|
||||||
|
sub_data += "\n";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
msg_endpoint.push({ header: data, body: sub_data });
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
msg_endpoint = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
return msg_endpoint;
|
||||||
|
};
|
||||||
|
|
||||||
|
const monitoramento_response2 = async (
|
||||||
|
response: any | null,
|
||||||
|
wbot: any,
|
||||||
|
contact: any,
|
||||||
|
ticket: any,
|
||||||
|
centro_de_custo: any,
|
||||||
|
final_message: string = "",
|
||||||
|
send_empty_incident?: boolean
|
||||||
|
) => {
|
||||||
|
if (!response) {
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: `Houve um erro ao tentar consultar o monitoramento da Operadora!${final_message}`,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
} else if (response.length > 0) {
|
||||||
|
for (let i = 0; i < response.length; i++) {
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: `*Situação do chamado na Operadora*\n\n*Incidente*:\n\n ${response[i].header}\n${response[i].body}${final_message}`,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} else if (send_empty_incident) {
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: `Conforme Monitoramento a internet da unidade está operacional${final_message}`,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
async function sendDelayedMessages(
|
||||||
|
wbot: Session,
|
||||||
|
ticket: Ticket,
|
||||||
|
contact: Contact,
|
||||||
|
message: string,
|
||||||
|
_msg?: WbotMessage
|
||||||
|
) {
|
||||||
|
const body = message.replace(/\\n/g, "\n");
|
||||||
|
|
||||||
|
if (body.search("dialog_actions") != -1) {
|
||||||
|
let msgAction = botMsgActions(body);
|
||||||
|
|
||||||
|
if (msgAction.actions[0] == "request_endpoint") {
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: msgAction.msgBody,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
|
||||||
|
// const url = 'https://sos.espacolaser.com.br/api/whatsapps/ticket/R32656'
|
||||||
|
let endPointResponse = await endPointQuery(msgAction.actions[1], "get");
|
||||||
|
|
||||||
|
await del(
|
||||||
|
`whatsappId:${wbot.id}:contactId:${contact.id}:identifier:query`
|
||||||
|
);
|
||||||
|
|
||||||
|
console.log(
|
||||||
|
"Object.entries(endPointResponse.data).length: ",
|
||||||
|
Object.entries(endPointResponse.data).length
|
||||||
|
);
|
||||||
|
|
||||||
|
if (
|
||||||
|
endPointResponse &&
|
||||||
|
endPointResponse.status == 200 &&
|
||||||
|
Object.entries(endPointResponse.data).length > 0
|
||||||
|
) {
|
||||||
|
if (
|
||||||
|
endPointResponse.data.categoria != "INFRAESTRUTURA" &&
|
||||||
|
endPointResponse.data.categoria != "ELOS"
|
||||||
|
) {
|
||||||
|
botSendMessage(
|
||||||
|
ticket,
|
||||||
|
`A categorização desse chamado não se enquadra no atendimento deste canal!\n\n _Digite *0* para voltar ao menu principal._`
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const response = Object.entries(endPointResponse.data);
|
||||||
|
let msg_endpoint_response = "";
|
||||||
|
let msg_endpoint2: any = [];
|
||||||
|
let centro_de_custo = "";
|
||||||
|
|
||||||
|
for (let i = 0; i < response.length; i++) {
|
||||||
|
if (
|
||||||
|
[
|
||||||
|
"id_solicitante",
|
||||||
|
"centro_custo_departamento",
|
||||||
|
"departamento_do_formulario",
|
||||||
|
"centro_de_custo_do_departamento_do_formulario"
|
||||||
|
].includes(response[i][0])
|
||||||
|
)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
msg_endpoint_response += `*${response[i][0]}*: ${String(
|
||||||
|
response[i][1]
|
||||||
|
).replace(/(<([^>]+)>)/gi, "")}\n`;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (
|
||||||
|
endPointResponse.data.centro_custo_departamento &&
|
||||||
|
endPointResponse.data.centro_custo_departamento.trim().length > 0 &&
|
||||||
|
endPointResponse.data.categoria == "INFRAESTRUTURA" &&
|
||||||
|
endPointResponse.data.subcategoria == "INTERNET"
|
||||||
|
) {
|
||||||
|
centro_de_custo = endPointResponse.data.centro_custo_departamento;
|
||||||
|
|
||||||
|
msg_endpoint2 = await queryEndPointHit(centro_de_custo);
|
||||||
|
}
|
||||||
|
|
||||||
|
const itsm_response = async (
|
||||||
|
message1: string = "",
|
||||||
|
message2: string = ""
|
||||||
|
) => {
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: `*Situação do chamado ${extractCallCode(
|
||||||
|
msgAction.msgBody
|
||||||
|
)}:*${message1}${msg_endpoint_response}${message2}\n_Digite *0* para voltar ao menu principal._`,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const sendMessageBot = async (
|
||||||
|
message1: string = "",
|
||||||
|
message2: string = ""
|
||||||
|
) => {
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: `${message1}${message2}`,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
if (body.search("dialog_options") != -1) {
|
||||||
|
let msgAction = botMsgActions(body);
|
||||||
|
|
||||||
|
let index = msgAction.actions.findIndex(i => i == "dialog_options");
|
||||||
|
|
||||||
|
if (index != -1) {
|
||||||
|
let dialog_options = msgAction.actions[index + 1];
|
||||||
|
|
||||||
|
if (
|
||||||
|
dialog_options == "3" &&
|
||||||
|
endPointResponse.data.categoria == "ELOS"
|
||||||
|
) {
|
||||||
|
index = msgAction.actions.findIndex(i => i == "queue_transfer");
|
||||||
|
|
||||||
|
if (index != -1) {
|
||||||
|
await itsm_response("\n\n");
|
||||||
|
|
||||||
|
await monitoramento_response2(
|
||||||
|
msg_endpoint2,
|
||||||
|
wbot,
|
||||||
|
contact,
|
||||||
|
ticket,
|
||||||
|
centro_de_custo,
|
||||||
|
"\n\n",
|
||||||
|
false
|
||||||
|
);
|
||||||
|
|
||||||
|
botSendMessage(
|
||||||
|
ticket,
|
||||||
|
`Estamos direcionando seu atendimento para o Suporte. Em breve você será atendido por um de nossos atendentes!\n\nPara voltar ao atendimento *automatizado* e sair da fila de atendimento *humano* digite *0*`
|
||||||
|
);
|
||||||
|
|
||||||
|
await transferTicket(
|
||||||
|
+msgAction.actions[index + 1],
|
||||||
|
wbot,
|
||||||
|
ticket
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (
|
||||||
|
(endPointResponse.data.categoria == "INFRAESTRUTURA" &&
|
||||||
|
endPointResponse.data.subcategoria == "INTERNET" &&
|
||||||
|
endPointResponse.data.terceiro_nivel == "QUEDA TOTAL") ||
|
||||||
|
(endPointResponse.data.categoria == "INFRAESTRUTURA" &&
|
||||||
|
endPointResponse.data.subcategoria == "INTERNET" &&
|
||||||
|
endPointResponse.data.terceiro_nivel == "PROBLEMA DE LENTIDÃO") ||
|
||||||
|
(endPointResponse.data.categoria == "ELOS" &&
|
||||||
|
endPointResponse.data.subcategoria == "VENDAS") ||
|
||||||
|
(endPointResponse.data.categoria == "ELOS" &&
|
||||||
|
endPointResponse.data.subcategoria == "INDISPONIBILIDADE")
|
||||||
|
) {
|
||||||
|
await itsm_response("\n\n");
|
||||||
|
|
||||||
|
if (
|
||||||
|
endPointResponse.data.categoria == "INFRAESTRUTURA" &&
|
||||||
|
endPointResponse.data.subcategoria == "INTERNET" &&
|
||||||
|
centro_de_custo
|
||||||
|
) {
|
||||||
|
await monitoramento_response2(
|
||||||
|
msg_endpoint2,
|
||||||
|
wbot,
|
||||||
|
contact,
|
||||||
|
ticket,
|
||||||
|
centro_de_custo,
|
||||||
|
"\n\n _Digite *0* para voltar ao menu principal._",
|
||||||
|
true
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
await sendMessageBot(
|
||||||
|
"Se deseja solicitar atendimento de urgência, digite *1*!",
|
||||||
|
"\n\n _Digite *0* para voltar ao menu principal._"
|
||||||
|
);
|
||||||
|
|
||||||
|
return;
|
||||||
|
} else {
|
||||||
|
await itsm_response("\n\n");
|
||||||
|
|
||||||
|
if (
|
||||||
|
endPointResponse.data.categoria == "INFRAESTRUTURA" &&
|
||||||
|
endPointResponse.data.subcategoria == "INTERNET" &&
|
||||||
|
centro_de_custo
|
||||||
|
) {
|
||||||
|
await monitoramento_response2(
|
||||||
|
msg_endpoint2,
|
||||||
|
wbot,
|
||||||
|
contact,
|
||||||
|
ticket,
|
||||||
|
centro_de_custo,
|
||||||
|
"\n\n _Digite *0* para voltar ao menu principal._",
|
||||||
|
true
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
await sendMessageBot(
|
||||||
|
"Acompanhe a evolução do atendimento através do SOS"
|
||||||
|
);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} else if (
|
||||||
|
endPointResponse &&
|
||||||
|
endPointResponse.status == 200 &&
|
||||||
|
Object.entries(endPointResponse.data).length == 0
|
||||||
|
) {
|
||||||
|
botSendMessage(
|
||||||
|
ticket,
|
||||||
|
`Não existe nenhum chamado para consulta com esse número!\n _Digite *0* para voltar ao menu principal._`
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
} else if (endPointResponse && endPointResponse.status == 500) {
|
||||||
|
botSendMessage(
|
||||||
|
ticket,
|
||||||
|
`Houve um erro ao realizar a consulta no sos espacolaser!\n _Digite *0* para voltar ao menu principal._`
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
} else {
|
||||||
|
botSendMessage(
|
||||||
|
ticket,
|
||||||
|
`Desculpe, nao foi possível realizar a consulta!\n _Digite *0* para voltar ao menu principal._`
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} else if (msgAction.actions[0] == "queue_transfer") {
|
||||||
|
console.log(
|
||||||
|
">>>>>>>>>>>>>>> msgAction: ",
|
||||||
|
msgAction,
|
||||||
|
" | msgAction.actions[1]: ",
|
||||||
|
msgAction.actions[1]
|
||||||
|
);
|
||||||
|
|
||||||
|
const contact_custom_field = await ShowContactCustomFieldService(
|
||||||
|
contact.id
|
||||||
|
);
|
||||||
|
|
||||||
|
if (contact_custom_field && contact_custom_field.length > 0) {
|
||||||
|
const msg_endpoint = await queryEndPointHit(
|
||||||
|
contact_custom_field[0].value
|
||||||
|
);
|
||||||
|
|
||||||
|
await monitoramento_response2(
|
||||||
|
msg_endpoint,
|
||||||
|
wbot,
|
||||||
|
contact,
|
||||||
|
ticket,
|
||||||
|
contact_custom_field[0].value
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log("************* contact_custom_field: ", contact_custom_field);
|
||||||
|
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: msgAction.msgBody,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
|
||||||
|
await transferTicket(+msgAction.actions[1], wbot, ticket);
|
||||||
|
} else if (msgAction.actions[0] == "send_file") {
|
||||||
|
const sourcePath = path.join(__dirname, `../../../public/bot`);
|
||||||
|
|
||||||
|
await SendWhatsAppMessage({
|
||||||
|
body: msgAction.msgBody,
|
||||||
|
ticket,
|
||||||
|
number: `${contact.number}@c.us`
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
sendWhatsAppMessageSocket(ticket, body);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const extractCallCode = (str: string) => {
|
||||||
|
if (str.includes("*") && str.indexOf("*") < str.lastIndexOf("*")) {
|
||||||
|
return str
|
||||||
|
.substring(str.indexOf("*"), str.lastIndexOf("*") + 1)
|
||||||
|
.split("*")
|
||||||
|
.join("");
|
||||||
|
}
|
||||||
|
return "";
|
||||||
|
};
|
||||||
|
|
||||||
const verifyQueue = async (
|
const verifyQueue = async (
|
||||||
wbot: Session,
|
wbot: Session,
|
||||||
msg: WbotMessage,
|
msg: WbotMessage,
|
||||||
|
@ -457,6 +770,17 @@ const mediaTypeWhatsappOfficial = (mimetype: string): object => {
|
||||||
return { type: null, mbsize: 0 };
|
return { type: null, mbsize: 0 };
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const botMsgActions = (params: string) => {
|
||||||
|
let lstActions = params.split("dialog_actions=");
|
||||||
|
let bodyMsg = lstActions[0];
|
||||||
|
let obj = {};
|
||||||
|
|
||||||
|
console.log("lstActions: ", lstActions[1].split("="));
|
||||||
|
let actions = lstActions[1].split("=");
|
||||||
|
|
||||||
|
return { msgBody: bodyMsg, actions: actions };
|
||||||
|
};
|
||||||
|
|
||||||
const isValidMsg = (msg: any): boolean => {
|
const isValidMsg = (msg: any): boolean => {
|
||||||
if (msg.from === "status@broadcast") return false;
|
if (msg.from === "status@broadcast") return false;
|
||||||
if (
|
if (
|
||||||
|
@ -663,13 +987,39 @@ const handleMessage = async (
|
||||||
)
|
)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
const ticket = await FindOrCreateTicketService(
|
let ticket;
|
||||||
|
|
||||||
|
const _botInfo = await BotIsOnQueue("botqueue");
|
||||||
|
|
||||||
|
if (_botInfo.isOnQueue) {
|
||||||
|
let ticket_obj: any = await FindOrCreateTicketServiceBot(
|
||||||
contact,
|
contact,
|
||||||
wbot.id!,
|
wbot.id!,
|
||||||
unreadMessages
|
unreadMessages
|
||||||
// groupContact
|
// groupContact
|
||||||
);
|
);
|
||||||
|
|
||||||
|
ticket = ticket_obj.ticket;
|
||||||
|
|
||||||
|
if (ticket_obj.created) {
|
||||||
|
let queue = await ShowQueueService(_botInfo.botQueueId);
|
||||||
|
|
||||||
|
await UpdateTicketService({
|
||||||
|
ticketData: { queueId: queue.id },
|
||||||
|
ticketId: ticket.id
|
||||||
|
});
|
||||||
|
|
||||||
|
ticket = await ShowTicketService(ticket.id);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
ticket = await FindOrCreateTicketService(
|
||||||
|
contact,
|
||||||
|
wbot.id!,
|
||||||
|
unreadMessages
|
||||||
|
// groupContact
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
if (getSettingValue("oneContactChatWithManyWhats")?.value == "disabled") {
|
if (getSettingValue("oneContactChatWithManyWhats")?.value == "disabled") {
|
||||||
// Para responder para o cliente pelo mesmo whatsapp que ele enviou a mensagen
|
// Para responder para o cliente pelo mesmo whatsapp que ele enviou a mensagen
|
||||||
if (wbot.id != ticket.whatsappId) {
|
if (wbot.id != ticket.whatsappId) {
|
||||||
|
@ -739,6 +1089,63 @@ const handleMessage = async (
|
||||||
} else {
|
} else {
|
||||||
console.log("MSG body: ", msg.body);
|
console.log("MSG body: ", msg.body);
|
||||||
|
|
||||||
|
if (msg.type != "chat") {
|
||||||
|
botSendMessage(
|
||||||
|
ticket,
|
||||||
|
`Desculpe, nao compreendi!\nEnvie apenas texto quando estiver interagindo com o bot!\n _Digite *0* para voltar ao menu principal._`
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (msg.type == "chat" && String(msg.body).length > 120) {
|
||||||
|
botSendMessage(
|
||||||
|
ticket,
|
||||||
|
`Desculpe, nao compreendi!\nTexto acima de 120 caracteres!\n _Digite *0* para voltar ao menu principal._`
|
||||||
|
);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let query = await get(
|
||||||
|
`whatsappId:${wbot.id}:contactId:${contact?.id}:identifier:query`
|
||||||
|
);
|
||||||
|
|
||||||
|
if (query && msg?.body?.trim() != "0") {
|
||||||
|
query = JSON.parse(query);
|
||||||
|
|
||||||
|
const regexString = query?.queryRegex?.slice(1, -1);
|
||||||
|
|
||||||
|
query.queryRegex = new RegExp(regexString);
|
||||||
|
|
||||||
|
if (!query?.queryRegex.test(msg.body)) {
|
||||||
|
await botSendMessage(ticket, query?.queryMsgInvalidParam);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (query?.value?.trim()?.length == 0) {
|
||||||
|
await set(
|
||||||
|
`whatsappId:${wbot.id}:contactId:${contact?.id}:identifier:query`,
|
||||||
|
JSON.stringify({ ...query, value: msg.body }),
|
||||||
|
true
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
let message = "";
|
||||||
|
|
||||||
|
// Refactor later
|
||||||
|
if (query?.optionsMenu == "3") {
|
||||||
|
message = `Consultando *${msg?.body?.trim()}* aguarde...
|
||||||
|
dialog_actions=request_endpoint=https://sos.espacolaser.com.br/api/whatsapp/ticket/${msg?.body?.trim()}=dialog_options=3=queue_transfer=1`;
|
||||||
|
} else if (query?.optionsMenu == "1") {
|
||||||
|
message = `Consultando *${msg.body}* aguarde...
|
||||||
|
dialog_actions=request_endpoint=https://sos.espacolaser.com.br/api/whatsapp/ticket/${msg?.body?.trim()}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (message.trim().length > 0)
|
||||||
|
await sendDelayedMessages(wbot, ticket, contact, message);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const menuMsg: any = await menu(msg.body, wbot.id, contact.id);
|
const menuMsg: any = await menu(msg.body, wbot.id, contact.id);
|
||||||
|
|
||||||
console.log("menuMsg: ", menuMsg);
|
console.log("menuMsg: ", menuMsg);
|
||||||
|
@ -755,6 +1162,22 @@ const handleMessage = async (
|
||||||
);
|
);
|
||||||
|
|
||||||
transferTicket(menuMsg.transferToQueue.trim(), wbot, ticket);
|
transferTicket(menuMsg.transferToQueue.trim(), wbot, ticket);
|
||||||
|
} else if (menuMsg?.query) {
|
||||||
|
await set(
|
||||||
|
`whatsappId:${wbot.id}:contactId:${contact?.id}:identifier:query`,
|
||||||
|
JSON.stringify({
|
||||||
|
whatsappId: wbot.id,
|
||||||
|
contactId: contact.id,
|
||||||
|
identifier: "query",
|
||||||
|
value: "",
|
||||||
|
queryRegex: menuMsg?.queryRegex,
|
||||||
|
query: menuMsg?.query,
|
||||||
|
queryMsg: menuMsg?.queryMsg,
|
||||||
|
queryMsgInvalidParam: menuMsg?.queryMsgInvalidParam,
|
||||||
|
optionsMenu: menuMsg?.optionsMenu
|
||||||
|
}),
|
||||||
|
true
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -894,6 +1317,10 @@ const menu = async (userTyped: string, whatsappId: any, contactId: any) => {
|
||||||
value: data[1].id
|
value: data[1].id
|
||||||
});
|
});
|
||||||
|
|
||||||
|
await del(
|
||||||
|
`whatsappId:${whatsappId}:contactId:${contactId}:identifier:query`
|
||||||
|
);
|
||||||
|
|
||||||
return data[1];
|
return data[1];
|
||||||
} else {
|
} else {
|
||||||
console.log("INVALID SEARCH");
|
console.log("INVALID SEARCH");
|
||||||
|
|
|
@ -321,16 +321,34 @@ const MessageInput = ({ ticketStatus }) => {
|
||||||
setTabOption('open')
|
setTabOption('open')
|
||||||
}
|
}
|
||||||
|
|
||||||
const message = {
|
|
||||||
|
if (templateParams) {
|
||||||
|
for (let key in templateParams) {
|
||||||
|
if (templateParams.hasOwnProperty(key)) {
|
||||||
|
// let value = templateParams[key]
|
||||||
|
// console.log('key: ', key, ' | ', 'VALUE: ', value)
|
||||||
|
|
||||||
|
if (key === '_reactName') {
|
||||||
|
templateParams = null
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let message = {
|
||||||
read: 1,
|
read: 1,
|
||||||
fromMe: true,
|
fromMe: true,
|
||||||
mediaUrl: "",
|
mediaUrl: "",
|
||||||
body: (signMessage && !templateParams)
|
body: (signMessage && !templateParams) ? `*${user?.name}:*\n${inputMessage.trim()}` : inputMessage.trim(),
|
||||||
? `*${user?.name}:*\n${inputMessage.trim()}`
|
quotedMsg: replyingMessage
|
||||||
: inputMessage.trim(),
|
|
||||||
quotedMsg: replyingMessage,
|
|
||||||
params: templateParams
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (templateParams) {
|
||||||
|
message = { ...message, params: templateParams }
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|
||||||
const { data } = await api.post(`/messages/${ticketId}`, message)
|
const { data } = await api.post(`/messages/${ticketId}`, message)
|
||||||
|
|
Loading…
Reference in New Issue