How to create a Case function that branches based off a searched substring? - azure-logic-apps

I am trying to apply the following logic in Azure Logic App.
if (contains(inputText, "test1")):
do action 1
elseif (contains(inputText, "test2")):
do action 2
elseif (contains(inputText, "test3")):
do action 3
I tried using Switch, but I can only use equals for each Case. Is there another way I can achieve this?

It's a bit ugly but you can try a couple of approaches.
Condition Action
The condition action allows you to perform a number of different types of searches/comparisons, the ugly thing about it is the nested view of the flow.
This example is looking for Test1 in the first condition and then Test2 if that first returns false.
You can build on that as need be.
Evaluated Variable
You can use the indexOf expression in an IF statement but depending on how much nesting you want to include, it could become fairly nasty as well.
if(greater(indexOf(variables('Input Text'), 'Test1'), -1), 'Test1', if(greater(indexOf(variables('Input Text'), 'Test2'), -1), 'Test2', if(greater(indexOf(variables('Input Text'), 'Test3'), -1), 'Test3', '')))
After that result, you can use your Switch expression to evaluate the results and do something with it.
This is the result ...

Related

Can't get Logic App Contains to work with array or comma separated string

I'm trying to look for specific keywords inside of text from a for each loop.
var text = "The lazy fox jumped over the brown dog."
var keywords = "fox,dog,sun";
If true, I want to do something with the text. If false, I want to ignore the text.
Does anyone know how to use an Array filter, Function, Select, Condition or inline code to check for this? If so, specific examples would be great.
By the way, I have a C# function that handles this extremely well in an ASP.net Core app.
UPDATE 1:
This doesn't work.
UPDATE 2:
The Condition is always false after the for each loop even after changing the settings and parallelism to 1.
Azure Logic App Condition does not work in loop if based on changing values
Thanks in advance!
There are so many ways to achieve what you need. Here are the 3 options that came to my mind within a minute.
The first one does use a For each loop, but I wouldn't recommend using it as it's not very efficient.
The For each parameter looks like this:
The Condition parameter looks like this:
The second option is much easier - no need for a loop, just filter the array straight away, then you can check whether it's empty or it has some items:
The Filter array parameters look as follows.
The split function is identical to the one used in option 1.
If you know JavaScript, you might decide to use regular expressions in inline code instead, e.g.:
Then you'd just need to check the output of the inline code. JavaScript code used in the example above:
var text = workflowContext.actions.Compose_text.outputs;
var keywords = workflowContext.actions.Compose_keywords.outputs;
return text.match(new RegExp("(" + keywords.split(",").join("|") + ")", "gi"));
My personal preference is option 2. However, please note that all 3 options above would find "sun" in text "The weather was sunny" even though there's no word "sun" in the text. If you do need "sun" to match only word "sun" - not "sunny", "asunder" or "unsung" - then go for option 3, just use a different, more complex regular expression.
One of the workaround would be use of Condition Connector. I have initialized the sentence in a string and then used Condition Connector which will be checking the conditions.
Finally, In the true section you can add the connectors accordingly.
Placing a Compose behind the for each loop and referencing the Output in the Condition is what finally worked for me. I used the toLower() function in my Compose. The Compose looks like this.
toLower(items('For_each_2')?['day']?['longPhrase'])

Filter Result Array from Loop in Power-Automate

I loop thru a lot of data in an array to filter it. I the example I only have one Supplier_ID to filter, in real life it would be a lot of.
As result I like to have one big array with all needed Supplier_IDs. This works fine.
But:
How can I avoid the "body": 'part / item' in the output of my COMPOSE (in German 'Verfassen') step?
Now I solved the union of the arrays inside the loop.
Please use expression
outputs('Filter_relevante_SupplierItems')?['body']
instead of
outputs('Filter_relevante_SupplierItems')
in the Verfassen step.
=============================Update============================
Have a try with expression: outputs('Filter_relevante_SupplierItems')[0]?['body']
=============================Update 2============================
Summarize from the chat room for other communities reference:
OP uses union() method to union two arrays in loop to solve the problem.
Another solution for others reference: we can also use replace() method to replace {"body":[ with empty string, replace(outputs(...), '{"body":[', ''). And then replace ]} with empty string, replace(outputs(...), ']}', ''). It can also remove the body.

Verify edge and create edge in the same instruction (gremlin python)

My initial logic of checking if an edge is present and creating an edge needs to query. Im trying to verify and create an edge in one instruction.
This query does not seem to work
ipdb> prop = self._graph.V('pppp').outE('friend').hasId('testEdge').as_('e').inV()
.hasId('dddd').select('e').
coalesce(__.property('testedder', 1111).fold().unfold(),
__.V('dddd'). as_('to_a').V('pppp').addE('friend').to('to_a')).
toList()
1) The first part of the coalesce - updating the property of Edges work fine
2) The second part of the coalesce is either not being called or not working. It is working as an independent query. Does 'as' not work in anonymous traversals?
PS: Im using AWS Neptune
You had the right idea but you needed some simplification. I'll try to do it in steps. First, whenever I see labelled steps, I try to see if there is a way to avoid using them. In this case, they can be factored out:
g.V('pppp').outE('friend').
filter(hasId('testEdge').inV().hasId('dddd')).
coalesce(__.property('testedder', 1111).fold().unfold(),
__.V('dddd'). as_('to_a').V('pppp').addE('friend').to('to_a'))
Readability of the traversal improves on those first two lines because the reader can immediately see that you want to find an edge given some criteria which was only implied by the step labeling approach. Next, I looked at coalesce(). As it stands, if filter() returns no edges then coalesce() will never get a chance to execute and that's why the second part of coalesce() never has an opportunity to work for you. So, let's clean that part up:
g.V(1).outE('knows').
filter(hasId(6).inV().hasId(2)).
fold().
coalesce(unfold().property('testedder', 1111),
V('dddd').as_('to_a').V('pppp').addE('friend').to('to_a'))
If it's not clear why the fold() and unfold() are where they are, you should check out my detailed explanation of the approach here. So, with fold() and unfold() where they should be, the coalesce() should now trigger both conditions depending on whether or not an edge passes the filter(). The first part of the coalesce() is fine, but the second could still use a bit of work as I'd again like to factor out the step labels if the aren't necessary:
g.V('pppp').outE('friend').
filter(hasId('testEdge').inV().hasId('dddd')).
fold().
coalesce(unfold().property('testedder', 1111),
addE('friend').from(V('pppp')).to(V('dddd')))
The above Gremlin assumes that you know "pppp" vertex exists. If you do not then you might try (as suggested by Daniel Kuppitz):
g.V('pppp').
not_(outE('friend').hasId('testEdge').
filter(inV().hasId('dddd')).
property('testedder', 1111)).as('p').
V('dddd').
addE('friend').from('p')

Test action outputs length

In my Logic App workflow, I'm trying to evaluate a condition for the previous action outputs array.
My condition expression
#less(action('Get_items').outputs.length, 1)
results in error
action 'Item_found' completed with status 'Failed' and code 'BadRequest'.
The same happens for
#greater(action('Get_items').outputs.length, 1)
as well as
#empty(action('Get_items').outputs)
What am I doing wrong here?
Background: The action('Get_items') is query retrieving items from a SPO site list using a Filter Query.
The action succeeds but the App Run Trace doesn't show any details on the outputs, in this case the expected empty array.
I managed to achieve the desired condition evaluation by correctly accessing the array the same way a for-each action does:
#empty(body('Get_items')['value'])
The documentation doesn't give a hint on this.
Accepted solution was not working for me for CDS entities, so I have solved it by using such condition:
#length(body('Get_items')['value'])
If I understand correctly it is converting array to string and empty array is converted to [], so you just have to check if the output of query is more than 2, then it means Get_Items is not empty.

ibatis dynamic sql using two conditions

I would like to use a dynamic sql statement that executes only when the variable is not null AND greater than zero. Like this:
<isNotNull prepend="AND" property="ProprietaryId">
<isGreaterThan prepend="AND" property="ProprietaryId" compareValue="0">
G.PROPRIETARY_ID = #ProprietaryId#
</isGreaterThan>
</isNotNull>
but without prepending two 'AND's.
I have read the documentation but have found no good example.
To work around to this issue I almost never use the "prepend" feature, but instead write an sql like this:
WHERE 1=1
<isNotNull property="ProprietaryId">
<isGreaterThan property="ProprietaryId" compareValue="0">
AND G.PROPRIETARY_ID = #ProprietaryId#
</isGreaterThan>
</isNotNull>
I just came across this question while looking for the same answer. While effective, this solution kind of bugged me so I studied the iBATIS docs some more and noticed this example:
<dynamic prepend="where">
<isGreaterThan prepend="and" property="id" compareValue="0">
ACC_ID = #id#
</isGreaterThan>
<isNotNull prepend="and" property="lastName">
ACC_LAST_NAME = #lastName#
</isNotNull>
</dynamic>
You'd think that might cause a superfluous "and" to be included within the WHERE clause if only one of the conditions is true, but apparently iBATIS is smart enough to prevent this when using the dynamic tag. It works for me (using iBATIS 2.3.0 in this case).
Its me from the future. Parent elements override the prepend of their first child, so your code will work fine since the isGreaterThan prepend will be overwritten by the parent isNotNull prepend.
From the docs:
The prepend attribute is a part of the code that is free to be overridden by the a parent element's prepend if necessary. In the above example the "where" prepend will override the first true conditional prepend. This is necessary to ensure that the SQL statement is built properly. For example, in the case of the first true condition, there is no need for the AND, and in fact it would break the statement.
<isNotNull property="ProprietaryId">
<isGreaterThan prepend="AND" property="ProprietaryId" compareValue="0">
G.PROPRIETARY_ID = #ProprietaryId#
</isGreaterThan>
</isNotNull>
just delete the first prepend will work

Resources