Fullcast exports territory coverage assignments using the standard Salesforce AccountTeamMember object. RevOps teams often use Salesforce Flows to automate actions based on this data, such as updating the Account Owner or other fields on the Account record. When Fullcast exports a high volume of data (e.g., during cutovers involving many thousands of records), robust Salesforce automation is crucial. Failing to consider factors like governor limits and potential recursion can lead to processing errors or system performance issues.
Using an Asynchronous Path within a Record-Triggered Flow is the recommended approach for handling these scenarios effectively. This article outlines key considerations and provides an example flow.
Benefits of Using Asynchronous Paths
When handling numerous record updates triggered by systems like Fullcast, using the Asynchronous Path within a Record-Triggered Flow is often the best strategy. Here’s why:
Avoids tight synchronous limits: Asynchronous paths run separately from the initial save transaction triggered by Fullcast. This prevents your automation from hitting strict synchronous governor limits (like CPU time, SOQL queries, or DML statements per transaction), which is essential when complex logic needs to run for many incoming records without causing errors on the initial save.
Provides Scalability Past Daily Scheduled Limits: Salesforce limits the total number of scheduled flow interviews processed per 24 hours (commonly 250,000 or based on user licenses). If your automation strategy involves triggering many Scheduled Paths from Fullcast updates and you hit this ceiling, shifting logic to an Asynchronous Path can help. Asynchronous paths run under different limits and do not count towards this specific scheduled interview limit.
Improves Performance & Responsiveness: By offloading processing, the initial record save initiated by Fullcast completes much faster. This prevents timeouts and allows the overall data synchronization process with Fullcast to proceed more efficiently.
Recursion Risk with Asynchronous Paths
Unlike Scheduled Paths, Asynchronous Paths don't have built-in recursion protection. Recursion occurs if a flow's action (like updating a related record) causes the flow's original trigger conditions to be met again, potentially leading to repeated execution, performance issues, or hitting governor limits.
Control fields (flag) can prevent recursion
Implementing a control mechanism is essential. A common method uses a dedicated 'control' field (e.g., a Checkbox) on the object that triggers the flow. For flows triggered by AccountTeamMember creation, this helps prevent newly created records (potentially created by the flow itself) from re-triggering the same automation.
Create Control Field: Add a Checkbox field to the triggering object (AccountTeamMember in our example). Let's call it Created_by_Automation__c, with a default value of false.
Refine Flow Entry Criteria: Configure the Record-Triggered Flow to only start if this control field is false. Example condition: Created_by_Automation__c Equals GlobalConstant.False. This check acts as a gatekeeper.
Set Flag When Flow Creates Records: If your flow logic involves creating new records of the same object type that triggers the flow (e.g., creating new AccountTeamMember records within a flow triggered by AccountTeamMember), ensure you set the control field to true on these new records before the 'Create Records' element. This prevents the newly created records from meeting the entry criteria and causing recursion.
Note:
If your flow triggered on updates and needed to run multiple times on the same record under different conditions, you would also need a separate process to reset this flag to false when appropriate. However, for a flow triggering only on creation, primarily setting the flag on flow-created records is the key recursion prevention step.
Example Flow: Updating Accounts After Fullcast Team Updates
Scenario: Fullcast creates new AccountTeamMember records. We want a flow to update the parent account's owner and potentially other role-specific fields (like SDR or sales manager lookup fields) based on the new team member's role. If the new team member is an 'Account Executive', we also want to completely replace the existing Account Team with one based on the prior team's structure. Here is a description of the flow. See the images at the bottom of the article for a visual
Flow Configuration
Trigger:
Object: AccountTeamMember
Trigger Event: A record is Created.
Entry Criteria: Define conditions to ensure the flow only runs for specific Fullcast-created records. For example:
fcio1__External_ID__c Is Null GlobalConstant.False (Identifies Fullcast record)
AND Created_by_Automation__c Equals GlobalConstant.False (Control flag check)
AND (TeamMemberRole Equals 'Account Executive' OR TeamMemberRole Equals 'SDR' OR TeamMemberRole Equals 'Sales Manager')
Optimize For: Actions and Related Records (The logic will run asynchronously).
Asynchronous path logic: Place all subsequent elements on the path labeled "Run Asynchronously".
Update related account (initial update):
Use an Update Records element.
Record(s) to update: Specify updating the related Account record (Find records related to the Account Team Member record that triggered the flow > Account ID).
Set field values: Define how to set Account fields. For example:
OwnerId = {!$Record.UserId} (Set Account Owner to the User on the triggering Account Team Member record).
Use formulas or conditions based on {!$Record.TeamMemberRole} to set fields like SDR__c, Sales_Manager__c, etc.
Decision by role:
Use a Decision element to check the {!$Record.TeamMemberRole} from the triggering record.
Create outcomes for 'Account Executive', 'SDR', 'Sales Manager', etc.
Role-specific account updates (SDR, sales manager paths):
For outcomes like 'SDR' or 'Sales Manager', you might add specific Update Records elements (updating the related Account) if further role-specific fields need setting beyond the initial update. End these paths afterward.
'Account Executive' Path - team recreation logic:
Get current team: Use Get Records to retrieve all existing AccountTeamMember records where AccountId equals {!$Record.AccountId}. Store all records automatically (e.g., in {!Get_Current_Team}).
Loop old team data: Add a Loop element. Iterate through the collection retrieved by Get Current Team ({!Get_Current_Team}). The data remains in flow memory even though the records were deleted.
Define new member (inside loop): Use an Assignment element (Define_New_Member). Create a record variable (varSingleNewMember of type AccountTeamMember). Assign values:
AccountId = {!$Record.AccountId}
UserId = {!LoopThroughOldTeamMembers.UserId} (Or other logic)
TeamMemberRole = {!LoopThroughOldTeamMembers.TeamMemberRole}
Copy AccountAccessLevel, OpportunityAccessLevel, CaseAccessLevel.
Created_by_Automation__c = GlobalConstant.True (Set the flag on the new record definition).
Add to collection (inside loop): Use another Assignment (Add_Member_to_Collection). Add {!varSingleNewMember} to a record collection variable (varNewCollection).
Create new team (after loop): Add a Create Records element. Use the collection {!varNewCollection} to create the new team members.
Conclusion
By leveraging asynchronous paths in record-triggered flows and implementing control fields like Created_by_Automation__c, Fullcast users can effectively automate actions based on account team member updates. Carefully structure your flow logic, ensuring you include necessary steps like explicitly deleting records when replacing related data (such as Account Teams), to achieve reliable and scalable automation within Salesforce governor limits. Always test thoroughly in a sandbox.
Images
Entire flow

This example flow follows the recommendations made above.
Flow start details - note inclusion of asynchronous path

The option to run asynchronously is key for avoiding various limits.