If we haven't talked about this already, I feel like I should take a moment to frame our conversations about Microsoft Power Automate. Unlike many of the other technology products out there, teaching and learning with Power Automate is unique in that the 'finished product' is going to be different for everyone. The usual approach of teaching everyone how to bake the same cake isn't going to work. We need to focus, rather, on...
The Ingredients
In my article, Modeling a Global Variable Without Variables in Power Automate / Flow, I walk through storing a placeholder in a text file outside of Power Automate so that subsequent runs have something to reference about previous runs rather than starting fresh each time.
In the article, Expression Interlude - Random Item from Array in Power Automate, I show how to choose elements of an array by controlling the digit at the end of the expression. In this instance, it was random...but by combining the two techniques, I can sequentially step through any array from run to run.
In the demo below, I'll use the alphabet as my array in order to rename images sequentially by date for my blog and/or community posts. But the array could just as easily be a list of phone numbers or email addresses that you'd want to step through for automated call/message distribution. The individual pieces to solve many business process issues are there, we just need to reframe how we approach learning and sharing solutions so that we highlight the steps rather than the final product. I think this will help users find relevance in their individual use-cases.
This Particular Cake
When I use images and/or screenshots in my blogs or responses in the community, I'll save the images on my desktop with a filename of yyyyMMddx.png, where x is some letter of the alphabet starting with a and working my way through. I rarely make it past 'm' on any given day, so going until 'z' should give me enough room. Since my website host can access images directly from Google Drive (among others), I wanted to be able to drop my images off in a folder, have Power Automate trigger from that and then rename the file as it moved it into a folder on my Google Drive. From there, I can pick it up and use it in either the blog or the community. Let's get started.
The Steps
Just as in the global variable article, we are going to create a text file to store the information, and then reference that in the flow. It can say whatever you'd like in the content, but if it's anything other than just the data, be sure to include an easy way to parse it out. In my example, I include a label so I have context...as well as an equals sign which I'll use later.
The first thing is a trigger based on where the screencap will be dropped off. I've used a OneDrive folder, but you can easily choose any other cloud storage that offers a similar trigger. After that is a step that is becoming standard for me: a simple Compose action where I keep my notes for any changes, which I've labeled as Release Notes. The next part of my setup is where I define the array. Remember that this can be anything from a string of letters, to a list of phone numbers to use in a Twilio action, or maybe a list of email addresses...all up to you!
We'll next get the date (converting the timezone and format in the same action) and then we'll read the content of the text file and parse out the information we want. In my compose action, I am also converting the value to an integer as that is what Power Automate expects when selecting a specific element of an array.
If you'd like more detail on how to use the Split() function, check out my first video on YouTube, Using the Split Function in the Microsoft Power Platform.
We'll also use the Split() function in the next action to change our Alphabet string into an array using the expression:
split(outputs('Alphabet'),' ')[outputs('StoreImageID')]
You can see we are splitting the string, using the space as a delimiter, and then selecting the 'nth' element of the array (n = the number stored in our text file). In this example, A would be 0, B would be 1, and so on.
Then I create the file in Google Drive. I've renamed the action to "Move File" to make it friendlier, but the filename is the output from my date action above, followed by the output from the previous ImageArray step using the Concat() function. Then we'll need to increment our Image ID by one and update the text file with the new number.
Some people had indicated that they were having trouble with this step in the Global Variable article, where the text file was being updated with the text of the expression rather than the result of it. I've spoken to the good folks at Microsoft about it, and they've implemented a fix that is currently being rolled out. If your text file starts to look like this:
Then you'll want to use the workaround: Simply to build the whole content inside of a Compose action, and use the output from that to update the file...see below.
Finally, I go back to the image source folder that triggered the flow and delete the original image file. Thinking through this as a whole: If this was the end of the story, then each day would just pick up where the previous day left off (letter-wise), so I'll need a separate flow that runs at midnight each day to reset the text file back to zero.
Iterative Learning (v2.0)
I've mentioned before that one of my favorite things about Power Automate is the flexibility to improve your process as you learn new things. Shortly after I published this article, I realized that I didn't account for different file types. The fix for this would be to get the file extension from the trigger, and then append that to the filename in our Create file step...but I'm not certain if this is a OneDrive "feature", or I'm misunderstanding the intent of 'filename', but we actually need to get the file's metadata first, then parse the extension from the 'Name' field in that.
To parse the extension, we'll use Split() again and the period as our delimiter...but because we don't know if the file name will have periods outside of the one we expect, we can't just put a [1] to grab the second element of the array. So we'll wrap our Split() expression in a Last() to get the very last thing in the 'collection'. My finished expression looked like this:
last(split(outputs('Get_file_metadata')?['body/Name'],'.'))
Then, down in our Create File action (which I had renamed to "Move File", we'll append a period and the output from the extension compose to finish out the complete filename.
concat(body('GetDate'),outputs('ImageArray'),'.',outputs('GetImageExtension'))
I hope you found this helpful, and I hope we'll see some traction on sharing the importance of the ingredients rather than the finished cake. I like cake....a lot! But, in this case, the pieces are infinitely more useful than the whole.
Good luck!
Comments