Atualização para habilitar ou desabilitar whatsapp oficial
							parent
							
								
									6d525e4224
								
							
						
					
					
						commit
						996e182fb6
					
				|  | @ -8,6 +8,8 @@ import ListSettingsService from "../services/SettingServices/ListSettingsService | |||
| import loadSettings from "../helpers/LoadSettings"; | ||||
| import updateSettingTicket from "../services/SettingServices/UpdateSettingTicket"; | ||||
| import SettingTicket from "../models/SettingTicket"; | ||||
| import Whatsapp from "../models/Whatsapp"; | ||||
| import whatsappOfficialNumberInfo from "../helpers/WhatsappOfficialNumberInfo"; | ||||
| 
 | ||||
| export const index = async (req: Request, res: Response): Promise<Response> => { | ||||
|   // if (req.user.profile !== "master") {
 | ||||
|  | @ -76,9 +78,7 @@ export const updateTicketSettings = async ( | |||
|     }); | ||||
|   } | ||||
| 
 | ||||
|   return res | ||||
|     .status(200) | ||||
|     .json({ | ||||
|   return res.status(200).json({ | ||||
|     outBusinessHours, | ||||
|     ticketExpiration, | ||||
|     weekend, | ||||
|  | @ -103,6 +103,40 @@ export const update = async ( | |||
|     value | ||||
|   }); | ||||
| 
 | ||||
|   if (key && key == "whatsaAppCloudApi") { | ||||
|     let whatsapps: any = await Whatsapp.findAll(); | ||||
| 
 | ||||
|     if (whatsapps) { | ||||
|       for (let i in whatsapps) { | ||||
|         const { id, wabaId, isOfficial } = whatsapps[i]; | ||||
| 
 | ||||
|         if (isOfficial && wabaId) { | ||||
|           try { | ||||
|             const whatsapp = await Whatsapp.findByPk(id); | ||||
|             if (whatsapp) { | ||||
|               if (value == "disabled") { | ||||
|                 whatsapp.update({ status: "OPENING" }); | ||||
|               } else if (value == "enabled") { | ||||
|                 const info = await whatsappOfficialNumberInfo(wabaId); | ||||
|                 if (info) { | ||||
|                   whatsapp.update({ | ||||
|                     classification: info.quality_rating, | ||||
|                     status: "CONNECTED" | ||||
|                   }); | ||||
|                 } | ||||
|               } | ||||
|             } | ||||
|           } catch (error) { | ||||
|             console.log( | ||||
|               "error on try update classification number from oficial whatsapp in SettingControllers.ts: ", | ||||
|               error | ||||
|             ); | ||||
|           } | ||||
|         } | ||||
|       } | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|   loadSettings(); | ||||
| 
 | ||||
|   const io = getIO(); | ||||
|  |  | |||
|  | @ -115,12 +115,24 @@ export const store = async (req: Request, res: Response): Promise<Response> => { | |||
|     } | ||||
|   }); | ||||
| 
 | ||||
|   if (getSettingValue("whatsaAppCloudApi")?.value == "enabled") { | ||||
|     if (ticket) { | ||||
|       await UpdateTicketService({ | ||||
|         ticketData: { status: "closed" }, | ||||
|         ticketId: ticket.id | ||||
|       }); | ||||
|       ticket = null; | ||||
|     } | ||||
|   } else { | ||||
|     if (ticket) { | ||||
|       await UpdateTicketService({ | ||||
|         ticketData: { status: "open", userId: userId, queueId }, | ||||
|         ticketId: ticket.id | ||||
|       }); | ||||
|   } else { | ||||
|     }   | ||||
|   } | ||||
| 
 | ||||
|   if(!ticket){ | ||||
|      ticket = await CreateTicketService({ | ||||
|        contactId, | ||||
|        status, | ||||
|  |  | |||
|  | @ -36,6 +36,10 @@ import ShowUserService from "../services/UserServices/ShowUserService"; | |||
| import fs from "fs"; | ||||
| import receiveWhatsAppMediaOfficialAPI from "../helpers/ReceiveWhatsAppMediaOfficialAPI"; | ||||
| 
 | ||||
| import whatsappOfficialAPI from "../helpers/WhatsappOfficialAPI"; | ||||
| import whatsappOfficialNumberInfo from "../helpers/WhatsappOfficialNumberInfo"; | ||||
| import { getSettingValue } from "../helpers/WhaticketSettings"; | ||||
| 
 | ||||
| interface WhatsappData { | ||||
|   name: string; | ||||
|   queueIds: number[]; | ||||
|  | @ -45,10 +49,45 @@ interface WhatsappData { | |||
|   farewellMessage?: string; | ||||
|   status?: string; | ||||
|   isDefault?: boolean; | ||||
|   isOfficial?: boolean; | ||||
|   phoneNumberId?: string; | ||||
|   wabaId?: string; | ||||
| } | ||||
| 
 | ||||
| let count: number = 0; | ||||
| 
 | ||||
| export const index = async (req: Request, res: Response): Promise<Response> => { | ||||
|   const whatsapps = await ListWhatsAppsService(); | ||||
|   let whatsapps = await ListWhatsAppsService(); | ||||
| 
 | ||||
|   if (getSettingValue("whatsaAppCloudApi")?.value == "enabled") { | ||||
|     // Atualizar isso quando tiver tempo
 | ||||
|     if (count > 12) count = 0; | ||||
|     if (count == 0) { | ||||
|       for (let i in whatsapps) { | ||||
|         const { id, wabaId, isOfficial } = whatsapps[i]; | ||||
| 
 | ||||
|         if (isOfficial && wabaId) { | ||||
|           try { | ||||
|             const info = await whatsappOfficialNumberInfo(wabaId); | ||||
|             if (info) { | ||||
|               const whatsapp = await Whatsapp.findByPk(id); | ||||
| 
 | ||||
|               if (whatsapp) { | ||||
|                 whatsapp.update({ | ||||
|                   classification: info.quality_rating | ||||
|                 }); | ||||
|                 whatsapps[i].classification = info.quality_rating; | ||||
|               } | ||||
|             } | ||||
|           } catch (error) { | ||||
|             console.log('error on try update classification number from oficial whatsapp in WhatsappController.ts: ', error) | ||||
|           } | ||||
|         } | ||||
|       } | ||||
|     } | ||||
|     console.log("count: ", count); | ||||
|     count++; | ||||
|   } | ||||
| 
 | ||||
|   return res.status(200).json(whatsapps); | ||||
| }; | ||||
|  | @ -59,7 +98,15 @@ export const whatsAppOfficialMatchQueue = async ( | |||
| ): Promise<Response> => { | ||||
|   const { userId, queueId }: any = req.query; | ||||
| 
 | ||||
|   const whatsapps = await GetDefaultWhatsApp({ userId, queueId }); | ||||
|   let whatsapps = await GetDefaultWhatsApp({ userId, queueId }); | ||||
| 
 | ||||
|   if (whatsapps && Array.isArray(whatsapps)) { | ||||
|     const uniqueWhatsApps = whatsapps.filter( | ||||
|       (whatsapp, index, self) => | ||||
|         index === self.findIndex(w => w.number === whatsapp.number) | ||||
|     ); | ||||
|     whatsapps = uniqueWhatsApps; | ||||
|   } | ||||
| 
 | ||||
|   return res.status(200).json(whatsapps); | ||||
| }; | ||||
|  | @ -255,7 +302,7 @@ export const weebhook = async ( | |||
| }; | ||||
| 
 | ||||
| export const store = async (req: Request, res: Response): Promise<Response> => { | ||||
|   const { | ||||
|   let { | ||||
|     name, | ||||
|     status, | ||||
|     isDefault, | ||||
|  | @ -263,17 +310,39 @@ export const store = async (req: Request, res: Response): Promise<Response> => { | |||
|     farewellMessage, | ||||
|     queueIds, | ||||
|     url, | ||||
|     urlApi | ||||
|     urlApi, | ||||
|     phoneNumberId, | ||||
|     wabaId, | ||||
|     isOfficial | ||||
|   }: WhatsappData = req.body; | ||||
| 
 | ||||
|   if (req.user.profile !== "master") { | ||||
|     throw new AppError("ERR_NO_PERMISSION", 403); | ||||
|   } | ||||
| 
 | ||||
|   let validate = validatePhoneName(name); | ||||
|   const invalid = checkWhatsAppData({ | ||||
|     urlApi, | ||||
|     isOfficial, | ||||
|     phoneNumberId, | ||||
|     wabaId | ||||
|   }); | ||||
| 
 | ||||
|   if (validate) { | ||||
|     return res.status(200).json({ message: validate }); | ||||
|   if (invalid) { | ||||
|     return res.status(400).json(invalid); | ||||
|   } | ||||
| 
 | ||||
|   if (isOfficial) { | ||||
|     urlApi = ""; | ||||
|     url = ""; | ||||
|   } else if (!isOfficial) { | ||||
|     phoneNumberId = ""; | ||||
|     wabaId = ""; | ||||
|   } | ||||
| 
 | ||||
|   let invalidPhoneName = validatePhoneName(name); | ||||
| 
 | ||||
|   if (invalidPhoneName) { | ||||
|     return res.status(200).json({ message: invalidPhoneName }); | ||||
|   } | ||||
| 
 | ||||
|   const { whatsapp, oldDefaultWhatsapp } = await CreateWhatsAppService({ | ||||
|  | @ -284,19 +353,22 @@ export const store = async (req: Request, res: Response): Promise<Response> => { | |||
|     isDefault, | ||||
|     greetingMessage, | ||||
|     farewellMessage, | ||||
|     queueIds | ||||
|     queueIds, | ||||
|     phoneNumberId, | ||||
|     wabaId, | ||||
|     isOfficial | ||||
|   }); | ||||
| 
 | ||||
|   console.log("whatsapp.id: ", whatsapp.id); | ||||
| 
 | ||||
|   if (!isOfficial) { | ||||
|     postData(`${whatsapp.urlApi}/api/session`, { | ||||
|       app_name: process.env.APP_NAME, | ||||
|       whatsappId: whatsapp.id, | ||||
|       number: getNumberFromName(name), | ||||
|       client_url: `${process.env.BACKEND_URL_RAW}:${process.env.PORT}` | ||||
|     }); | ||||
| 
 | ||||
|   // StartWhatsAppSession(whatsapp);
 | ||||
|   } | ||||
| 
 | ||||
|   const io = getIO(); | ||||
|   io.emit("whatsapp", { | ||||
|  | @ -329,12 +401,31 @@ export const update = async ( | |||
|   const { whatsappId } = req.params; | ||||
|   const whatsappData = req.body; | ||||
| 
 | ||||
|   let validate = validatePhoneName(whatsappData.name); | ||||
|   let invalidPhoneName = validatePhoneName(whatsappData.name); | ||||
| 
 | ||||
|   console.log("validate", validate); | ||||
|   if (invalidPhoneName) { | ||||
|     return res.status(200).json({ message: invalidPhoneName }); | ||||
|   } | ||||
| 
 | ||||
|   if (validate) { | ||||
|     return res.status(200).json({ message: validate }); | ||||
|   const { urlApi, isOfficial, phoneNumberId, wabaId } = whatsappData; | ||||
| 
 | ||||
|   const invalid = checkWhatsAppData({ | ||||
|     urlApi, | ||||
|     isOfficial, | ||||
|     phoneNumberId, | ||||
|     wabaId | ||||
|   }); | ||||
| 
 | ||||
|   if (invalid) { | ||||
|     return res.status(400).json(invalid); | ||||
|   } | ||||
| 
 | ||||
|   if (isOfficial) { | ||||
|     whatsappData.urlApi = ""; | ||||
|     whatsappData.url = ""; | ||||
|   } else if (!isOfficial) { | ||||
|     whatsappData.phoneNumberId = ""; | ||||
|     whatsappData.wabaId = ""; | ||||
|   } | ||||
| 
 | ||||
|   const { whatsapp, oldDefaultWhatsapp } = await UpdateWhatsAppService({ | ||||
|  | @ -342,12 +433,14 @@ export const update = async ( | |||
|     whatsappId | ||||
|   }); | ||||
| 
 | ||||
|   if (!whatsappData?.isOfficial) { | ||||
|     postData(`${whatsapp.urlApi}/api/session`, { | ||||
|       app_name: process.env.APP_NAME, | ||||
|       whatsappId: whatsapp.id, | ||||
|       number: getNumberFromName(whatsapp.name), | ||||
|       client_url: `${process.env.BACKEND_URL_RAW}:${process.env.PORT}` | ||||
|     }); | ||||
|   } | ||||
| 
 | ||||
|   const io = getIO(); | ||||
|   io.emit("whatsapp", { | ||||
|  | @ -377,10 +470,12 @@ export const remove = async ( | |||
| 
 | ||||
|   const whatsapp: any = await Whatsapp.findByPk(whatsappId, { raw: true }); | ||||
| 
 | ||||
|   if (!whatsapp?.isOfficial) { | ||||
|     postData(`${whatsapp.urlApi}/api/session/del`, { | ||||
|       app_name: process.env.APP_NAME, | ||||
|       whatsappId: whatsappId | ||||
|     }); | ||||
|   } | ||||
| 
 | ||||
|   await DeleteWhatsAppService(whatsappId); | ||||
| 
 | ||||
|  | @ -407,3 +502,25 @@ export const remove = async ( | |||
| 
 | ||||
|   return res.status(200).json({ message: "Whatsapp deleted." }); | ||||
| }; | ||||
| 
 | ||||
| interface WhatsappDataValidate { | ||||
|   urlApi?: string; | ||||
|   isOfficial?: boolean; | ||||
|   phoneNumberId?: string; | ||||
|   wabaId?: string; | ||||
| } | ||||
| 
 | ||||
| const checkWhatsAppData = ({ | ||||
|   urlApi, | ||||
|   isOfficial, | ||||
|   phoneNumberId, | ||||
|   wabaId | ||||
| }: WhatsappDataValidate) => { | ||||
|   if (isOfficial && (!phoneNumberId || phoneNumberId.trim() == "")) { | ||||
|     return { message: "Phone number Id is required!" }; | ||||
|   } else if (isOfficial && (!wabaId || wabaId.trim() == "")) { | ||||
|     return { message: "WABA ID is required!" }; | ||||
|   } else if (!isOfficial && (!urlApi || urlApi.trim() == "")) { | ||||
|     return { message: "urlApi is required!" }; | ||||
|   } | ||||
| }; | ||||
|  |  | |||
|  | @ -0,0 +1,15 @@ | |||
| import { QueryInterface, DataTypes } from "sequelize"; | ||||
| 
 | ||||
| module.exports = { | ||||
|   up: (queryInterface: QueryInterface) => { | ||||
|     return queryInterface.addColumn("Whatsapps", "isOfficial", { | ||||
|       type: DataTypes.BOOLEAN, | ||||
|       allowNull: false, | ||||
|       defaultValue: false | ||||
|     }); | ||||
|   }, | ||||
| 
 | ||||
|   down: (queryInterface: QueryInterface) => { | ||||
|     return queryInterface.removeColumn("Whatsapps", "isOfficial"); | ||||
|   } | ||||
| }; | ||||
|  | @ -0,0 +1,14 @@ | |||
| import { QueryInterface, DataTypes } from "sequelize"; | ||||
| 
 | ||||
| module.exports = { | ||||
|   up: (queryInterface: QueryInterface) => { | ||||
|     return queryInterface.addColumn("Whatsapps", "wabaId", { | ||||
|       type: DataTypes.STRING, | ||||
|       allowNull: true | ||||
|     }); | ||||
|   }, | ||||
| 
 | ||||
|   down: (queryInterface: QueryInterface) => { | ||||
|     return queryInterface.removeColumn("Whatsapps", "wabaId"); | ||||
|   } | ||||
| }; | ||||
|  | @ -0,0 +1,14 @@ | |||
| import { QueryInterface, DataTypes } from "sequelize"; | ||||
| 
 | ||||
| module.exports = { | ||||
|   up: (queryInterface: QueryInterface) => { | ||||
|     return queryInterface.addColumn("Whatsapps", "classification", { | ||||
|       type: DataTypes.STRING, | ||||
|       allowNull: true | ||||
|     }); | ||||
|   }, | ||||
| 
 | ||||
|   down: (queryInterface: QueryInterface) => { | ||||
|     return queryInterface.removeColumn("Whatsapps", "classification"); | ||||
|   } | ||||
| }; | ||||
|  | @ -8,8 +8,6 @@ import { Op, where } from "sequelize"; | |||
| 
 | ||||
| import wbotByUserQueue from "../helpers/GetWbotByUserQueue";  | ||||
| 
 | ||||
| // import WhatsQueueIndex from "./WhatsQueueIndex";
 | ||||
| 
 | ||||
| import { WhatsIndex } from "./LoadBalanceWhatsSameQueue"; | ||||
| 
 | ||||
| interface Request { | ||||
|  | @ -35,7 +33,7 @@ const GetDefaultWhatsApp = async ({ | |||
|       if (userId && queueId) { | ||||
|         if (whatsapps.length > 1) { | ||||
|           let whatsAppOfficial: any = whatsapps.find( | ||||
|             (w: any) => w.phoneNumberId != null | ||||
|             (w: any) => w.phoneNumberId && w.phoneNumberId.trim().length > 0 | ||||
|           ); | ||||
| 
 | ||||
|           if (whatsAppOfficial) { | ||||
|  |  | |||
|  | @ -1,49 +0,0 @@ | |||
| 
 | ||||
| import Ticket from "../models/Ticket"; | ||||
| import ListWhatsAppsNumber from "../services/WhatsappService/ListWhatsAppsNumber"; | ||||
| import GetTicketWbot from "./GetTicketWbot"; | ||||
| 
 | ||||
| const sendMessageMultiSession = async (ticket: Ticket, body?: any, quotedMsgSerializedId?: any, sendSeen?: boolean) => { | ||||
| 
 | ||||
|     let sentMessage: any = '' | ||||
| 
 | ||||
|     const listWhatsapp: any = await ListWhatsAppsNumber(ticket.whatsappId, 'CONNECTED') | ||||
| 
 | ||||
|     if (listWhatsapp.length > 0) { | ||||
| 
 | ||||
|         for (let w = 0; w < listWhatsapp.length; w++) { | ||||
| 
 | ||||
|             if(listWhatsapp[w].id == ticket.whatsappId) continue | ||||
| 
 | ||||
|             try { | ||||
| 
 | ||||
|                 console.log('CHANGE THE WHATSAPP SESSION ID: ', listWhatsapp[w].id) | ||||
| 
 | ||||
|                 await ticket.update({ whatsappId: listWhatsapp[w].id }) | ||||
| 
 | ||||
|                 const wbot = await GetTicketWbot(ticket); | ||||
| 
 | ||||
|                 if (sendSeen) { | ||||
| 
 | ||||
|                     await wbot.sendSeen(`${ticket.contact.number}@${ticket.isGroup ? "g" : "c"}.us`); | ||||
| 
 | ||||
|                 } | ||||
|                 else if (body) { | ||||
| 
 | ||||
|                     sentMessage = await wbot.sendMessage(`${ticket.contact.number}@${ticket.isGroup ? "g" : "c"}.us`, body, { quotedMessageId: quotedMsgSerializedId, linkPreview: false }); | ||||
| 
 | ||||
|                 } | ||||
| 
 | ||||
|                 break | ||||
| 
 | ||||
|             } catch (error) { | ||||
|                 console.log('Cannot send send the message using the whatsapp id: ', listWhatsapp[w].id, ' | error: ', error) | ||||
|             } | ||||
| 
 | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     return sentMessage | ||||
| }; | ||||
| 
 | ||||
| export default sendMessageMultiSession; | ||||
|  | @ -0,0 +1,21 @@ | |||
| import whatsappOfficialAPI from "./WhatsappOfficialAPI"; | ||||
| 
 | ||||
| async function whatsappOfficialNumberInfo(wabaId: string) { | ||||
|   try { | ||||
|     const { data } = await whatsappOfficialAPI.get( | ||||
|       `/${process.env.VERSION}/${wabaId}/phone_numbers` | ||||
|     ); | ||||
|     console.log("data: ", data); | ||||
| 
 | ||||
|     if (data && Object.keys(data).length > 0) { | ||||
|       return data.data[0]; | ||||
|     } | ||||
|   } catch (error) { | ||||
|     console.log( | ||||
|       `There was an error into whatsappOfficialNumberInfo method : ${error}` | ||||
|     ); | ||||
|   } | ||||
| 
 | ||||
|   return null; | ||||
| } | ||||
| export default whatsappOfficialNumberInfo; | ||||
|  | @ -1,39 +1,28 @@ | |||
| const fsPromises = require("fs/promises"); | ||||
| const fs = require('fs') | ||||
| import axios from 'axios'; | ||||
| const fs = require("fs"); | ||||
| import axios from "axios"; | ||||
| import * as https from "https"; | ||||
| 
 | ||||
| const endPointQuery = async (url: string, data: any) => { | ||||
| 
 | ||||
|     let response: any = null | ||||
|   let response: any = null; | ||||
| 
 | ||||
|   try { | ||||
| 
 | ||||
|     response = await axios.post(url, data); | ||||
| 
 | ||||
|         console.log(`TEST URL CLIENT POST ROUTE: ${url} | STATUS CODE: ${response.status}`); | ||||
| 
 | ||||
| 
 | ||||
|     console.log( | ||||
|       `TEST URL CLIENT POST ROUTE: ${url} | STATUS CODE: ${response.status}` | ||||
|     ); | ||||
|   } catch (err: any) { | ||||
| 
 | ||||
|     if (err.response) { | ||||
|             // The client was given an error response (5xx, 4xx)
 | ||||
|             // console.log('err.response: ', err.response)
 | ||||
|             console.log('err.response: ', err.response) | ||||
| 
 | ||||
|             // return { data: err.response.data, status: err.response.status }
 | ||||
| 
 | ||||
|       console.log("err.response: ", err.response); | ||||
|     } else if (err.request) { | ||||
|             // The client never received a response, and the request was never left
 | ||||
|             console.log('err.request: ', err.request) | ||||
|       console.log("err.request: ", err.request); | ||||
|     } else { | ||||
|             // Anything else
 | ||||
|       console.error(`Erro ao consultar endpoint ${url}: ${err}`); | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|     return response | ||||
| 
 | ||||
| } | ||||
|   return response; | ||||
| }; | ||||
| 
 | ||||
| export default endPointQuery; | ||||
|  | @ -65,6 +65,17 @@ class Whatsapp extends Model<Whatsapp> { | |||
|   @Column | ||||
|   phoneNumberId: string; | ||||
| 
 | ||||
|   @Column | ||||
|   classification: string; | ||||
| 
 | ||||
|   @Column | ||||
|   wabaId: string; | ||||
| 
 | ||||
|   @Default(false) | ||||
|   @AllowNull | ||||
|   @Column | ||||
|   isOfficial: boolean; | ||||
| 
 | ||||
|   @Default(false) | ||||
|   @AllowNull | ||||
|   @Column | ||||
|  |  | |||
|  | @ -16,6 +16,10 @@ const DeleteWhatsAppMessage = async (messageId: string): Promise<Message | any> | |||
|     ] | ||||
|   }); | ||||
|    | ||||
|   if(message && message?.phoneNumberId){ | ||||
|     throw new AppError("Mensagens enviada pela API Oficial do Whatsapp não são deletadas!"); | ||||
|   } | ||||
| 
 | ||||
|   if (!message) { | ||||
|     throw new AppError("No message found with this ID."); | ||||
|   } | ||||
|  | @ -32,18 +36,6 @@ const DeleteWhatsAppMessage = async (messageId: string): Promise<Message | any> | |||
|     limit: limit | ||||
|   })  | ||||
| 
 | ||||
|   // console.log('messageToDelete.data.data: ',messageToDelete.data.data)
 | ||||
|   | ||||
|   // const { ticket } = message;
 | ||||
| 
 | ||||
|   // const messageToDelete = await GetWbotMessage(ticket, messageId);
 | ||||
| 
 | ||||
|   // try {
 | ||||
|   //   await messageToDelete.delete(true);
 | ||||
|   // } catch (err) {
 | ||||
|   //   throw new AppError("ERR_DELETE_WAPP_MSG");
 | ||||
|   // }
 | ||||
| 
 | ||||
|   if (messageToDelete && messageToDelete.data.data) { | ||||
|     await message.update({ isDeleted: true }); | ||||
|   } | ||||
|  |  | |||
|  | @ -21,7 +21,6 @@ import ListWhatsAppsNumber from "../WhatsappService/ListWhatsAppsNumber"; | |||
| import { getWbot } from "../../libs/wbot"; | ||||
| import { json } from "sequelize/types"; | ||||
| 
 | ||||
| import sendMessageMultiSession from "../../helpers/TrySendMessageMultiSession"; | ||||
| import { restartWhatsSession } from "../../helpers/RestartWhatsSession"; | ||||
| // import { insertOrUpeateWhatsCache, searchWhatsappCache } from "../../helpers/WhatsCache";
 | ||||
| import GetDefaultWhatsApp from "../../helpers/GetDefaultWhatsApp"; | ||||
|  | @ -83,6 +82,7 @@ const SendWhatsAppMessage = async ({ | |||
| 
 | ||||
|     if (!listWhatsapp) { | ||||
|       listWhatsapp = await ListWhatsAppsNumber(ticket.whatsappId, "CONNECTED"); | ||||
|       console.log("@@@@@@@@@@@ listWhatsapp: ", listWhatsapp); | ||||
|     } | ||||
| 
 | ||||
|     if ( | ||||
|  | @ -106,20 +106,21 @@ const SendWhatsAppMessage = async ({ | |||
|       listWhatsapp.whatsapps.length == 0 && | ||||
|       listWhatsapp.whatsapp.status != "CONNECTED" | ||||
|     ) { | ||||
|       console.log("listWhatsapp.whatsapps == 0"); | ||||
| 
 | ||||
|       whatsapps = await wbotByUserQueue({ userId: ticket.userId }); | ||||
| 
 | ||||
|       console.log("============> The whatsapps: ", whatsapps); | ||||
| 
 | ||||
|       if (whatsapps.length > 0) { | ||||
|         whatsapps = whatsapps.filter((w: any) => !w?.isOfficial); | ||||
| 
 | ||||
|         if (whatsapps.length > 1) { | ||||
|           await ticket.update({ | ||||
|             whatsappId: whatsapps[+WhatsIndex(whatsapps)].id | ||||
|           }); | ||||
|         } else { | ||||
|         } else if (whatsapps && whatsapps.length == 1) { | ||||
|           await ticket.update({ whatsappId: whatsapps[0].id }); | ||||
|         } | ||||
|         else{ | ||||
|           throw new Error('Sessão de Whatsapp desconectada! Entre em contato com o suporte.') | ||||
|         } | ||||
|       } | ||||
|     } | ||||
| 
 | ||||
|  |  | |||
|  | @ -153,7 +153,7 @@ const verifyMediaMessage = async ( | |||
|     throw new Error("ERR_WAPP_DOWNLOAD_MEDIA"); | ||||
|   } | ||||
|    | ||||
|   const messageData = { | ||||
|   let messageData = { | ||||
|     id: msg.id.id, | ||||
|     ticketId: ticket.id, | ||||
|     contactId: msg.fromMe ? undefined : contact.id, | ||||
|  | @ -165,10 +165,16 @@ const verifyMediaMessage = async ( | |||
|     quotedMsgId: quotedMsg | ||||
|   }; | ||||
|   | ||||
| 
 | ||||
|   if (!ticket?.phoneNumberId) { | ||||
|     if (!media.filename) { | ||||
|       const ext = media.mimetype.split("/")[1].split(";")[0]; | ||||
|       media.filename = `${new Date().getTime()}.${ext}`; | ||||
|       messageData = { | ||||
|         ...messageData, | ||||
|         mediaUrl: media.filename, | ||||
|         body: media.filename | ||||
|       }; | ||||
|     }  | ||||
| 
 | ||||
|     try { | ||||
|  | @ -189,6 +195,77 @@ const verifyMediaMessage = async ( | |||
|   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 ( | ||||
|   msg: any, | ||||
|   ticket: Ticket, | ||||
|  |  | |||
|  | @ -13,6 +13,9 @@ interface Request { | |||
|   farewellMessage?: string; | ||||
|   status?: string; | ||||
|   isDefault?: boolean; | ||||
|   phoneNumberId?: string; | ||||
|   wabaId?: string; | ||||
|   isOfficial?: boolean; | ||||
| } | ||||
| 
 | ||||
| interface Response { | ||||
|  | @ -29,10 +32,11 @@ const CreateWhatsAppService = async ({ | |||
|   greetingMessage, | ||||
|   farewellMessage, | ||||
|   isDefault = false, | ||||
|   isOfficial = false, | ||||
|   phoneNumberId, | ||||
|   wabaId | ||||
| }: Request): Promise<Response> => { | ||||
| 
 | ||||
|   try { | ||||
| 
 | ||||
|     const schema = Yup.object().shape({ | ||||
|       name: Yup.string() | ||||
|         .required() | ||||
|  | @ -48,12 +52,11 @@ const CreateWhatsAppService = async ({ | |||
|             return !nameExists; | ||||
|           } | ||||
|         ), | ||||
|       isDefault: Yup.boolean().required(), | ||||
|       urlApi: Yup.string().required() | ||||
|       isDefault: Yup.boolean().required() | ||||
|     }); | ||||
| 
 | ||||
|     try { | ||||
|       await schema.validate({ name, status, isDefault, urlApi }); | ||||
|       await schema.validate({ name, status, isDefault }); | ||||
|     } catch (err: any) { | ||||
|       throw new AppError(err.message); | ||||
|     } | ||||
|  | @ -70,7 +73,6 @@ const CreateWhatsAppService = async ({ | |||
|       }); | ||||
|       if (oldDefaultWhatsapp) { | ||||
|         await oldDefaultWhatsapp.update({ isDefault: false }); | ||||
|          | ||||
|       } | ||||
|     } | ||||
| 
 | ||||
|  | @ -78,6 +80,12 @@ const CreateWhatsAppService = async ({ | |||
|       throw new AppError("ERR_WAPP_GREETING_REQUIRED"); | ||||
|     } | ||||
| 
 | ||||
|     const classification = isOfficial ? "GREEN" : null; | ||||
| 
 | ||||
|     if (isOfficial) { | ||||
|       status = "CONNECTED"; | ||||
|     } | ||||
| 
 | ||||
|     const whatsapp = await Whatsapp.create( | ||||
|       { | ||||
|         name, | ||||
|  | @ -86,7 +94,11 @@ const CreateWhatsAppService = async ({ | |||
|         urlApi, | ||||
|         greetingMessage, | ||||
|         farewellMessage, | ||||
|         isDefault | ||||
|         isDefault, | ||||
|         phoneNumberId, | ||||
|         wabaId, | ||||
|         isOfficial, | ||||
|         classification | ||||
|       }, | ||||
|       { include: ["queues"] } | ||||
|     ); | ||||
|  | @ -94,13 +106,10 @@ const CreateWhatsAppService = async ({ | |||
|     await AssociateWhatsappQueue(whatsapp, queueIds); | ||||
| 
 | ||||
|     return { whatsapp, oldDefaultWhatsapp }; | ||||
|      | ||||
|   } catch (error: any) { | ||||
|     console.error('===> Error on CreateWhatsAppService.ts file: \n', error) | ||||
|     console.error("===> Error on CreateWhatsAppService.ts file: \n", error); | ||||
|     throw new AppError(error.message); | ||||
|   } | ||||
| 
 | ||||
|    | ||||
| }; | ||||
| 
 | ||||
| export default CreateWhatsAppService; | ||||
|  |  | |||
|  | @ -12,14 +12,14 @@ const ListWhatsAppsNumber = async ( | |||
|     if (status) { | ||||
|       whatsapps = await Whatsapp.findAll({ | ||||
|         raw: true, | ||||
|         where: { number: whatsapp.number, status: status }, | ||||
|         attributes: ["id", "number", "status", "isDefault", "url"] | ||||
|         where: { number: whatsapp.number, status: status, }, | ||||
|         attributes: ["id", "number", "status", "isDefault", "url", 'isOfficial'] | ||||
|       }); | ||||
|     } else { | ||||
|       whatsapps = await Whatsapp.findAll({ | ||||
|         raw: true, | ||||
|         where: { number: whatsapp.number }, | ||||
|         attributes: ["id", "number", "status", "isDefault", "url"] | ||||
|         attributes: ["id", "number", "status", "isDefault", "url", 'isOfficial'] | ||||
|       }); | ||||
|     } | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,8 +9,6 @@ import AssociateWhatsappQueue from "./AssociateWhatsappQueue"; | |||
| import { getWbot } from "../../libs/wbot"; | ||||
| import { restartWhatsSession } from "../../helpers/RestartWhatsSession"; | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
| interface WhatsappData { | ||||
|   name?: string; | ||||
|   url?: string; | ||||
|  | @ -18,6 +16,9 @@ interface WhatsappData { | |||
|   status?: string; | ||||
|   session?: string; | ||||
|   isDefault?: boolean; | ||||
|   isOfficial?: boolean; | ||||
|   phoneNumberId?: string; | ||||
|   wabaId?: string; | ||||
|   greetingMessage?: string; | ||||
|   farewellMessage?: string; | ||||
|   queueIds?: number[]; | ||||
|  | @ -37,19 +38,20 @@ const UpdateWhatsAppService = async ({ | |||
|   whatsappData, | ||||
|   whatsappId | ||||
| }: Request): Promise<Response> => { | ||||
| 
 | ||||
|   try { | ||||
| 
 | ||||
|     const schema = Yup.object().shape({ | ||||
|       name: Yup.string().min(2), | ||||
|       status: Yup.string(), | ||||
|       isDefault: Yup.boolean() | ||||
|     }); | ||||
| 
 | ||||
|     const { | ||||
|     let { | ||||
|       name, | ||||
|       status, | ||||
|       isDefault, | ||||
|       phoneNumberId, | ||||
|       wabaId, | ||||
|       isOfficial, | ||||
|       url, | ||||
|       urlApi, | ||||
|       session, | ||||
|  | @ -58,8 +60,6 @@ const UpdateWhatsAppService = async ({ | |||
|       queueIds = [] | ||||
|     } = whatsappData; | ||||
| 
 | ||||
|    | ||||
|    | ||||
|     try { | ||||
|       await schema.validate({ name, status, isDefault }); | ||||
|     } catch (err: any) { | ||||
|  | @ -85,10 +85,23 @@ const UpdateWhatsAppService = async ({ | |||
| 
 | ||||
|     // console.log('############## whatsapp: ', JSON.parse(JSON.stringify(whatsapp)))
 | ||||
| 
 | ||||
|     if (name && !name.includes(whatsapp.number) && whatsapp.status === 'CONNECTED') { | ||||
|    | ||||
|     if ( | ||||
|       name && | ||||
|       !name.includes(whatsapp.number) && | ||||
|       whatsapp.status === "CONNECTED" && | ||||
|       !whatsapp.isOfficial | ||||
|     ) { | ||||
|       throw new AppError("ERR_WAPP_WRONG_SESSION_NAME"); | ||||
|     } | ||||
| 
 | ||||
|     const classification = isOfficial ? "GREEN" : null; | ||||
| 
 | ||||
|     if (isOfficial) { | ||||
|       status = "CONNECTED"; | ||||
|     } | ||||
| 
 | ||||
|     if (whatsapp.isOfficial && !isOfficial) { | ||||
|       status = "OPENING"; | ||||
|     } | ||||
| 
 | ||||
|     await whatsapp.update({ | ||||
|  | @ -99,7 +112,11 @@ const UpdateWhatsAppService = async ({ | |||
|       urlApi, | ||||
|       greetingMessage, | ||||
|       farewellMessage, | ||||
|       isDefault | ||||
|       isDefault, | ||||
|       isOfficial, | ||||
|       phoneNumberId, | ||||
|       wabaId, | ||||
|       classification | ||||
|     }); | ||||
| 
 | ||||
|     // await insertOrUpeateWhatsCache(`whatsapp:${whatsapp.id}`, {
 | ||||
|  | @ -114,12 +131,10 @@ const UpdateWhatsAppService = async ({ | |||
|     await AssociateWhatsappQueue(whatsapp, queueIds); | ||||
| 
 | ||||
|     return { whatsapp, oldDefaultWhatsapp }; | ||||
| 
 | ||||
|   } catch (error: any) { | ||||
|     console.error('===> Error on UpdateWhatsAppService.ts file: \n', error) | ||||
|     console.error("===> Error on UpdateWhatsAppService.ts file: \n", error); | ||||
|     throw new AppError(error.message); | ||||
|   } | ||||
|   | ||||
| }; | ||||
| 
 | ||||
| export default UpdateWhatsAppService; | ||||
|  |  | |||
|  | @ -8,7 +8,6 @@ import Select from "@material-ui/core/Select" | |||
| import FormControl from "@material-ui/core/FormControl" | ||||
| import InputLabel from "@material-ui/core/InputLabel" | ||||
| import MenuItem from "@material-ui/core/MenuItem" | ||||
| import LinearProgress from "@material-ui/core/LinearProgress" | ||||
| import { makeStyles } from "@material-ui/core" | ||||
| 
 | ||||
| import DialogActions from "@material-ui/core/DialogActions" | ||||
|  | @ -21,9 +20,6 @@ import { AuthContext } from "../../context/Auth/AuthContext" | |||
| 
 | ||||
| import toastError from "../../errors/toastError" | ||||
| 
 | ||||
| import { WhatsAppsContext } from "../../context/WhatsApp/WhatsAppsContext" | ||||
| 
 | ||||
| 
 | ||||
| import api from "../../services/api" | ||||
| 
 | ||||
| const useStyles = makeStyles((theme) => ({ | ||||
|  | @ -40,7 +36,6 @@ const useStyles = makeStyles((theme) => ({ | |||
| 
 | ||||
| const ContactCreateTicketModal = ({ modalOpen, onClose, contactId }) => { | ||||
|   const { user } = useContext(AuthContext) | ||||
|   const { whatsApps } = useContext(WhatsAppsContext) | ||||
| 
 | ||||
|   let isMounted = useRef(true) | ||||
| 
 | ||||
|  | @ -65,8 +60,6 @@ const ContactCreateTicketModal = ({ modalOpen, onClose, contactId }) => { | |||
| 
 | ||||
|           const { data } = await api.get("/whatsapp/official/matchQueueUser", { params: { userId: user.id, queueId: selectedQueue }, }) | ||||
| 
 | ||||
|           console.log('DATA: ', data) | ||||
|   | ||||
|           setQueues(data) | ||||
| 
 | ||||
|         } catch (err) { | ||||
|  | @ -79,7 +72,7 @@ const ContactCreateTicketModal = ({ modalOpen, onClose, contactId }) => { | |||
|     }, 500) | ||||
|     return () => clearTimeout(delayDebounceFn) | ||||
| 
 | ||||
|   }, [user]) | ||||
|   }, [user, selectedQueue]) | ||||
| 
 | ||||
|   const handleClose = () => { | ||||
|     onClose() | ||||
|  | @ -87,9 +80,7 @@ const ContactCreateTicketModal = ({ modalOpen, onClose, contactId }) => { | |||
| 
 | ||||
|   const handleSaveTicket = useCallback(async (contactId, userId, queueId, selectedWhatsId, whatsQueue, queues) => { | ||||
| 
 | ||||
|     console.log(`contactId: ${contactId}, userId: ${userId}, queueId: ${queueId}, selectedWhatsId: ${selectedWhatsId}, whatsQueue: ${whatsQueue}, queues: ${queues}`) | ||||
| 
 | ||||
|     if (queues && queues.length == 1 && queues[0].disable) { | ||||
|     if (queues && queues.length === 1 && queues[0].disable) { | ||||
|       toast.warn('Não é possível criar um Ticket porque a fila a qual você esta adicionado(a) não está associado a nenhum numero!') | ||||
|       return | ||||
|     } | ||||
|  | @ -137,15 +128,11 @@ const ContactCreateTicketModal = ({ modalOpen, onClose, contactId }) => { | |||
| 
 | ||||
|   useEffect(() => { | ||||
| 
 | ||||
|     if (selectedQueue && selectedQueue.length === 0 || !selectedQueue) { | ||||
|     if (selectedQueue && (selectedQueue.length === 0 || !selectedQueue)) { | ||||
|       setDisabled(true) | ||||
|       setWhatsQueue(null) | ||||
|     } | ||||
| 
 | ||||
|     // if (modalOpen && queues.length <= 1) {
 | ||||
|     //   handleSaveTicket(contactId, user.id, selectedQueue, selectedWhatsId, whatsQueue, queues)
 | ||||
|     // }
 | ||||
| 
 | ||||
|     if (!Array.isArray(whatsQueue)) { | ||||
|       setSelectedWhatsId(null) | ||||
|       setWhatsQueue(null) | ||||
|  | @ -170,6 +157,8 @@ const ContactCreateTicketModal = ({ modalOpen, onClose, contactId }) => { | |||
| 
 | ||||
|           const { data } = await api.get("/whatsapp/official/matchQueue", { params: { userId: user.id, queueId: selectedQueue }, }) | ||||
| 
 | ||||
|           console.log('WHATSAPP DATA: ', data) | ||||
| 
 | ||||
|           setWhatsQueue(data) | ||||
| 
 | ||||
|           setDisabled(false) | ||||
|  | @ -186,10 +175,10 @@ const ContactCreateTicketModal = ({ modalOpen, onClose, contactId }) => { | |||
| 
 | ||||
|   }, [selectedQueue, user.id]) | ||||
| 
 | ||||
| 
 | ||||
|   // if (modalOpen && queues.length <= 1) {
 | ||||
|   //   return <LinearProgress />
 | ||||
|   // }
 | ||||
|   useEffect(() => { | ||||
|     console.log('selectedWhatsId: ', selectedWhatsId) | ||||
|     console.log('whatsQuee: ', whatsQueue) | ||||
|   }, [whatsQueue]) | ||||
| 
 | ||||
|   return ( | ||||
|     <Dialog open={modalOpen} onClose={handleClose} maxWidth="xs" scroll="paper" classes={{ paper: classes.paper }}> | ||||
|  |  | |||
|  | @ -41,28 +41,6 @@ const useStyles = makeStyles(theme => ({ | |||
| }))  | ||||
| 
 | ||||
| 
 | ||||
| let _fifo | ||||
| 
 | ||||
| // const onlineEmitter = async (socket, user) => {
 | ||||
| 
 | ||||
| // 	try {
 | ||||
| // 		clearInterval(_fifo);
 | ||||
| 
 | ||||
| // 		socket.emit("online", user.id)
 | ||||
| 
 | ||||
| // 	} catch (error) {
 | ||||
| // 		console.log('error on onlineEmitter: ', error)
 | ||||
| // 	}
 | ||||
| // 	finally {
 | ||||
| // 		_fifo = setInterval(onlineEmitter, 3000);
 | ||||
| // 	}
 | ||||
| // }
 | ||||
| 
 | ||||
| // _fifo = setInterval(onlineEmitter, 3000);
 | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
| const NotificationsPopOver = () => { | ||||
| 	const classes = useStyles() | ||||
| 
 | ||||
|  |  | |||
|  | @ -60,7 +60,7 @@ const SessionSchema = Yup.object().shape({ | |||
|     .required('Required'), | ||||
| }) | ||||
| 
 | ||||
| const WhatsAppModal = ({ open, onClose, whatsAppId }) => { | ||||
| const WhatsAppModal = ({ open, onClose, whatsAppId, whatsAppOfficial }) => { | ||||
|   const classes = useStyles() | ||||
|   const initialState = { | ||||
|     name: '', | ||||
|  | @ -69,12 +69,17 @@ const WhatsAppModal = ({ open, onClose, whatsAppId }) => { | |||
|     greetingMessage: '', | ||||
|     farewellMessage: '', | ||||
|     isDefault: false, | ||||
|     isOfficial: false, | ||||
|     phoneNumberId: '', | ||||
|     wabaId: '' | ||||
|   } | ||||
| 
 | ||||
|   const { user } = useContext(AuthContext) | ||||
| 
 | ||||
|   const [whatsApp, setWhatsApp] = useState(initialState) | ||||
|   const [selectedQueueIds, setSelectedQueueIds] = useState([]) | ||||
|   const [isOfficial, setIsOfficial] = useState(false) | ||||
| 
 | ||||
| 
 | ||||
|   useEffect(() => { | ||||
|     const fetchSession = async () => { | ||||
|  | @ -82,7 +87,9 @@ const WhatsAppModal = ({ open, onClose, whatsAppId }) => { | |||
| 
 | ||||
|       try { | ||||
|         const { data } = await api.get(`whatsapp/${whatsAppId}`)  | ||||
| 
 | ||||
|         setWhatsApp(data) | ||||
|         setIsOfficial(data?.isOfficial) | ||||
| 
 | ||||
|         const whatsQueueIds = data.queues?.map((queue) => queue.id) | ||||
|         setSelectedQueueIds(whatsQueueIds) | ||||
|  | @ -94,6 +101,17 @@ const WhatsAppModal = ({ open, onClose, whatsAppId }) => { | |||
|   }, [whatsAppId]) | ||||
| 
 | ||||
|   const handleSaveWhatsApp = async (values) => { | ||||
| 
 | ||||
|     console.log('values1: ', values) | ||||
| 
 | ||||
|     const { isOfficial } = values | ||||
| 
 | ||||
|     if (!isOfficial) { | ||||
|       values.phoneNumberId = '' | ||||
|       values.wabaId = '' | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
|     const whatsappData = { ...values, queueIds: selectedQueueIds } | ||||
| 
 | ||||
|     let response = null | ||||
|  | @ -131,6 +149,7 @@ const WhatsAppModal = ({ open, onClose, whatsAppId }) => { | |||
|   const handleClose = () => { | ||||
|     onClose() | ||||
|     setWhatsApp(initialState) | ||||
|     setIsOfficial(false) | ||||
|   } | ||||
| 
 | ||||
|   return ( | ||||
|  | @ -189,8 +208,26 @@ const WhatsAppModal = ({ open, onClose, whatsAppId }) => { | |||
|                           } | ||||
|                           label={i18n.t('whatsappModal.form.default')} | ||||
|                         /> | ||||
| 
 | ||||
|                         {whatsAppOfficial && | ||||
|                           <FormControlLabel | ||||
|                             control={ | ||||
|                               <Field | ||||
|                                 as={Switch} | ||||
|                                 color="primary" | ||||
|                                 name="isOfficial" | ||||
|                                 onClick={() => setIsOfficial(!isOfficial)} | ||||
|                                 checked={values.isOfficial} | ||||
|                               /> | ||||
|                             } | ||||
|                             label={'Whatsapp Oficial'} | ||||
|                           /> | ||||
|                         } | ||||
| 
 | ||||
| 
 | ||||
|                       </div> | ||||
|                       <div className={classes.multFieldLine}> | ||||
| 
 | ||||
|                       {!isOfficial ? <div className={classes.multFieldLine}> | ||||
|                         <Field | ||||
|                           as={TextField} | ||||
|                           label="url API" | ||||
|  | @ -213,7 +250,39 @@ const WhatsAppModal = ({ open, onClose, whatsAppId }) => { | |||
|                           margin="dense" | ||||
|                           className={classes.textField} | ||||
|                         /> | ||||
|                       </div> : | ||||
| 
 | ||||
|                         <div className={classes.multFieldLine}> | ||||
|                           <Field | ||||
|                             as={TextField} | ||||
|                             label="Phone number id" | ||||
|                             autoFocus | ||||
|                             name="phoneNumberId" | ||||
|                             error={touched.name && Boolean(errors.name)} | ||||
|                             helperText={touched.name && errors.name} | ||||
|                             variant="outlined" | ||||
|                             margin="dense" | ||||
|                             className={classes.textField} | ||||
|                           /> | ||||
| 
 | ||||
|                           <Field | ||||
|                             as={TextField} | ||||
|                             label="WABA ID" | ||||
|                             autoFocus | ||||
|                             name="wabaId" | ||||
|                             error={touched.name && Boolean(errors.name)} | ||||
|                             helperText={touched.name && errors.name} | ||||
|                             variant="outlined" | ||||
|                             margin="dense" | ||||
|                             className={classes.textField} | ||||
|                           /> | ||||
|                         </div> | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
|                       } | ||||
| 
 | ||||
| 
 | ||||
|                     </> | ||||
|                   )} | ||||
|                 /> | ||||
|  |  | |||
|  | @ -5,9 +5,9 @@ import { format, parseISO } from 'date-fns' | |||
| import openSocket from 'socket.io-client' | ||||
| 
 | ||||
| import { makeStyles } from '@material-ui/core/styles' | ||||
| import { green } from '@material-ui/core/colors' | ||||
| import { green, red, yellow, grey } from '@material-ui/core/colors' | ||||
| 
 | ||||
| import Settings from "@material-ui/icons/Settings"; | ||||
| import Settings from "@material-ui/icons/Settings" | ||||
| 
 | ||||
| import { | ||||
|   Button, | ||||
|  | @ -27,6 +27,7 @@ import { | |||
|   CheckCircle, | ||||
|   SignalCellularConnectedNoInternet2Bar, | ||||
|   SignalCellularConnectedNoInternet0Bar, | ||||
|   FiberManualRecord, | ||||
|   SignalCellular4Bar, | ||||
|   CropFree, | ||||
|   DeleteOutline, | ||||
|  | @ -103,6 +104,33 @@ const CustomToolTip = ({ title, content, children }) => { | |||
|   ) | ||||
| } | ||||
| 
 | ||||
| const whatsAppClasssification = ({ isOfficial, classification }) => { | ||||
| 
 | ||||
|   if (isOfficial && classification) { | ||||
| 
 | ||||
|     if (classification === 'GREEN') | ||||
|       return <CustomToolTip title={'Qualidade alta'}> | ||||
|         <FiberManualRecord style={{ color: green[500] }} /> | ||||
|       </CustomToolTip> | ||||
| 
 | ||||
|     if (classification === 'YELLOW') | ||||
|       return <CustomToolTip title={'Qualidade média'}> | ||||
|         <FiberManualRecord style={{ color: yellow[500] }} /> | ||||
|       </CustomToolTip> | ||||
| 
 | ||||
|     if (classification === 'RED') | ||||
|       return <CustomToolTip title={'Qualidade baixa'}> | ||||
|         <FiberManualRecord style={{ color: red[500] }} /> | ||||
|       </CustomToolTip> | ||||
|   } | ||||
|   else { | ||||
|     return <CustomToolTip title={i18n.t('connections.toolTips.connected.title')}> | ||||
|       <SignalCellular4Bar style={{ color: green[500] }} /> | ||||
|     </CustomToolTip> | ||||
|   } | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| const Connections = () => { | ||||
|   //--------
 | ||||
|   const { user } = useContext(AuthContext) | ||||
|  | @ -118,8 +146,6 @@ const Connections = () => { | |||
| 
 | ||||
|   const [diskSpaceInfo, setDiskSpaceInfo] = useState({})  | ||||
| 
 | ||||
|   const [disabled, setDisabled] = useState(true) | ||||
| 
 | ||||
|   const [settings, setSettings] = useState([]) | ||||
| 
 | ||||
|   const [buttons, setClicks] = useState([]) | ||||
|  | @ -139,6 +165,7 @@ const Connections = () => { | |||
|     const fetchSession = async () => { | ||||
|       try { | ||||
|         const { data } = await api.get('/settings') | ||||
| 
 | ||||
|         setSettings(data.settings) | ||||
|       } catch (err) { | ||||
|         toastError(err) | ||||
|  | @ -149,7 +176,6 @@ const Connections = () => { | |||
| 
 | ||||
|   const getSettingValue = (key) => { | ||||
|     const { value } = settings.find((s) => s.key === key) | ||||
| 
 | ||||
|     return value | ||||
|   } | ||||
| 
 | ||||
|  | @ -162,6 +188,7 @@ const Connections = () => { | |||
|   } | ||||
| 
 | ||||
|   const handleRestartWhatsAppSession = async (whatsapp) => { | ||||
| 
 | ||||
|     try { | ||||
|       whatsapp.disabled = true | ||||
| 
 | ||||
|  | @ -280,6 +307,9 @@ const Connections = () => { | |||
|   } | ||||
| 
 | ||||
|   const renderActionButtons = (whatsApp) => { | ||||
| 
 | ||||
|     if (whatsApp.isOfficial) return | ||||
| 
 | ||||
|     return ( | ||||
|       <Can | ||||
|         role={user.profile} | ||||
|  | @ -352,7 +382,15 @@ const Connections = () => { | |||
|             <SignalCellularConnectedNoInternet0Bar color="secondary" /> | ||||
|           </CustomToolTip> | ||||
|         )} | ||||
|         {whatsApp.status === 'OPENING' && ( | ||||
|         {whatsApp.status === 'OPENING' && whatsApp.isOfficial && (settings && | ||||
|           settings.length > 0 && | ||||
|           getSettingValue('whatsaAppCloudApi') && | ||||
|           getSettingValue('whatsaAppCloudApi') === 'disabled') && ( | ||||
|             <CustomToolTip title={'Whatsapp Cloud API está desativado'}> | ||||
|               <FiberManualRecord style={{ color: grey[500] }} /> | ||||
|             </CustomToolTip>  | ||||
|           )} | ||||
|         {whatsApp.status === 'OPENING' && !whatsApp.isOfficial && ( | ||||
|           <CircularProgress size={24} className={classes.buttonProgress} /> | ||||
|         )} | ||||
|         {whatsApp.status === 'qrcode' && ( | ||||
|  | @ -363,11 +401,11 @@ const Connections = () => { | |||
|             <CropFree /> | ||||
|           </CustomToolTip> | ||||
|         )} | ||||
| 
 | ||||
|         {whatsApp.status === 'CONNECTED' && ( | ||||
|           <CustomToolTip title={i18n.t('connections.toolTips.connected.title')}> | ||||
|             <SignalCellular4Bar style={{ color: green[500] }} /> | ||||
|           </CustomToolTip> | ||||
|           whatsAppClasssification({ ...whatsApp, }) | ||||
|         )} | ||||
| 
 | ||||
|         {(whatsApp.status === 'TIMEOUT' || whatsApp.status === 'PAIRING') && ( | ||||
|           <CustomToolTip | ||||
|             title={i18n.t('connections.toolTips.timeout.title')} | ||||
|  | @ -397,8 +435,6 @@ const Connections = () => { | |||
|             params: { status: 'status' }, | ||||
|           })  | ||||
| 
 | ||||
|           setDisabled(false) | ||||
| 
 | ||||
|           setClicks((buttons) => | ||||
|             buttons.map((e) => { | ||||
|               return { id: e.id, disabled: false } | ||||
|  | @ -464,6 +500,10 @@ const Connections = () => { | |||
|             open={whatsAppModalOpen} | ||||
|             onClose={handleCloseWhatsAppModal} | ||||
|             whatsAppId={!qrModalOpen && selectedWhatsApp?.id} | ||||
|             whatsAppOfficial={(settings && | ||||
|               settings.length > 0 && | ||||
|               getSettingValue('whatsaAppCloudApi') && | ||||
|               getSettingValue('whatsaAppCloudApi') === 'enabled') ? true : false} | ||||
|           /> | ||||
| 
 | ||||
|           <ConfigModal | ||||
|  | @ -567,13 +607,13 @@ const Connections = () => { | |||
|                       yes={() => <TableCell align="center">Restore</TableCell>} | ||||
|                     /> | ||||
| 
 | ||||
|                     <Can | ||||
|                     {/* <Can | ||||
|                       role={user.profile} | ||||
|                       perform="connection-button:show" | ||||
|                       yes={() => ( | ||||
|                         <TableCell align="center">Session MB</TableCell> | ||||
|                       )} | ||||
|                     /> | ||||
|                     /> */} | ||||
| 
 | ||||
|                     <TableCell align="center"> | ||||
|                       {i18n.t('connections.table.lastUpdate')} | ||||
|  | @ -592,8 +632,24 @@ const Connections = () => { | |||
|                   ) : ( | ||||
|                     <> | ||||
|                       {whatsApps?.length > 0 && | ||||
|                         whatsApps.map((whatsApp) => ( | ||||
|                           <TableRow key={whatsApp.id}> | ||||
|                         whatsApps.map((whatsApp) => { | ||||
| 
 | ||||
|                           let disabledRow = {} | ||||
|                           let disabled = false | ||||
| 
 | ||||
|                           if (whatsApp?.isOfficial && ((settings && | ||||
|                             settings.length > 0 && | ||||
|                             getSettingValue('whatsaAppCloudApi') && | ||||
|                             getSettingValue('whatsaAppCloudApi') === 'disabled'))) { | ||||
|                             disabledRow = { | ||||
|                               'opacity': '0.5', | ||||
|                               // 'pointer-events': 'none'
 | ||||
|                             } | ||||
|                             disabled = true | ||||
|                           } | ||||
| 
 | ||||
|                           return ( | ||||
|                             <TableRow key={whatsApp.id} style={disabledRow}> | ||||
|                               <TableCell align="center"> | ||||
|                                 {whatsApp.name} | ||||
|                               </TableCell> | ||||
|  | @ -617,6 +673,8 @@ const Connections = () => { | |||
|                                 perform="connection-button:show" | ||||
|                                 yes={() => ( | ||||
|                                   <TableCell align="center"> | ||||
| 
 | ||||
|                                     {!whatsApp?.isOfficial && | ||||
|                                       <Button | ||||
|                                         disabled={ | ||||
|                                           whatsApp.disabled || disabled | ||||
|  | @ -631,12 +689,14 @@ const Connections = () => { | |||
|                                         } | ||||
|                                       > | ||||
|                                         Restore | ||||
|                                   </Button> | ||||
|                                       </Button>} | ||||
| 
 | ||||
| 
 | ||||
|                                   </TableCell> | ||||
|                                 )} | ||||
|                               /> | ||||
| 
 | ||||
|                             <Can | ||||
|                               {/* <Can | ||||
|                                 role={user.profile} | ||||
|                                 perform="connection-button:show" | ||||
|                                 yes={() => ( | ||||
|  | @ -651,7 +711,7 @@ const Connections = () => { | |||
|                                     </CustomToolTip> | ||||
|                                   </TableCell> | ||||
|                                 )} | ||||
|                             /> | ||||
|                               /> */} | ||||
| 
 | ||||
|                               <TableCell align="center"> | ||||
|                                 {format( | ||||
|  | @ -726,7 +786,8 @@ const Connections = () => { | |||
|                                 /> | ||||
|                               </TableCell> | ||||
|                             </TableRow> | ||||
|                         ))} | ||||
|                           ) | ||||
|                         })} | ||||
|                     </> | ||||
|                   )} | ||||
|                 </TableBody> | ||||
|  |  | |||
|  | @ -310,21 +310,6 @@ const Contacts = () => { | |||
|     setIsCreateTicketModalOpen(false) | ||||
|   }  | ||||
|     | ||||
|   // const handleSaveTicket = async (contactId) => {
 | ||||
|   //   if (!contactId) return;
 | ||||
|   //   setLoading(true);
 | ||||
|   //   try {
 | ||||
|   //     const { data: ticket } = await api.post("/tickets", {
 | ||||
|   //       contactId: contactId,
 | ||||
|   //       userId: user?.id,
 | ||||
|   //       status: "open",
 | ||||
|   //     });
 | ||||
|   //     history.push(`/tickets/${ticket.id}`);
 | ||||
|   //   } catch (err) {
 | ||||
|   //     toastError(err);
 | ||||
|   //   }
 | ||||
|   //   setLoading(false);
 | ||||
|   // };
 | ||||
| 
 | ||||
|   const hadleEditContact = (contactId) => { | ||||
|     setSelectedContactId(contactId) | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue