feat: Salesforce when create contacts under an account if creating leads is chosen [CAL-4713] (#17630)

This commit is contained in:
Joe Au-Yeung authored and GitHub committed 2024-11-14 10:29:21 -05:00
1 parent ff2754f663
commit 3589767099
2 files changed
+134 -52

No files matched your search

@@ -93,6 +93,20 @@ const EventTypeAppCard: EventTypeAppCardComponent = function EventTypeAppCard({
value: "",
});
// Used when creating events under leads or contacts under account
const CreateContactUnderAccount = () => {
return (
<Switch
label={t("salesforce_create_new_contact_under_account")}
labelOnLeading
checked={createNewContactUnderAccount}
onCheckedChange={(checked) => {
setAppData("createNewContactUnderAccount", checked);
}}
/>
);
};
return (
<AppCard
returnTo={`${WEBAPP_URL}${pathname}?tabName=apps`}
@@ -142,19 +156,15 @@ const EventTypeAppCard: EventTypeAppCardComponent = function EventTypeAppCard({
setAppData("createEventOnLeadCheckForContact", checked);
}}
/>
<div className="mt-4">
<CreateContactUnderAccount />
</div>
</div>
) : null}
{createEventOnSelectedOption.value === SalesforceRecordEnum.ACCOUNT ? (
<>
<div className="mb-4">
<Switch
label={t("salesforce_create_new_contact_under_account")}
labelOnLeading
checked={createNewContactUnderAccount}
onCheckedChange={(checked) => {
setAppData("createNewContactUnderAccount", checked);
}}
/>
<CreateContactUnderAccount />
</div>
<div>
<Switch
+116 -44
View File
@@ -42,6 +42,8 @@ type ContactRecord = {
[key: string]: any;
};
type Attendee = { email: string; name: string };
const salesforceTokenSchema = z.object({
id: z.string(),
issued_at: z.string(),
@@ -398,35 +400,56 @@ export default class SalesforceCRMService implements CRM {
: [];
}
async createContacts(contactsToCreate: { email: string; name: string }[], organizerEmail?: string) {
async createContacts(contactsToCreate: Attendee[], organizerEmail?: string) {
const conn = await this.conn;
const appOptions = this.getAppOptions();
const createEventOn = appOptions.createEventOn ?? SalesforceRecordEnum.CONTACT;
// See if the organizer exists in the CRM
const organizerId = organizerEmail ? await this.getSalesforceUserIdFromEmail(organizerEmail) : undefined;
const createdContacts: { id: string; email: string }[] = [];
if (createEventOn === SalesforceRecordEnum.CONTACT || createEventOn === SalesforceRecordEnum.LEAD) {
// See if the organizer exists in the CRM
if (createEventOn === SalesforceRecordEnum.CONTACT) {
await Promise.all(
contactsToCreate.map(async (attendee) => {
return await conn
.sobject(createEventOn)
.create(
this.generateCreateRecordBody({
attendee,
recordType: createEventOn,
organizerId,
})
)
.then((result) => {
if (result.success) {
createdContacts.push({ id: result.id, email: attendee.email });
}
});
return await this.createAttendeeRecord({
attendee,
recordType: SalesforceRecordEnum.CONTACT,
organizerId,
}).then((result) => {
createdContacts.push(...result);
});
})
);
}
if (createEventOn === SalesforceRecordEnum.LEAD) {
// Base this off of the first contact
const attendee = contactsToCreate[0];
if (appOptions.createNewContactUnderAccount) {
// Check for an account
const accountId = await this.getAccountIdBasedOnEmailDomainOfContacts(attendee.email);
if (accountId) {
const createdAccountContacts = await this.createNewContactUnderAnAccount({
attendee,
accountId,
organizerId,
});
if (createdContacts.length > 0) {
createdContacts.push(...createdAccountContacts);
}
}
}
await this.createAttendeeRecord({ attendee, recordType: SalesforceRecordEnum.LEAD, organizerId }).then(
(result) => {
createdContacts.push(...result);
}
);
}
if (createEventOn === SalesforceRecordEnum.ACCOUNT) {
if (!appOptions.createNewContactUnderAccount && !appOptions.createLeadIfAccountNull) {
this.setDoNotCreateEvent(true);
@@ -441,34 +464,16 @@ export default class SalesforceCRMService implements CRM {
let contactCreated = false;
if (accountId && appOptions.createNewContactUnderAccount) {
// First see if the contact already exists and connect it to the account
const userQuery = await conn.query(`SELECT Id, Email FROM Contact WHERE Email = '${attendee.email}'`);
if (userQuery.records.length) {
const contact = userQuery.records[0] as { Id: string; Email: string };
await conn.sobject(SalesforceRecordEnum.CONTACT).update({
// The first argument is the WHERE clause
Id: contact.Id,
AccountId: accountId,
});
return [{ id: contact.Id, email: contact.Email }];
}
const createdAccountContacts = await this.createNewContactUnderAnAccount({
attendee,
accountId,
organizerId,
});
await conn
.sobject(SalesforceRecordEnum.CONTACT)
.create({
...this.generateCreateRecordBody({
attendee,
recordType: SalesforceRecordEnum.CONTACT,
organizerId,
}),
AccountId: accountId,
})
.then((result) => {
if (result.success) {
createdContacts.push({ id: result.id, email: attendee.email });
contactCreated = true;
}
});
if (createdContacts.length > 0) {
createdContacts.push(...createdAccountContacts);
contactCreated = true;
}
}
if (!accountId && appOptions.createLeadIfAccountNull && !contactCreated) {
@@ -629,6 +634,42 @@ export default class SalesforceCRMService implements CRM {
return dominantAccountId;
}
private async createAttendeeRecord({
attendee,
recordType,
organizerId,
accountId,
}: {
attendee: Attendee;
recordType: SalesforceRecordEnum;
organizerId?: string;
accountId?: string;
}) {
const conn = await this.conn;
return await conn
.sobject(recordType)
.create({
...this.generateCreateRecordBody({
attendee,
recordType: recordType,
organizerId,
}),
AccountId: accountId,
})
.then((result) => {
if (result.success) {
return [{ id: result.id, email: attendee.email }];
} else {
return [];
}
})
.catch((error) => {
this.log.error(`Error creating Salesforce contact for ${attendee.email} with error ${error}`);
return [];
});
}
private generateCreateRecordBody({
attendee,
recordType,
@@ -864,6 +905,37 @@ export default class SalesforceCRMService implements CRM {
return query.records[0] as Record<string, any>;
}
private async createNewContactUnderAnAccount({
attendee,
accountId,
organizerId,
}: {
attendee: Attendee;
accountId: string;
organizerId?: string;
}) {
const conn = await this.conn;
// First see if the contact already exists and connect it to the account
const userQuery = await conn.query(`SELECT Id, Email FROM Contact WHERE Email = '${attendee.email}'`);
if (userQuery.records.length) {
const contact = userQuery.records[0] as { Id: string; Email: string };
await conn.sobject(SalesforceRecordEnum.CONTACT).update({
// The first argument is the WHERE clause
Id: contact.Id,
AccountId: accountId,
});
return [{ id: contact.Id, email: contact.Email }];
}
return await this.createAttendeeRecord({
attendee,
recordType: SalesforceRecordEnum.CONTACT,
accountId,
organizerId,
});
}
async findUserEmailFromLookupField(
attendeeEmail: string,
fieldName: string,