Portal Community

Example 1: Convert an Inbound Lead to Account, Contact, and Opportunity

Scenario: A web form submission triggers a workflow. The lead is created in Salesforce, then immediately converted — creating a linked Account, Contact, and Opportunity in a single lead/convert call. The resulting IDs are stored as variables for downstream steps.

Step 1 — Create the lead
{
  "resource": "lead",
  "operation": "create",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "FirstName": "{{ trigger.body.first_name }}",
  "LastName": "{{ trigger.body.last_name }}",
  "Company": "{{ trigger.body.company }}",
  "Email": "{{ trigger.body.email }}",
  "Phone": "{{ trigger.body.phone }}",
  "LeadSource": "Web",
  "Status": "Open - Not Contacted",
  "Rating": "Hot",
  "Description": "Inbound web form submission — {{ trigger.body.message }}"
}
Step 2 — Convert the lead (uses the ID from step 1)
{
  "resource": "lead",
  "operation": "convert",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "LeadId": "{{ nodes.createLead.output.id }}",
  "OpportunityName": "{{ trigger.body.company }} — Initial Opportunity",
  "OverwriteLeadSource": true
}
Expected outcome: A new Account, Contact, and Opportunity are created and linked. The conversion output provides accountId, contactId, and opportunityId. Use a Variable Assignment node to store these three IDs and pass them to any subsequent steps — for example, sending a welcome email via the Gmail node or creating an onboarding task in a project management system.

Example 2: Query All Open Opportunities Closing This Month Using SOQL

Scenario: A scheduled workflow runs on the first of each month and fetches all open opportunities with a close date within the current calendar month. Results are looped and emailed to the sales manager as a pipeline report.

{
  "resource": "soql",
  "operation": "executeWithPagination",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "Query": "SELECT Id, Name, Amount, StageName, CloseDate, Account.Name, Owner.Name FROM Opportunity WHERE IsClosed = false AND CloseDate = THIS_MONTH ORDER BY Amount DESC",
  "PageSize": 2000
}
Expected outcome: The executeWithPagination operation automatically fetches all pages and returns a single records array containing every open opportunity closing this month. The totalCount field gives the pipeline deal count. A Loop node iterates the array to build a summary table, which a downstream Email node sends to the sales team.
SOQL date literals: Salesforce supports date literals like THIS_MONTH, NEXT_QUARTER, LAST_N_DAYS:30, and THIS_FISCAL_YEAR in SOQL WHERE clauses — no date formatting or calculation needed in the workflow.

Example 3: Bulk Create 500 Contacts from a CSV Import

Scenario: A marketing campaign delivers a CSV file of 500 new contacts to an SFTP location. A workflow reads the file, parses it with a Code Execute node into a JSON array, then bulk-inserts all contacts into Salesforce in a single operation.

{
  "resource": "bulk",
  "operation": "create",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "Object": "Contact",
  "Records": "{{ nodes.parseCsv.output.contacts }}"
}

The parseCsv node (Code Execute) produces a JSON array in this shape:

[
  {
    "FirstName": "Sarah",
    "LastName": "Johnson",
    "Email": "sarah.johnson@techcorp.com",
    "Phone": "+1-415-555-0192",
    "Title": "VP Engineering",
    "AccountId": "0015e000005XYZABC",
    "MailingCity": "San Francisco",
    "MailingState": "CA",
    "MailingCountry": "US"
  },
  {
    "FirstName": "Marcus",
    "LastName": "Williams",
    "Email": "m.williams@globalinc.com",
    "Phone": "+44-20-7946-0958",
    "Title": "Procurement Manager",
    "AccountId": "0015e000005DEFGHI",
    "MailingCity": "London",
    "MailingState": "",
    "MailingCountry": "UK"
  }
  // ... 498 more records
]
Expected outcome: All 500 contacts are submitted to the Salesforce Bulk API in one job. The output provides successCount, failureCount, and a detailed errors array for any failed records. A downstream If Condition node checks failureCount > 0 and routes failures to an alert email with the error details.
Avoiding duplicates: Use bulk/upsert with ExternalIdField: "Email" instead of bulk/create when re-importing data. This ensures contacts that already exist in Salesforce are updated rather than duplicated.

Example 4: Automatically Create a Salesforce Case from a Support Webhook

Scenario: A customer support platform sends a webhook when a new support ticket is opened. The workflow creates a corresponding Salesforce Case linked to the matching Account and Contact, enabling the support team to track issues from within Salesforce.

{
  "resource": "case",
  "operation": "create",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "Subject": "{{ trigger.body.ticket_subject }}",
  "Description": "Ticket #{{ trigger.body.ticket_id }} opened via {{ trigger.body.channel }}.\n\n{{ trigger.body.message_body }}",
  "Status": "New",
  "Priority": "{{ trigger.body.priority }}",
  "Type": "Problem",
  "AccountId": "{{ vars.matched_account_id }}",
  "ContactId": "{{ vars.matched_contact_id }}"
}
Expected outcome: A new Salesforce Case is created and linked to the correct Account and Contact. The created case ID ({{ nodes.createCase.output.id }}) is stored and sent back to the support platform as a reference, creating a bidirectional link between the external ticket and the Salesforce Case. A Slack notification is sent to the #support channel with the case ID and direct link.
Looking up Account and Contact first: Before this step, use a soql/execute node to find the Account and Contact IDs by email: SELECT Id FROM Contact WHERE Email = '{{ trigger.body.customer_email }}' LIMIT 1. Store the result in vars.matched_contact_id and retrieve the associated AccountId from the same record.

Example 5: Close a Won Opportunity and Update the Related Account Revenue

Scenario: A sales rep marks a deal as won in an external deal desk application. A webhook triggers a workflow that closes the Salesforce Opportunity as "Closed Won" and updates the parent Account's AnnualRevenue field to reflect the new contract value.

Step 1 — Close the opportunity as won
{
  "resource": "opportunity",
  "operation": "close",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "OpportunityId": "{{ trigger.body.opportunity_id }}",
  "StageName": "Closed Won",
  "CloseDate": "{{ trigger.body.close_date }}"
}
Step 2 — Fetch the opportunity to get the linked AccountId and Amount
{
  "resource": "opportunity",
  "operation": "get",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "OpportunityId": "{{ trigger.body.opportunity_id }}",
  "Fields": "AccountId,Amount,Name"
}
Step 3 — Update the Account's AnnualRevenue
{
  "resource": "account",
  "operation": "update",
  "InstanceUrl": "{{ env.SF_INSTANCE_URL }}",
  "AccessToken": "{{ env.SF_ACCESS_TOKEN }}",
  "AccountId": "{{ nodes.getOpportunity.output.AccountId }}",
  "AnnualRevenue": "{{ vars.updated_annual_revenue }}",
  "Description": "Revenue updated by BizFirstAI workflow on deal close: {{ nodes.getOpportunity.output.Name }}"
}
Expected outcome: The opportunity stage is set to "Closed Won" with today's (or the provided) close date. The parent Account's AnnualRevenue field is updated to reflect the new contract contribution. A Variable Assignment node calculates vars.updated_annual_revenue by adding the opportunity amount to the account's previous revenue value (fetched via a prior account/get step). A congratulations message is posted to the sales team's Slack channel via the Slack node, including the deal name and value.