wexa-chat 0.3.2 → 0.3.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.cts +4 -0
- package/dist/index.d.ts +4 -0
- package/dist/index.js +189 -123
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +189 -123
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.d.cts
CHANGED
|
@@ -176,11 +176,13 @@ interface IMessage extends Document {
|
|
|
176
176
|
linkedin?: {
|
|
177
177
|
subject?: string;
|
|
178
178
|
isInMail?: boolean;
|
|
179
|
+
linkedinApi?: string;
|
|
179
180
|
senderName?: string;
|
|
180
181
|
senderProfileUrl?: string;
|
|
181
182
|
};
|
|
182
183
|
whatsapp?: {
|
|
183
184
|
senderName?: string;
|
|
185
|
+
senderPhone?: string;
|
|
184
186
|
};
|
|
185
187
|
};
|
|
186
188
|
parentMessageId?: string;
|
|
@@ -276,6 +278,7 @@ type SendMessageArgs = {
|
|
|
276
278
|
linkedin?: {
|
|
277
279
|
subject?: string;
|
|
278
280
|
isInMail?: boolean;
|
|
281
|
+
linkedinApi?: 'classic' | 'recruiter' | 'sales_navigator';
|
|
279
282
|
};
|
|
280
283
|
};
|
|
281
284
|
};
|
|
@@ -302,6 +305,7 @@ type ReceiveWhatsappMessageArgs = {
|
|
|
302
305
|
message: string;
|
|
303
306
|
messageId?: string;
|
|
304
307
|
senderName?: string;
|
|
308
|
+
senderPhone?: string;
|
|
305
309
|
};
|
|
306
310
|
type ReceiveLinkedinMessageArgs = {
|
|
307
311
|
linkedinChatId: string;
|
package/dist/index.d.ts
CHANGED
|
@@ -176,11 +176,13 @@ interface IMessage extends Document {
|
|
|
176
176
|
linkedin?: {
|
|
177
177
|
subject?: string;
|
|
178
178
|
isInMail?: boolean;
|
|
179
|
+
linkedinApi?: string;
|
|
179
180
|
senderName?: string;
|
|
180
181
|
senderProfileUrl?: string;
|
|
181
182
|
};
|
|
182
183
|
whatsapp?: {
|
|
183
184
|
senderName?: string;
|
|
185
|
+
senderPhone?: string;
|
|
184
186
|
};
|
|
185
187
|
};
|
|
186
188
|
parentMessageId?: string;
|
|
@@ -276,6 +278,7 @@ type SendMessageArgs = {
|
|
|
276
278
|
linkedin?: {
|
|
277
279
|
subject?: string;
|
|
278
280
|
isInMail?: boolean;
|
|
281
|
+
linkedinApi?: 'classic' | 'recruiter' | 'sales_navigator';
|
|
279
282
|
};
|
|
280
283
|
};
|
|
281
284
|
};
|
|
@@ -302,6 +305,7 @@ type ReceiveWhatsappMessageArgs = {
|
|
|
302
305
|
message: string;
|
|
303
306
|
messageId?: string;
|
|
304
307
|
senderName?: string;
|
|
308
|
+
senderPhone?: string;
|
|
305
309
|
};
|
|
306
310
|
type ReceiveLinkedinMessageArgs = {
|
|
307
311
|
linkedinChatId: string;
|
package/dist/index.js
CHANGED
|
@@ -594,32 +594,67 @@ function createMessagesService(models, hooks = {}) {
|
|
|
594
594
|
const linkedinMeta = metadata == null ? void 0 : metadata.linkedin;
|
|
595
595
|
lastLinkedInId = LinkedinConnector == null ? void 0 : LinkedinConnector.connectorId;
|
|
596
596
|
if (LinkedinConnector) {
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
597
|
+
if (linkedinMeta == null ? void 0 : linkedinMeta.isInMail) {
|
|
598
|
+
const missingFields = [];
|
|
599
|
+
if (!linkedinMeta.subject) missingFields.push("subject");
|
|
600
|
+
if (!linkedinMeta.linkedinApi) missingFields.push("linkedinApi");
|
|
601
|
+
if (missingFields.length > 0) {
|
|
602
|
+
failed_source.push({
|
|
603
|
+
source: "linkedin",
|
|
604
|
+
message: `InMail requires the following fields: ${missingFields.join(", ")}`
|
|
605
|
+
});
|
|
606
|
+
} else {
|
|
607
|
+
tasks.push({
|
|
608
|
+
name: "linkedin",
|
|
609
|
+
run: async () => {
|
|
610
|
+
const path = paths.linkedin.startChat(String(LinkedinConnector.connectorId));
|
|
611
|
+
const payload = {
|
|
612
|
+
linkedin_url: LinkedinConnector.contactId,
|
|
613
|
+
text
|
|
614
|
+
};
|
|
615
|
+
if (linkedinMeta.subject) {
|
|
616
|
+
payload.subject = linkedinMeta.subject;
|
|
617
|
+
}
|
|
618
|
+
if (linkedinMeta.linkedinApi) {
|
|
619
|
+
payload.linkedin_api = linkedinMeta.linkedinApi;
|
|
620
|
+
}
|
|
621
|
+
if (linkedinMeta.isInMail) {
|
|
622
|
+
payload.linkedin_inmail = linkedinMeta.isInMail;
|
|
623
|
+
}
|
|
624
|
+
try {
|
|
625
|
+
const res = await getAxios().post(path, payload);
|
|
626
|
+
const data = res.data;
|
|
627
|
+
linkedinChatId = data.chat_data.chat_id;
|
|
628
|
+
return { status: "fulfilled", value: data };
|
|
629
|
+
} catch (error) {
|
|
630
|
+
return { status: "rejected", reason: error };
|
|
631
|
+
}
|
|
632
|
+
}
|
|
633
|
+
});
|
|
621
634
|
}
|
|
622
|
-
}
|
|
635
|
+
} else {
|
|
636
|
+
tasks.push({
|
|
637
|
+
name: "linkedin",
|
|
638
|
+
run: async () => {
|
|
639
|
+
const path = paths.linkedin.startChat(String(LinkedinConnector.connectorId));
|
|
640
|
+
const payload = {
|
|
641
|
+
linkedin_url: LinkedinConnector.contactId,
|
|
642
|
+
text
|
|
643
|
+
};
|
|
644
|
+
if (linkedinMeta == null ? void 0 : linkedinMeta.linkedinApi) {
|
|
645
|
+
payload.linkedin_api = linkedinMeta.linkedinApi;
|
|
646
|
+
}
|
|
647
|
+
try {
|
|
648
|
+
const res = await getAxios().post(path, payload);
|
|
649
|
+
const data = res.data;
|
|
650
|
+
linkedinChatId = data.chat_data.chat_id;
|
|
651
|
+
return { status: "fulfilled", value: data };
|
|
652
|
+
} catch (error) {
|
|
653
|
+
return { status: "rejected", reason: error };
|
|
654
|
+
}
|
|
655
|
+
}
|
|
656
|
+
});
|
|
657
|
+
}
|
|
623
658
|
} else {
|
|
624
659
|
failed_source.push({ source: "linkedin", message: "Missing connector configuration" });
|
|
625
660
|
}
|
|
@@ -793,121 +828,152 @@ function createMessagesService(models, hooks = {}) {
|
|
|
793
828
|
return message;
|
|
794
829
|
},
|
|
795
830
|
/**
|
|
796
|
-
* Receive a new message by whatsappChatId
|
|
831
|
+
* Receive a new message by whatsappChatId — delivers to ALL conversations
|
|
832
|
+
* that share this chatId (across organizations).
|
|
797
833
|
*/
|
|
798
834
|
async receiveWhatsappMessage(args) {
|
|
799
|
-
const { whatsappChatId, message, messageId, senderName } = args;
|
|
800
|
-
const
|
|
801
|
-
if (!
|
|
835
|
+
const { whatsappChatId, message, messageId, senderName, senderPhone } = args;
|
|
836
|
+
const conversations = await Conversation.find({ whatsappChatId }).lean();
|
|
837
|
+
if (!conversations.length) {
|
|
802
838
|
throw new Error("Conversation not found for given whatsappChatId");
|
|
803
839
|
}
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
|
|
811
|
-
|
|
812
|
-
|
|
840
|
+
let lastSavedMessage = null;
|
|
841
|
+
for (const conversation of conversations) {
|
|
842
|
+
if (messageId) {
|
|
843
|
+
const existingMessage = await Message.findOne({
|
|
844
|
+
organizationId: conversation.organizationId,
|
|
845
|
+
conversationId: String(conversation._id),
|
|
846
|
+
externalMessageId: messageId
|
|
847
|
+
}).lean();
|
|
848
|
+
if (existingMessage) {
|
|
849
|
+
console.log(`Duplicate WhatsApp message detected for conversation ${conversation._id}: ${messageId}`);
|
|
850
|
+
lastSavedMessage = existingMessage;
|
|
851
|
+
continue;
|
|
852
|
+
}
|
|
813
853
|
}
|
|
814
|
-
|
|
815
|
-
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
854
|
+
const applicationParticipant = conversation.participants.find(
|
|
855
|
+
(p) => p.entityModel === "Application"
|
|
856
|
+
);
|
|
857
|
+
if (!applicationParticipant) {
|
|
858
|
+
console.log(`Application participant not found in conversation ${conversation._id}, skipping`);
|
|
859
|
+
continue;
|
|
860
|
+
}
|
|
861
|
+
const orgId = conversation.organizationId;
|
|
862
|
+
const senderModel = "Application";
|
|
863
|
+
const senderId = applicationParticipant.entityId;
|
|
864
|
+
const msgDoc = new Message({
|
|
865
|
+
organizationId: orgId,
|
|
866
|
+
conversationId: String(conversation._id),
|
|
867
|
+
senderModel,
|
|
868
|
+
senderId,
|
|
869
|
+
text: message,
|
|
870
|
+
kind: "text",
|
|
871
|
+
source: ["whatsapp"],
|
|
872
|
+
externalMessageId: messageId,
|
|
873
|
+
parentMessageId: void 0,
|
|
874
|
+
rootThreadId: void 0,
|
|
875
|
+
metadata: senderName || senderPhone ? {
|
|
876
|
+
whatsapp: {
|
|
877
|
+
senderName,
|
|
878
|
+
senderPhone
|
|
879
|
+
}
|
|
880
|
+
} : void 0
|
|
881
|
+
});
|
|
882
|
+
try {
|
|
883
|
+
await msgDoc.save();
|
|
884
|
+
} catch (saveError) {
|
|
885
|
+
if ((saveError == null ? void 0 : saveError.code) === 11e3) {
|
|
886
|
+
console.log(`Duplicate key for conversation ${conversation._id}, already saved by concurrent request`);
|
|
887
|
+
continue;
|
|
838
888
|
}
|
|
839
|
-
|
|
840
|
-
});
|
|
841
|
-
await msgDoc.save();
|
|
842
|
-
await Conversation.findByIdAndUpdate(conversation._id, {
|
|
843
|
-
$set: {
|
|
844
|
-
lastMessageAt: msgDoc.createdAt,
|
|
845
|
-
lastMessagePreview: message.substring(0, 100),
|
|
846
|
-
lastMessageSenderId: senderId,
|
|
847
|
-
lastMessageSenderModel: senderModel
|
|
889
|
+
throw saveError;
|
|
848
890
|
}
|
|
849
|
-
|
|
850
|
-
|
|
851
|
-
|
|
891
|
+
await Conversation.findByIdAndUpdate(conversation._id, {
|
|
892
|
+
$set: {
|
|
893
|
+
lastMessageAt: msgDoc.createdAt,
|
|
894
|
+
lastMessagePreview: message.substring(0, 100),
|
|
895
|
+
lastMessageSenderId: senderId,
|
|
896
|
+
lastMessageSenderModel: senderModel
|
|
897
|
+
}
|
|
898
|
+
});
|
|
899
|
+
if (onMessageCreated) onMessageCreated(msgDoc);
|
|
900
|
+
lastSavedMessage = msgDoc;
|
|
901
|
+
}
|
|
902
|
+
return lastSavedMessage;
|
|
852
903
|
},
|
|
853
904
|
/**
|
|
854
|
-
* Receive a new message by linkedinChatId
|
|
905
|
+
* Receive a new message by linkedinChatId — delivers to ALL conversations
|
|
906
|
+
* that share this chatId (across organizations).
|
|
855
907
|
*/
|
|
856
908
|
async receiveLinkedinMessage(args) {
|
|
857
909
|
const { linkedinChatId, message, messageId, senderName, senderProfileUrl } = args;
|
|
858
|
-
const
|
|
859
|
-
if (!
|
|
910
|
+
const conversations = await Conversation.find({ linkedinChatId }).lean();
|
|
911
|
+
if (!conversations.length) {
|
|
860
912
|
throw new Error("Conversation not found for given linkedinChatId");
|
|
861
913
|
}
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
914
|
+
let lastSavedMessage = null;
|
|
915
|
+
for (const conversation of conversations) {
|
|
916
|
+
if (messageId) {
|
|
917
|
+
const existingMessage = await Message.findOne({
|
|
918
|
+
organizationId: conversation.organizationId,
|
|
919
|
+
conversationId: String(conversation._id),
|
|
920
|
+
externalMessageId: messageId
|
|
921
|
+
}).lean();
|
|
922
|
+
if (existingMessage) {
|
|
923
|
+
console.log(`Duplicate LinkedIn message detected for conversation ${conversation._id}: ${messageId}`);
|
|
924
|
+
lastSavedMessage = existingMessage;
|
|
925
|
+
continue;
|
|
926
|
+
}
|
|
871
927
|
}
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
928
|
+
const applicationParticipant = conversation.participants.find(
|
|
929
|
+
(p) => p.entityModel === "Application"
|
|
930
|
+
);
|
|
931
|
+
if (!applicationParticipant) {
|
|
932
|
+
console.log(`Application participant not found in conversation ${conversation._id}, skipping`);
|
|
933
|
+
continue;
|
|
934
|
+
}
|
|
935
|
+
const orgId = conversation.organizationId;
|
|
936
|
+
const senderModel = "Application";
|
|
937
|
+
const senderId = applicationParticipant.entityId;
|
|
938
|
+
const msgDoc = new Message({
|
|
939
|
+
organizationId: orgId,
|
|
940
|
+
conversationId: String(conversation._id),
|
|
941
|
+
senderModel,
|
|
942
|
+
senderId,
|
|
943
|
+
text: message,
|
|
944
|
+
kind: "text",
|
|
945
|
+
source: ["linkedin"],
|
|
946
|
+
externalMessageId: messageId,
|
|
947
|
+
parentMessageId: void 0,
|
|
948
|
+
rootThreadId: void 0,
|
|
949
|
+
metadata: senderName || senderProfileUrl ? {
|
|
950
|
+
linkedin: {
|
|
951
|
+
senderName,
|
|
952
|
+
senderProfileUrl
|
|
953
|
+
}
|
|
954
|
+
} : void 0
|
|
955
|
+
});
|
|
956
|
+
try {
|
|
957
|
+
await msgDoc.save();
|
|
958
|
+
} catch (saveError) {
|
|
959
|
+
if ((saveError == null ? void 0 : saveError.code) === 11e3) {
|
|
960
|
+
console.log(`Duplicate key for conversation ${conversation._id}, already saved by concurrent request`);
|
|
961
|
+
continue;
|
|
897
962
|
}
|
|
898
|
-
|
|
899
|
-
});
|
|
900
|
-
await msgDoc.save();
|
|
901
|
-
await Conversation.findByIdAndUpdate(conversation._id, {
|
|
902
|
-
$set: {
|
|
903
|
-
lastMessageAt: msgDoc.createdAt,
|
|
904
|
-
lastMessagePreview: message.substring(0, 100),
|
|
905
|
-
lastMessageSenderId: senderId,
|
|
906
|
-
lastMessageSenderModel: senderModel
|
|
963
|
+
throw saveError;
|
|
907
964
|
}
|
|
908
|
-
|
|
909
|
-
|
|
910
|
-
|
|
965
|
+
await Conversation.findByIdAndUpdate(conversation._id, {
|
|
966
|
+
$set: {
|
|
967
|
+
lastMessageAt: msgDoc.createdAt,
|
|
968
|
+
lastMessagePreview: message.substring(0, 100),
|
|
969
|
+
lastMessageSenderId: senderId,
|
|
970
|
+
lastMessageSenderModel: senderModel
|
|
971
|
+
}
|
|
972
|
+
});
|
|
973
|
+
if (onMessageCreated) onMessageCreated(msgDoc);
|
|
974
|
+
lastSavedMessage = msgDoc;
|
|
975
|
+
}
|
|
976
|
+
return lastSavedMessage;
|
|
911
977
|
},
|
|
912
978
|
/**
|
|
913
979
|
* Receive a new message by emailChatId with full email metadata
|