Andy in the Cloud

From BBC Basic to Force.com and beyond…

More power to your Flows in Summer’14

32 Comments

Since an earlier blog post describing how to hookup a Flow to a Custom Button, I have been promoting this #clicksnotcode platform feature further at my local DUG and recently the Salesforce1 World Tour London and internally within FinancialForce, the response has been great.

I have also been working on some new use cases showing the use of Flow from Workflow which is capability in pilot for Spring’14. Then before i knew it I had i had found even more new Flow features in my hands delivered via the upcoming Summer’14 release! You can read all about these features in the excellent Visual Workflow Implementation Guide. This blog provides step by step guide as to how I’ve explored these new features and a summary of their current and general availability. Note: The Flow Trigger functionality looks to remain in Pilot beyond Summer’14.

Flow SObject Collections Summer’14 (GA)

NewElements

Lets take a look at two new Resource types in Flow and how they work in conjunction with four new Data elements, known as Fast Create, Fast Read, Fast Update and Fast Delete. With these new elements you can drag them onto the Flow canvas as with the previous ones. The difference is these allow you to basically manage multiple records at once, or in bulk to use Apex term.

NewVariables

The Fast prefix comes from a reflection on what you would have to have done in the past to manipulate several records of the same object. The previous alternative was to create your own loop around the existing Create element creating a single record at time. Which in general is much slower and gives greater rise to hitting platform governors around the number of database operations that can be performed in a single Flow execution. Flow is grow up for greater volumes!

EnterAmountTo illustrate these new features i decide to implement in Flow something i have previously written using Apex code. The following use case is to Apply a user entered discount to selected Quote Line Items from the Related list. The flow will prompt the user for the Discount amount and they apply it, before returning the user back to the Quote detail page.

ApplyDiscount

Here is the high level steps i took to achieve this.

  1. Created a Flow that exposes an Input only variable of type SObject Collection and used by the new  Loop and Fast Update elements to perform the calculations and update the rows passed in.
  2. Created a Visualforce page (no Apex required) that uses the standard platform Selected field to pass in the users selected records (from a List View or Related List). This was a little more Visualforce than i wanted personally, but is still a pretty good template for other use cases with minimal changes required.
  3. Created a List View Custom Button and associated it with the above Visualforce page.
  4. Edited the Quote layout to add the above button the Quote Line Items related list

 

Lets take a look at the Flow I created and then I’ll go into some more detail on the Visualforce page needed to call it. First things first is to create an SObject Collection variable of the appropriate object type, in this case QuoteLineItem.

SObjectCollection

Keep a note of the Unique Name used, it will be important when we create the Visualforce page to call this flow. The next step is to loop over the SObject (or QuoteLineItem) records and apply the discount. The new Loop element is super easy to use, it has two arrows, one for each iteration and another arrow to point to the next step once all records in the collection have been processed.

ApplyDiscountFlow

The following screenshots show the elements in more detail. The Loop element uses new SObject Variable QuoteLineItem, for each record, which allows you to operate at the field level using the existing Assignment element. I also used the existing Formula functionality in Flow to perform the discount calculation. After this i added the record to a another SObject Collection variable that i would later pass to the Fast Update method.

The Visualforce page that runs the Flow looks similar to the one i used in the previous blog to invoke a Flow from the Detail Page Custom Button. The difference is passes in multiple record from those selected by the user via the Selected binding. There is some magic above the flow:interview element that ensures the fields used by the Flow are queried by the platform, otherwise an error occurs when the Assignment steps are executed stating the UnitPrice field has not been queried (I’m open to better ways of resolving this!).

<apex:page standardController="QuoteLineItem" recordSetVar="Quotes">
    <apex:repeat value="{!Selected}" var="SelectedRow" rendered="false">
        {!SelectedRow.QuoteId}{!SelectedRow.UnitPrice}
    </apex:repeat>
    <apex:variable var="QuoteId" value="{!Selected[0].QuoteId}"/>
    <flow:interview name="ApplyDiscount" finishLocation="/{!QuoteId}">
        <apex:param name="SelectedQuoteLines" value="{!Selected}"/>
    </flow:interview>
</apex:page>

Flow Triggers via Spring’14 (Pilot)

CreateElementThe use case I chose here was one i found on IdeasExchange, it related to someone who wanted to use Workflow to create a new child record when a parent record was inserted. In this demo i create a new Task child record whenever an Account is created, this could be for example, to ensure a follow up is made on the Account. The Flow i created was insanely simple, just one Flow variable (set to Input Only) and a Create element!

RecordCreate

Once this is created in my pilot org i found a new Workflow Action, called Flow Trigger. This Workflow action allowed me to pick the Flow and define any parameters i wanted to pass in. In this case the WhatId parameter which would later be used by the Flow when populating the Task fields to associate the task with the Account being created. Finally (not shown) i linked this new Workflow Action with a Workflow Rule to try it out.

FlowTriggers
FlowTriggerEdit

Any that was it! I created a new Account and sure enough my new Task appeared, no Apex code in sight!

TaskChild

Some thoughts and observations…

  • No UI Flows. Flow’s used in this context cannot use any Screen elements, and are thus known sometimes as “Headless” flows. The platform will automatically validate for this and prevent you assigning a UI Flow to a Flow Trigger.
  • Bulkification of Flow Triggers or not? Normally when doing things at a record level Apex developers have it drummed into them to think about bulk or multiple record situations (for example Data Loader use cases) not just a single record at a time. However you will notice this was not the case above? I did expect the new SObject Collection to take a role here but not so. What Salesforce attempts to do is internally bulk insert Tasks for you by running your Flow in parallel and synchronising the executions at the time they all need to insert a record to ensure it’s done optimally. This is cleverly transparent from the Flow designer and i think intentionally so, as it is quite an advanced topic for the target user of Flow. However i do wonder how well this will stand up to more complex Flow’s. No doubt why Salesforce is being so careful over how long this remains in Pilot.

When are these features available (Safe Harbour)?

FlowRoadmap

32 thoughts on “More power to your Flows in Summer’14

  1. Great stuff! I too was thinking about doing this for our DUG here in Dallas!

  2. Flows from Triggers: Spring ’16?

  3. Pingback: Cloudlife Podcast #16 6th June 2014 | Desynit

  4. Excellent post, Andy – lots of great detail for use case and setup.

  5. Hi
    Thanks for sharing this.
    My name is Ashwin, I am salesforce developer
    I tried creating sample flow to -create task when Account is inserted, but i couldn’t find the “Flow trigger” option.Can you help me where to find “flow trigger”.

    • This is only available once Salesforce enable it as it is currently in Pilot only. You can ask to be part of the Pilot by raising a Support Case.

  6. A truly awesome post. Thank you so much for educating the rest of us

  7. Nice post. I have a question: did you find a way to display an sObject Collection on screen during a flow? I couldn’t find a way to do it.

    • I’ve not tried that, but can add it to my list of things to try. Can you give me more details about your use case?

    • Hi teejay, you can adde a screen element after a fast lookup that includes the name of an sObject variable. The screen will display the collection id’s in a comma separated list. Hope this helps – Sean

  8. Andrew (Andy?), good article. I’ve been building flows for a while and I’m currently trying to stretch the limits of the new Flow tools that are in Beta/Pilot. I have managed to Batch record creates using the sObject Collection, sObject Variable and other new goodies. This has been helpful to avoid (to some degree) the inherent DML and other limitations of flow. Specifically we had a use case where I had to cycle through 150+ parent lines and for each line generate 10+ child records. The optimal way inside of flow to do this was to use sObject collections to batch create the new child records in batches of 200. Your article was a good starting point when I set out to create the solution. Thanks again.

  9. Great post Andy! I’m wondering, if I wanted to have a user enter x, y, and z , which all get added as child objects (an object for X, and object for Y, and object for Z) to the Contact record I’m creating as part of the Flow, could I create them using a Loop? I’m not really sure how I could assign the variables from them to an SObject Collection. Maybe this is not the right use case and I have to do it another way. Still wrapping my head around using the Loop element.

  10. Excellent post, thank you. I’ve implemented a similar solution on our custom objects but I’d like to provide error handling when the user clicks the button but has not selected any rows/records from the related list.

    When the user clicks the button without selecting any rows, the sObject Collection Variable contains no records and displays in Flow as “[]”. Unfortunately, this is not a “Null” value so the Flow Decision element cannot evaluate this correctly. I’ve tried comparing the sObject Collection Variable to another sObject Collection Variable that I set to empty (“”) in my Visualforce page but the Decision element does not correctly evaluate that comparison either.

    Is there some extra logic we can include in the Visualforce page to evaluate the “!Selected” variable?

    I’m quite stumped how we can evaluate whether an sObject Collection Variable is empty. I have a stack exchange question here: http://salesforce.stackexchange.com/questions/51797/visual-workflow-how-to-evaluate-whether-an-sobject-collection-variable-isnull

  11. I’m trying to do the same thing you do with Quotes, but with Opportunity Line Items. I’m running into a wall because there is no List Controller for Opp Line Items. Any idea how I can get selected Opp Line Items into the Flow?

  12. In your blog you mention an issues with Assignment elements.

    “There is some magic above the flow:interview element that ensures the fields used by the Flow are queried by the platform, otherwise an error occurs when the Assignment steps are executed stating the UnitPrice field has not been queried (I’m open to better ways of resolving this!).”

    I believe i am experiencing this issue. I have a Fast Lookup element, then a “Debug” Screen to see the results then it goes to an Assignment Element. If the Debug screen is between the Lookup and the Assignment it works successfully, however if I go straight from the Fast Lookup to the Assignment I get an Internal Server error. (Not the typical Flow errors screen or fault screen.)

    Any advice on how to resolve the issue without having to put a screen between/before every Fast Lookup and Assignment elements?

    • An internal server error sounds like a platform bug, my first suggestion is to raise a case with Salesforce otherwise we don’t really know what we are working around. There maybe a simple underlying error message that will shed more light on this, Salesforce support can tell you this.

  13. In salesforce when you create a quote from an opportunity – the quote record is created and all opp line items are added as line items to the quote automatically . I am trying to build a flow that creates a quote from the opportunity. I am successful at getting the quote created but having issues getting the line items created. Would I need to do something similar to this post. Thanks for the great info. You site has been added to my favorites.

  14. Thanks for this I got it working great. However, I would like to validate that items have been selected. I can’t seem to figure out how to do this in the flow. I can use a javascript button to do the validation, however, I can’t figure out how to pass the IDs into the sobject collection variable. Any ideas?

    • I didn’t know you could use JavaScript in flow? Do you have a link on this?

      • I’m not using JavaScript in the flow, I have a JavaScript button where I can validate the items selected before I kick off the flow.

      • I see, so you want to pass Parameters via url? There are details on this the flow developers guide. However not sure if you can pass collections this way. You may need apex for this. Can you perhaps share a gist of what your doing and we can chat easier there and see code etc

  15. Hi Andrew! great article. I’m trying to capture the a list of Cases in a list view to give the user the option to Mass Change the Owners to a Queue along with other options. I’m trying to get the Case ID’s in a Collection Variable but i’m having trouble. What would i need to change in your VF page in order to capture the Case ID’s selected in the list view? Thanks so much!

    • Your welcome and thanks. The article does cover this already does it not? By passing in the recordset variable from the standard controller.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s