I Wanna Flow Clone!


Brian and I talked about this on this week’s WizardNews WizardCast, but we thought perhaps a text-based walkthrough might be in order. So let’s talk about clones, baby.

The clone button on Salesforce records is great, for obvious reasons. But it has one major shortcoming: it brings over EVERYTHING.

Let’s say you want to clone a case, because a second client is having the exact same problem 3 months later. For one, it’s probably not going onto the same account, or have the same contact. For another, the Case Status probably needs to be reset to its earliest setting, since the original Case is (hopefully) closed.

But keep in mind that a mature Case object may have many fields that are NOT on the page layout, but nonetheless important to maintain. You may have an Approval Status that keeps track of approval steps but is hidden to prevent modification. You may have date fields that log when certain events occurred, but again, are hidden for security. You may have checkboxes or other fields verified by validation rules to ensure changes go through proper channels, like API or Flow.

These are all data points that you would NOT want to be brought over in a clone, because they are probably not going to be accurate for your new Flow.

So how to clone while still ensuring that existing data doesn’t become bad data? Simple! Flow!

Flows can be fired off of buttons, just like cloning, so that makes it an excellent candidate, plus Flow has the ability to read existing records and create new ones. Let’s take a quick look at what needs to be done.

We’re going to assume, to start with, that we’re going to be passing in the ID of the case we are cloning. We only need to pass that one piece of data in, because we can get the rest later. Let’s make a new variable: varCaseID. Don’t forget to make its Input/Output Type “Input Only”, so it can receive that data. If you leave it as Private, it’ll never be able to receive data passed to it.

Screen Shot 2015-04-08 at 14.10.32

Now that the Flow has a place to store which Case we are cloning, let’s get the rest of our fields. Create a Record Lookup, and set the filter to look on the Case object for a record where the Id is equal to our new variable, varCaseID. This is all you need to define, because you’ll only ever get one record with that ID!

Screen Shot 2015-04-08 at 14.13.34

In the section below, you will need to manually define which fields should get brought over in the clone. Yes, this may get tedious if you have a lot of fields that need to come over. But I would highly advise confirming with your stakeholders which data is truly needed. You’ll find most of your fellow employees or executives only want the data they really need, and are happy to let the rest go. You will need to store each of these data points in its own variable, and those variables can remain set as Private, because the Lookup will go and get the data; it’s not the same as having data pushed to it.

Screen Shot 2015-04-08 at 14.23.32

For the sake of this example, let’s assume the Account and Contact are the same; this is a whole other can of worms that would practically take a whole other article to examine properly.

Now that you have your old data brought over, we can begin creating our clone. All we need to do is add a Record Create to the Flow, and set it to create a new Case. Then, in the fields below, you can assign all of your variables to the proper case fields, like so:

Screen Shot 2015-04-08 at 14.29.12

That’s it! Draw an arrow between from the Lookup to the Create, and click the Start icon (the green arrow circle in the top right) on your Record Lookup so the Flow knows where to begin. You can now save your Flow, and create your Clone button.

Screen Shot 2015-04-08 at 14.38.16

Once you’ve saved your Flow, close it to get to the Flow’s information screen. On this screen, you’ll see a URL; copy this to your clipboard, you’ll need it in a second.

Screen Shot 2015-04-08 at 14.38.30

Now on to the button itself. I prefer calling the button something else, to reduce confusion. Something like SmartClone, to let you and the users know that this button is smarter than the average Clone. Before actually defining the button itself, I suggest changing the Behavior to “Display in Existing Window without Sidebar or Header”. This will effectively replace the contents of the users’ open tab when they click the button.

Now the URL for the button. Paste the URL you saved from your Flow, and add the following:


Screen Shot 2015-04-08 at 14.44.05

Here’s the breakdown.

  • The ? is important because it lets Salesforce know to expect settings to be set in the URL. Each element we pass is essentially something we are setting this URL to do.
  • varCaseID – This is the variable we created, remember? Putting this here tells Salesforce we need to send something to this variable when the flow is started.
  • {!Case.Id} – This is a merge field that turns into the Case ID itself. You can generate this via the merge field operators right above the URL window, as always.
  • & – We can pass more than one piece of information, but we need to separate each one with a & symbol.
  • retURL – Here you can set where the Flow should go when it is done. If you do not set this, the Flow will just repeat over and over. By passing it / then the Case ID again, it knows to go back to the Case that started this.

It may help to put your varCaseID and your retURL on separate lines in the URL window. Adding line breaks won’t cause any problems, as they get ignored, and it makes your URL a lot more readable when you have to support/troubleshoot it later.

Voila! Put this on your case page layout, and you’ve got a SmartClone!

The Casting of Pods: WizardCast

wizardcastlogo-smallpngBACK, we are!

And boy are we coming back with a BANG. Well, at the very least, we are coming back audibly. Literally.

I am teaming up with the illustrious SalesforceWizard (aka Brian Kwong) to bring you WizardCast, a new Salesforce podcast. Yes, I know. Another Salesforce podcast. No, hang on, this one is DIFFERENT. Really, I promise. Mainly because we refuse to take ourselves seriously. At ALL.

The goal is to do weekly shows, life notwithstanding, so take a listen here to get a feel for what the show will be like, and watch for more casting of pods soon.

On other fronts, there are more blog posts currently being written and more opportunities for learning on the horizon. Be on the watch for more coming!

For the KIDS

Screen Shot 2014-10-20 at 13.56.08

Alright, Community. We’re winding down from Dreamforce, an exhausting event, to say the least. There’s a lot to do and a lot to absorb at Dreamforce, but one of the themes that appears again and again at every Dreamforce is one of philanthropy. Marc Benioff is well-known for his 1-1-1 business model, in which businesses commit to devoting 1% of their time, money, and product to charities in need.

In the spirit of that mindset, I’d like to ask you, my fellow Salesforce community members, a favor. This year, I am working with the Extra-Life charity, a group that works to provide funds for the Children’s Miracle Network hospitals, specifically for children whose families cannot afford the medical treatment they need to live without pain or even survive. Our major event is this Saturday, and I am helping to raise money for this incredibly worthy cause.

There are not many things that are as life-changing as meeting the 10-year-old boy whose life you helped to save by raising money to pay for his surgery, hearing his words of gratitude, and receiving the deeply-heartfelt hug of a young life given hope.

Please, if you can help any amount at all, please consider donating to this cause before Saturday. You can do so by clicking here or on the banner image above, which will take you to a secure donation page. The entire donation will go to children in need. You can visit Extra-Life.org for any validation you may need, and of course, it’s tax-deductible.

The New Way to Socialize at Dreamforce 2014

Influenza. Enterovirus. Ebola.

Ok, come back, it’s alright. Just reading the names won’t make you sick, alright?

It’s no secret that 2014 has been a bit of a banner year for infectious disease. And, not to scare anybody, but a LOT of us are about to all gather in a location with 150,000 other people from around the world, all at the same time. I don’t know about you, but that gives me just a liiiiittle pause.

But there is a solution! And it is a good one. Recently, the Harvard Medical School published its findings on the nature of hand-to-hand communications, and the likelihood of transmission of diseases in its different forms. The short version: fist bumps are a safer and cleaner alternative to handshakes.

That’s right, you read correctly. Harvard has officially stated that we should all be fist bumping.


Absurd as it sounds, there is a very strong logic to it. When we shake hands, anything that is in our palms or on our fingers is instantly transferred to the receiving hand, and vice versa. The slight amount of moisture we always have on our hands practically ensures that the transfer occurs, too. There’s no “10-second rule” either; those bugs move instantly as they are practically shoved into waiting hands.

With the fist bump, however, the likelihood of transfer is much lower, because the contact is not so wide-spread, there is less moisture and pressure being applied, and because of the drastically-reduced amount of microorganisms on the outside of our fingers.

So I propose this, fellow Dreamforce attendees: the (un)official greeting of Dreamforce 2014 should be the Fist Bump.

Now I know what you’re thinking. “But Mark, that’s so unprofessional!” Ah, my friends, “professional” is what you make it. “Professional” is basically another way of saying “extremely polite”, and what could be more polite than not passing on the DreamPox?

No no, hear me out! We can make the Fist Bump professional, right? Let’s set some guidelines, ok? Nothing says “professional” like rules and guidelines, am I right?

The Professional Bump is straight-trajectory, no-frills, and quick contact.


However, do not “explode” afterwards. This is tacky, and is therefore right out.


Unless you’re doing it with a bald eagle.


Maintain low velocity when jewelry is present. It is not professional to cause contusions.


The “guided strike” is inadvisable, as it defeats the purpose and further invades personal space.


Bumping in gloves is acceptable, so as to not facilitate the awkward pause of waiting for removal of said glove.


Welp, here you have it, folks. If that doesn’t convince everyone to be slow-punchin’ at DF14, I don’t know what will. Just don’t be offended if I keep a bottle of Purell handy, ok? Love you.

The First Not-Really-Annual-We-Just-Do-This-When-We-Feel-Like-It Community Flow Hackathon!

2012.05.04-HackathonOn the 25th of June in the year of our lord 2014, it was hereby decreed that there would be a great ‘Thon of Hacking, dedicated to the communication of ideas and knowledge of The Great Flow. Over the following 7 days, many heroes from across the land ventured forth to slay the Dragon of Communal Ignorance, valiantly submitting their contributions and felling the great beast. When the dust cleared on the 2nd of July, there were only victors.

Hang on, I think my nerd is showing. Can you tell I run Dungeons & Dragons games in my spare time?

If you have any interest in Flow, I highly advise heading to the Success Community page for the #Sp14FlowHackathon topic, where you can see the collective hackathon in its entirety. It was started in the group “Official: Salesforce Workflow Automation“, and there truly were some amazing ideas. I’ll be dedicating an entire blog post to my submission next week, but at the moment I want to highlight some of the other submissions here.

(The following “awards” are mine and mine alone, and I do not represent Salesforce or any other company or individual.)

Best Use of New Features Award – Reassign Records when the Owner becomes Inactive

Jen Nelson brings the awesome with a Flow that uses Flow Triggers, Fast Lookups and Loops seamlessly. What’s more, it’s incredibly useful to ANY admin and operates quietly, predictably, and seamlessly. It’s the sort of automation that throws off new admins in the org; it’s so clean that it fools them into thinking it’s part of core Salesforce functionality, not realizing something else enabled it. Hey Jen, be sure you train any new admin you work with that this is flow! Otherwise he’s going to get that question wrong on his 201 Certification test!

Most Work Saved Award – Assign and Maintain Due Dates for all Tasks in a Campaign

Jen Dunn not only wins the award for Most Work Saved, but also for Most Patient Users! Whoever had the job of manually assigning and updating up to 35 tasks had a crap job, and Jen made it a whole lot easier! I just hope you didn’t put someone out of a job! This is a prime example of the power of Flow: taking a massive, repetitive task and reducing it to a few clicks. Bravo.

Wildest Idea Award – Clone Chatter Group with Members

Rakesh “The Flow Machine” Gupta makes us all ask ourselves the deep philosophical question: “Will I ever have to clone a Chatter Group? And if so, what am I going to do about all those Members?” That’s heavy, man. So hardcore. If nothing else, I love Flows like this because they make admins stop and say “Wait, Flow can do THAT? If it can do that, I wonder what else it’s capable of.” Nothing better illustrates the breadth of awesome that Flow can accomplish.

These are just some of the Flows that were shown. Go and take a look at the rest!


So We Have DF14 Speakers. Let’s All Calm the F*$# Down.

hilary-protest-pakistanNo really. Calm down. Deep breaths. Hear me out. I’m not a fan of this move either (I’m a centrist who is largely apolitical at times, and this kind of divisive move rankles against my more peace-seeking sensibilities), but I think I know why they did it.

Nooo, no. Stop. Stop stop st… STOP. That’s not why. I kn… Yes I know you thin… LET ME FINISH.

Clearly the choice of Hillagore is a politically charged one. But before you go off the rails with cries of “WELL I’M NOT GOING TO DREAMFORCE NOW”… ok, before you go off any more of those rails… just… hear me out. Benioff is not so short-sighted; he had to know this was going to ruffle feathers, and a lot of them. Let’s face it, the Business Airspace has no small amount of planes that fly at Right angles most of the time. And our political landscape right now is metaphorically akin to something resembling the offspring of a house of mirrors, an electric fence of Jurassic Park-strength wattage, and a spotter tower filled with over-caffeinated snipers strung out on PCP. You don’t even have to take a wrong step and you’ll have bullets whizzing around your ears.

These are known quantities. Marc Benioff is well-known for being a left-leaning bleeding-heart liberal idealist, but he is most definitely not stupid. Therefore, it stands to reason that he made this decision despite knowing the reaction it would have, believing the gains would outweigh the possible backlash.

Where could the answer lie then? At the end of May, Salesforce received Authority to Operate by the FedRAMP, effectively opening its Government Cloud for business. Inviting two prominent Democratic Party representatives to speak is just good business for Salesforce, because it gets their foot in the door for the Government Cloud.

Think about it. Salesforce is, at the very least, a database of businesses and/or people, with the ability to expand far beyond that, into things such as ERP and project tracking. It’s a collection of DATA. What government agencies are going to want to collect data? Well, you’ve got intelligence agencies, but they’d never let another company track their data. Probably the same story for the IRS. But then there’s Social Security, Housing and Urban Development… social programs and infrastructure. And historically, which party puts more money into social programs and infrastructure? Hillagore’s Party.

I’m not talking about whether or not anyone should put money into those programs. I’m simply saying that Salesforce and Marc Benioff know who their demographic is for the Goverment Cloud, and they’re marketing to that. Hillary is already pretty much THE shoe-in for the Dems in this upcoming election. If she wins, and had a marvelous experience at DF14, it’s a huge feather in Salesforce’s cap, business-wise. There will be a lot of money to be made. This is a business decision.

Sure, they could have invited Paul Ryan or someone like that to get the opposing viewpoint, but there’s a few reasons why they won’t. One, I think Benioff would have a hard time playing mediator; he’s not unbiased and he’s wise enough to know that. Two, it wouldn’t accomplish their business goal, and might actually take away from a positive Hillary experience.

Yes, there will almost assuredly be protestors at the conference, but please don’t count yourself among them. You’ve got better things to do at Dreamforce than waste your time accomplishing nothing except rubbing elbows with other people who think the same way you do. For the record, I’d be saying the same thing to the other side, were the tables turned.

Salesforce is an inclusive platform; it’s remarkably democratic (and I mean that in the general definition of the word, not referring to the party) in that it gives a lot of power to individuals in how they set up their business software. It enables ANYONE with sufficient intelligence to maintain their business. There are no politics on an Account page, no party lines drawn in how you configure your workflow. Salesforce, and therefore Dreamforce, is about working TOGETHER, not about being divided. So don’t let yourself fall into the Us vs. Them trap, because there’s no room for it at my table, and there’s no room for it at Dreamforce.

Getting Record Type IDs in Flow without Hardcoding (UPDATED!)


Have you ever migrated your Salesforce data or fields into another org? Do you develop your new features in a Sandbox first? (And if not, WHY?)

If you answered “no” to both of these questions, ask yourself if you can safely say you will NEVER do so.

Chances are that any given admin will, at some point in their admin career, have to either migrate at least some part of your Salesforce, or at the very least be REQUIRED to build something complex in the Sandbox first, so as not to impact current process. If your company gets acquired, there’s a very good chance you’ll have to merge orgs.  One way or another, you’re probably going to be beholden to this fact of life. The business world necessitates preparedness for just such an eventuality.

Previously, I had thought this would never be a problem. I’d never had to release anything that was so impactful that I couldn’t build in production and delay its effect (pardon me a moment while I slap my own wrists). I didn’t anticipate a full org merge with another Salesforce org, though I really should have. So I didn’t foresee the pain that would be, the horror known as: HARD-CODED RECORD TYPE IDs.



You may think that using hard-coded IDs is not a big deal, and if you only have one or two uses, it’s probably not. But over time, the practice can become pervasive in your admin methodology, and it will then grow well beyond those happy few. I mean, let’s face it, most of the time it’s a lot easier to deploy than other solutions, right? Just referencing a single ID is a lot simpler than writing the formulas, workarounds and methods needed to not use them, right?

The trick is, this trap has two kinds of cheese. The first is the fact that it’s usually easier, but the second is the fact that we as admins and developers often come to the conclusion that there is no workaround. Years ago this used to be the case, but today we have a lot more tools at our disposal, and many of the cases where we would be forced to use a hard-coded ID are not actually cases where we are truly forced, if we just keep working and digging at a solution.

Then I had an org merge to work. Because of our long-standing practices in our 5-year-old org, we had hundreds of single hard-coded IDs in our system. The trap had closed. In order to merge our system into theirs, we would have to reconcile ALL of those. We had a mountain of work ahead of us, because we had not looked ahead.

In working on solutions, I have developed a way to avoid hard-coded Record Type IDs in Visual Workflow. This has traditionally been a place which is widely considered to be inescapable for hard-coded IDs, but today I say thee NAY. There is a way!

(UPDATE: I had previously published a kludgey way of doing this, but it turns out there is a better way to do it that Salesforce has provided! Special thank you to MVP Aiden Martin for pointing out this exists!)

Screen Shot 2014-06-17 at 12.50.33

Create a Record Lookup, and when choosing what object you’re looking at, choose “RecordType“. Many an admin have glossed over that picklist choice, not even realizing it’s there, but this is an object usually referenced by Apex or API for the purposes of finding RecordType information. Because it’s in the API, we can use it in the Flow!

In your filters, choose “SobjectType” and set this to the object whose record type you are looking up. To determine which record type to use, I recommend using DeveloperName instead of just Name; the Name is the equivalent to the Record Type’s label, and is more likely to change. By basing it on the DeveloperName, you’re less likely to have issues with the name changing and breaking your flow.

Assign the Id value into a variable for use later and BOOM! You now have your Record Type ID stored in a variable for using later in your flow, and you didn’t have to manually enter it into the Flow. If the Record Type changes to a different ID in the future (and odds are it will), you will not be screwed. I REPEAT: you will NOT be screwed.

How I Learned to Stop Worrying and Test My Flow

darthvadertestingDo you write Flows? If so, congratulations, you’re a developer. No no, you are. You’re developing software, just with a declarative interface, so yes, you’re a developer. And what does every developer have to do, even though they hate it?

Test. Test. Test.

Once you’re a developer, you’re not exempt any more! Welcome to the development world. Yes, we hate testing. We like to think our Flow is just going to work the first time, but in all of the 30+ flows I have written in my time, I can only say that I am just lucky enough to have gotten away with it once. Seriously, that’s like a 3% chance.

Even then, I played it safe, and verified that it was going to work right by testing it first. You will save yourself SO much time and frustration by testing before deploying.

Flow is a unique beast, though, and there’s not a lot of documentation out there on how to test your stuff. By and large, we’re left wondering just what we should do to actually test. There’s some obvious things, but then the only truly obvious route is to actually deploy in order to test, and that’s not always a good option.

So without any further ado, here are some of the methods and guidelines I have come up with for testing my Flows.

1. Sandbox Sandbox Sandbox


I know sandboxes seem like a waste. I know the concept is alien to some of us. But really, do it. DO IT. This is especially important for Flow Triggers, which, I can attest to personally, can cause stupendous failures.

When a Visual Flow crashes, it only affects the person trying to run the flow, and usually just throws an error. When a Flow Trigger crashes, that crash can affect ANYONE who is trying to do their work. Even if you have “Administrators run the latest flow version” turned on, you can still have problems if you haven’t activated any versions. So trust me when I say, Sandboxes are more important than ever before for Flow.

2. Always Fault

There’s nothing that your users hate more than a cryptic error. Seeing

An unhandled fault has occurred in this flow. An unhandled fault has occurred while processing the flow. Please contact your system administrator for more information.

is the surest way to frustrate and confuse, not to mention driving your users AWAY from using your blood-sweat-and-tears Flow. Nobody wants to use a tool they don’t understand, so quite simply, they won’t.

So how do we avoid this? We add Faults.

Screen Shot 2014-05-06 at 13.54.13

Every Create, Update, Lookup, or Delete.

Any Record or Fast Element can have a Fault element attached to it, and your best practice is to ensure that every Record or Fast Element has a Fault element attached to it. A Fault element can be made by creating any element and drawing an arrow to it from your Record or Fast Element AFTER they already have an arrow pointing to another element. If the Flow errors on that source element, it will then perform whatever is in your Fault, rather than showing that “unhandled fault”. That’s what unhandled means; it means that you haven’t defined what should happen when a fault happens.

A fault can contain a message to the user, it can create records, it can even send an email if you use the Email Plugin. Anything Flow can do, you can make happen from a Fault, so this is invaluable not only to your users, but also to your debugging and testing. Having a screen that tells you what your variables’ values are AT the point of failure is essential.

Another quick tip: if you want your fault to do things AND present a screen (I almost always have mine send an email and then show a customized error in a screen), do the email or other things first, THEN do your screen. If a user gets an error message screen, they are a lot more likely to exit the screen instead of clicking the Next or Finish button, and if they don’t click that button, it WON’T fire your email or other actions.

3. Gotta Test ‘Em All


This is another drudgery chore, but as admins I cannot stress enough that you have to personally try out your functionality. Don’t just try your flow while logged in as you; try it while logged in as the actual users who will use it. Try each choice option you present in your screens, or at least a sample of them, if there are too many to test. Make sure you run your Flow through every possible decision path, to be sure each decision path actually works.

Also, try your flow while logged in as the actual users who will use it. What, I already said that? Well, good, it needs to be said again. It’s so easy to forget to do, because you have to do it in a sandbox in order to do it safely, but it’s one of the most important things you can possibly do in your testing.

So How Do I Test Exactly?

The Temporary Assign Element Method

Screen Shot 2014-05-06 at 13.58.00

The Run button is a great option in the Flow Designer, but unfortunately it’s fairly useless without some setup. Almost every flow needs some data passed to it, and that Run button cannot pass any of that data. So how do we make it useful again?

Create an Assign element BEFORE the start of your Flow, and in it, assign some sample data to the variables that would usually have been set. Draw its arrow going to the start of your Flow, and then make the Assign element the actual starting element.

You can now use the Run button with impunity! This makes testing a lot faster when you don’t have to click around to get to your Flow, and it has the additional bonus of being able to test your Flow (at least, the testing that you do while logged in as you) without making it live for everyone. It’s a great way to do quick proof-of-concept testing as well.

Please keep in mind this doesn’t work on any flow with sObject variables or collections at this time.

The Screen Debug Method

Screen Shot 2014-05-06 at 14.06.44

This ties in directly with bullet point 2 above. If, in your testing, you hit an error or bug or other unexpected result, being able to insert a temporary Screen that just repeats what the variables or Screen Choice values are at any given point can be the key to unlocking the mystery behind your dysfunctional flow. There is no reason this cannot be done at any time; you can insert this into the middle of your flow’s track without having to use a FAULT path, so you’re seeing things as they happen, even before the error comes down.

Of course, because this method uses Screens, it is incompatible with Flow Trigger flows. Bummer.

[Edit: Removed the Flow Debug object method. Turns out this has some pretty glaring issues with most faulting in Salesforce. Thus reiterates my overall point about being extremely thorough in your testing of, well, anything.]

New Tech for Flow Triggers: Complex Validation Rules

Street_Fighter_III love Salesforce, but in my spare time I do a lot with gaming. I have a particular interest in the fighting game community (or FGC as it is referred to by its members). The FGC subculture is very competitive, but also very tight-knit, and this closeness, combined with time and creativity, has formed its own subcultural lingo, with terms like “salty” and “happy birthday”.

One of those terms is “tech”, which is short for “technology” but is often used more like the word “technique”. When someone comes up with “new tech”, it means they have devised a new trick, and if it’s useful, it’s likely to be seen and repeated by other players. Because of the social nature of the FGC, with tournaments being streamed live and higher internet speeds now making online matches a viable place for competition, new “tech” can often spread around the world and be used professionally within a matter of days.

Granted, not all new tech is actually useful.

Granted, not all new tech is actually useful.

In a lot of ways, the Salesforce community is similar. Admins and developers create “new tech” all the time, and with all of the online tools like the Answers community, the official Collaboration groups, and the blogosphere, the tech gets spread quickly from admin to admin, developer to developer. Just look at SteveMo’s posts; the amount of new tech he comes up with for reporting is insane! (The “Power of One” piece of tech is practically iconic!)

So last night I had a flash of inspiration for some new Visual Workflow tech, gave it a try, and met with some moderate success. It is dependent on Flow Triggers, so if you don’t have that pilot yet, this won’t apply to you, but that’s ok, because this tech isn’t quiiiiite usable yet by anyone. But we’ll get to that.

Here’s the concept: Let’s say you want to ensure that an opportunity cannot be Closed Won if it contains Product A BUT does NOT contain Product X. Previously, this was not possible without Apex, because validation rules do not run in that direction; you can control your Opportunity Products based on the Opp, but you cannot control your Opp based on the Opp Products. This is now possible, however, with flow triggers.


To start with, you’ll need to make a new checkbox field on your Opportunity. For this example, let’s call it Product Validation Alarm. Don’t put it on any page layout; you won’t need to actually access it. It just needs to be there, and it needs to be writeable by every profile. Once you have this, make a simple Opportunity validation rule that checks if Product Validation Alarm is TRUE. That’s it, nothing else needed!

Now that we have that to start with, let’s make our flow!

As a proof of concept, all that is needed here is a flow that sets that Product Validation Alarm checkbox to TRUE. If we were doing this for real, we would set up a Loop element with a Fast Lookup to parse through the OpportunityLineItems looking for any that match Product A, but for just the proof of concept, this is all we need.

Screen Shot 2014-04-28 at 13.43.55


A simple flow trigger can then be set up with any workflow rule. I created a rule that just looks for Stage to be changed to Closed Lost. In our scenario, you could have this go off when the Stage is changed to Closed Won, if you just want to set up the proverbial bouncer at the door of the club, or even when the Opportunity Product is created, if you REALLY wanted to be prohibitive.

Note that in the Flow Trigger we will have to pass in the opportunity’s ID to our Flow’s variable. (I LOVE that we can do this here instead of having to define arguments in the URL!)

Screen Shot 2014-04-28 at 13.50.38


Basically, what we are doing here is PURPOSEFULLY setting up criteria that will trigger a validation error. But we are using Flow to be the watchman that presses the Alarm button, rather than relying on a validation rule that cannot even fathom what might be happening. It’s like hiring a physicist to watch the Large Hadron Collider for anything that might go wrong, as opposed to hiring a 7th grade science teacher. (No offense to 6th grade science teachers, mine was completely awesome, super smart and one of my favorite teachers ever, but she probably wouldn’t have been able to be an overseer at CERN.)

Now, here’s the catch:

rtaImageThis is why I was saying that no one can really use this right now.

Right now, when Flow causes a Validation Rule error to fire, this is what it displays. It doesn’t actually show the validation rule’s error, and it doesn’t appear to be an option at all to display it.

This IS currently effective, however, at stopping users, even if it does not tell them why they are being stopped. It’s not good UX. If you’ve got reeeeaally savvy users, you can use this and give them a list of the flow IDs as they correspond to what is being blocked. Or, if you have only one of these errors, it’s relatively easy to train your users that when they see this message, it means they did {insert problem here} wrong. But even then… new hires come on, people forget because they don’t hit the error for months… it’s a minefield of possible problems.

So if you want to see Flow Triggers being able to be used as complex validation rules…


There is an idea on the Salesforce Success site requesting this very thing. Give it a thumbs-up to make sure this happens!

In the meantime, this still serves to show the sheer power of Flow and Flow Triggers. Go forth and use that power!