Vote for official supportIdea: support standard id/ids flow variables

"How do I submit multiple records into my process?"

This sounds like an obvious job for Flow and a List Custom Button, right? We open the list view, tick a few checkboxes, click the list button… but quickly find the Selected Record IDs are nowhere to be found in Flow.

There are a few workarounds to inject the checked rows:

  • Use code or a package to run the flow as a batch process
  • Add a custom field and use mass edits to invoke process builder
  • Create a VF page with apex:interview to inject the selected records
  • Use GETRECORDIDS in a JavaScript custom button (alarm bells ringing…)

How to pass Record IDs to flow from buttons

Here's the thing - the id or ids are accessible in flow already - the trick is to launch the Flow using its URL in the button content and create a variable with a special name:

Then, configure the 'Nudge Owner' flow so the posted IDs are received:

  1. Create a new Collection Variable resource
  2. Enter the Unique Name called ids
  3. Set the Type to Input Only

When configured correctly, Salesforce automatically populates the collection variable with the IDs of the selected checkboxes. Now we can loop over the collection variable and perform business logic.


  • This parameter isn't documented anywhere.
  • The name of the ids collection variable is case sensitive.
  • Remember to "close the loop" otherwise only the first ID is handled by Flow.

The same technique works on Detail Page Buttons: if an id variable exists in the flow, it is automatically populated with the current Record ID context. If you've seen this before, it's because it's the same way the standard id/ids parameters work in standard controllers:

Mass flow actions can be bulkified too, they need not be limited by iterations of the loop element. Plugins using the @InvocableMethod annotation do support collection variables - the ids list can be passed straight in.

Why start flows from URL buttons

Unlike using a Visualforce Page to launch flow, the URL button gives you access to the id/ids parameters. Then the parameters behave like an interface contract, and we can attach flows to objects using the Metadata API. Further:

  • Avoiding the VF page also avoids any need to modify Profiles.
  • Using a URL button prevents the Flow from becoming a dependency itself.
  • Less documentation needed to explain inputs, because everyone knows what an ID is.

True, distributing flows using Visualforce Pages offers more granular access control since the entry point is restricted by its associated page - this is applicable in sites and communities or portals.

Vote for official supportIdea: support standard id/ids flow variables

Renato Oliveira  

Since it is not documented then we have no guarantee that this won't real in a platform update. That's a more or less good reason in my opinion.

Can you provide detail on your "Assign Next" node? I believe I have "closed my loop" but do have my flow operating on only 1 of the "ids" after looping through them. Thank you!

Hi Bruce, the node "Assign" is a do-nothing that sets the id variable to empty string. If that doesn't work, try eliminating it altogether and drawing the output from the email straight back to the loop element (it will display as a connector with an arrow on both ends)

Interesting to learn about the ids collection variable!
I will add that for a single record from a record detail page, using "recordId" is the documented and supported way to get the record ID

Thanks, found "recordId" in the official documentation:

I attempted to do this but the flow got hung up any time I clicked the button after selecting records.

Hi Natalya, try setting the behaviour to "Display in existing window without sidebar or header"

Natalya Murphy  

Thanks for figuring that out. I've confirmed it works when the display is set to Display in existing window without sidebar or header.

WOW that works even in lightning - THANK YOU VERY MUCH !

You are most welcome

Alexander Twomey-McLeod  

Why when I do this does it pass ALL the records for that object and not the selected ones? Cannot figure it out

Simon Kinder  

seems to pass every single items id rather than checked ones? did this get changed

Lee Anne Galasso  

This is just not working for my custom object. I'm getting: "Unable to set value for variable 'ids'. Flow encountered an error when processing and converting between data types. Please check the flow and ensure all data types are matched correctly." when I start the flow from the button.

Kylie Harrison  

This seemed like a great solution for me, but I have tried to get this to work in 2 separate screens and it does not work for custom objects, unfortunately. When I run it on custom objects and direct to a flow all I get is white screen and nothing in the debug log. Just in case I tried a 2nd built flow to take the ids and same story.

Lee Anne I had this error as well. I changed the ids from an sObject collection variable to just a Collection Variable, and it worked great. I wish this hack worked with sobjects as that would save a ton of steps in certain use cases. Also, I'm using it on a custom object as well.

Lee Anne Galasso  

Banzai, thanks for the tip, but I have no idea how to use a non-record Collection variable. I'm assuming you created a text collection variable. But then, how did you use that collection variable to find the records you were looking for?

Tyson Kirksey  

This is exactly what I need, but I can't get it to work with Opportunities in Lightning. I get the same error as Lee Anne. Any ideas?

Still works for me! You are genius for this!!

Keerthana Pachalla  

This works great in lightning but cannot get it to work in communities. Any ideas?!

Hi, I am receiving the same message as above "error when processing and converting between data types".
If this can work on custom objects, as Banzai Admin, reports, then how should the ids variable be set up as a Collection Variable, instead of an sObject collection variable?

Hi J, the collection variable called "ids" should be of type ID or Text. Can you try creating a Screen Flow and URL button like this? It works OK in the new flow builder too.

Yaakov Singer  


So, first of all, it's working … in general. I needed to activate the latest version. Oops! The ids are being collected. That's the key step.

Thank you!

I'm using Lightning flow to create multiple accounts, all these records are stored in a 'List' aura attribute. In Flow I have created a Account Collection variable to store all accounts. But I am not able to send the list from component to flow.

var inputVariables = [{
name : 'accList,
type : 'SObject',
value : cmp.get('v.accountList')

flow.startFlow('Create_Account', inputVariables);
Note: In list we have more than 20 records.

Hi this is great, but is there any way to make this work as a modal in Lightning? I'm using a screen flow and the screen elements stretch across the entire screen, plus there's no way to return to the original list view.

I've tried using a VF page instead of the URL but this doesn't work with screen Flow because it wants to run in Classic runtime instead of Lightning runtime.

I have the same issue, once the flow is finished on lightning , its just opens an infinite loop on new tab .

Found an answer here:

"You will need to manually set your flow's finish location or it will loop back to the beginning of the flow when done. You can set the flow return url via retUrl in your custom button."

I have tried the same solution for sfxd, put the custom button that uses the url described above, and I use the retURL but it breaks the url somehow. The solution described above (SFXD) article doesn't work for this solution.

make sure your button's display behavior is - without sidebar or header , otherwise the redirect doesn't work

What wound up working for me was {!URLFOR('/flow/Delete_Selected_CUSTOMOBJ?retURL=lightning/o/CUSTOMOBJ__c/list')} - this brings you back to the list view after the flow completes.

Maureen Caballero  

So, I am having trouble getting the custom button to show up. I clicked on buttons and links under contact/object manager, then selected new button or link. Named it, chose List Button, display checkboxes,display in existing window without sidebar or header and selected URL for content source. Finally, I entered {!URLFOR('/flow/Attendance')}. Then I selected the Attendance button in the default search layout. No button shows up (it's supposed to be on the Contact page list view, correct?)

Maureen Caballero  

Also, when setting up the actual flow, it's not clear: do we need to first have a "GetRecords" element prior to the loop or does the loop actually collect the selected ids? In the Get Records filter I selected = {id} and chose multiple records. Then I used both the {ids} collection variable and {id} variable in the loop. Does that sound right?

Justin Feldman  

@Maureen, responding to your 2 posts separately:

1. I struggled with the same thing. In Lightning Experience, you need to add the Custom Button to both the LEX Search Layouts section (Default Search Layout) AND the "Salesforce Classic Search Layouts". Then refresh your page and ensure that you're looking at any list view EXCEPT the "Recently Viewed" list view. Give that a shot.

2. Your loop sounds correct. You don't have to place the Get Record component at the beginning. I started my loop and then placed the Get Record component inside the loop. HOWEVER, this isn't best practice, since it will probably fail if you select > 50 records (due to flow query limits). I think that best practice would probably be to use the Get Record element to get ALL records (no filtering) at the beginning, and then loop through all the records and use an assignment to pull out records that meet your criteria and add each to a NEW collection. You would then loop through the NEW collection and perform your logic there (being careful not to do any DML operations inside the loop either). That way you get the benefit of looping through a collection of records without performing SOQL queries inside the loop.

Hope that all helps.

Maureen Caballero  

@Justin - So excited that I had to reply right away after doing step 1 - After 8 hours of trying to get the custom button to show up on the list view, your suggestion did it! Now on to try the actual flow...

Hi ,

I just want to know if there is a way to open all the records we have selected in the list view, in separate tab, in the same window.
I am trying to achieve it in Lightning service console for case object.


is this still working in Lightning? We created the flow and it´s working perfectly in classic but in Lightning it doesn´t get any ids from the list view. Did something change here?

Brian Romanowski  

I'm seeing the same issue. We already have this in use so I need to find a workaround quick!

Actually we have the same problem, on the scratch org everything works fine, but on Test environment only classic is ok.

Here is the request for SFDC to support standardized id/ids flow vars:

I'm new to Salesforce and I'm trying to get this to work for a mass delete of QuoteLineItems, without having to learn how to create a VF page. I understand that as the QuoteLineItems are a related list on the Quote object it functions a little differently.

I've given the above a shot and no joy. Any ideas?

This works OK
- new autolaunched flow
- add list variable "ids" of type text
- loop element then delete records using loop variable
- create list button on Quote Line Items then add to related list layout

Button and flow in an unmanaged package here

Hello. We had utilized this method of collecting ids for a flow, but with the Winter '21 preview the functionality has stopped working (no ids are being passed into the flow). Has anyone else encountered this issue? Is there a workaround for it, short of creating a vf page and controller?

Here is the request for SFDC to support standardized id/ids flow vars:

This works great! Was able to pass the ids in just few minutes. Hope this will still work after Winer '21 update. However, why would SF close it?

Same problem for me, it's not working anymore with Winter21. I replaced this feature by the flow screen component datatableV2 which also allows to filter the items to show (contrary to the list view). Perfect workaround for my need.

Issue with Winter 21 seems fixed now

I have tried creating the "ids" variable in a button-launched flow from URL button on a related list. What are the steps in the flow to assign the incoming ids from a multi-select list of records to the variable? I set it as text, collection type and used no Assignment step. Didn't seem to work. Debugging the flow with a single record variable input seemed to work. No idea why this isn't working.

Ash SanFilippo  

I'm having this same issue. I have the "ids" variable set as text with multiples allowed. But I'm struggling using that to get the actual records. Did you figure this out?

Trying to add custom buttons to a related list to allow for quick attendance record status updates. Followed the sequence, but being directed to an error page each time:
"Unfortunately, there was a problem. Please try again. If the problem continues, get in touch with your administrator with the error ID shown here and any other related details. Error ID: 260458417-40180 (674300471)
This page has an error. You might just need to refresh it. [Error in $A.getCallback() [[object Object]]]"

I have a Record (Single) Variable named "id" that is data type: Record and is available for input, a Record Collection Variable named "ids" that is data type: Record and is available for input.

My flow starts with a Loop through the "ids" collection variable, assigns each record Status = Present then assigns the single record to a new Record Collection Variable to be called by the final action - Update Records.

How can I figure out where the hang up is?

Thank you so much for your help.

A complete life saver, thank you so much for the tip!
A hint to anybody, who did everything and it still doesn't work: you have to set the show multi-checkboxes in the list button!

We want to use this to send emails, how do you bulkify to avoid loop limit? How is that done, we need to send more than 12 emails at a time.

Can you try converting the ids to records using Get Records, then save all the records in one step - or have a separate record-triggered flow with an email alert step. Hope this helps

Sounds like a plan, Thanks
How do I update each record without having a GET (to pull in each record from the collection variable) in the loop?

Don't update each record. Assemble a records collection (from the ids) using a loop. Then, save all the records in one step. Here is a working example without having a GET step, best regards

Interesting, do you mean the flow really needs another assignment component to collect all the looped assignments?