I like what Microsoft’s doing in the app integration space. They breathed new life into their classic integration bus (BizTalk Server). The family of Azure Service Bus technologies (Queues, Topics, Relay) is super solid. API Management and Event Hubs solve real needs. And Azure Logic Apps is maturing at an impressive rate. That last one is the one I wanted to dig into more. Logic Apps gets updated every few weeks, and I thought it’d be fun to put a bunch of new functionality to the test. Specifically, I’m going to check out the updated JSON support, and invoke a bunch of Azure services.
Step 1 – Create Azure DocumentDB collection
In my fictitious example, I’m processing product orders. The Logic App takes in the order, and persists it in a database. In the Azure Portal, I created a database account.
DocumentDB stores content in “collections”, so I needed one of those. To define a collection you must provide some names, throughput (read/write) capacity, and a partition key. The partition key is used to shard the data, and document IDs have to be unique within that partition.
Ok, I was all set to store my orders.
Step 2 – Create Azure Function
Right now, you can’t add custom code inside a Logic App. Microsoft recommends that you call out to an Azure Function if you want to do any funny business. In this example, I wanted to generate a unique ID per order. So, I needed a snippet of code that generated a GUID.
First up, I created a new Azure Functions app.
Next up, I had to create an actual function. I could start from scratch, or use a template. I chose the “generic webhook” template for C#.
This function is basic. All I do is generate a GUID, and return it back.
Step 3 – Create Service Bus Queue
When a big order came in, I wanted to route a message to a queue for further processing. Up front, I created a new Service Bus queue to hold these messages.
With my namespace created, I added a new queue named “largeorders.”
That was the final prerequisite for this demo. Next up, building the Logic App!
Step 4 – Create the Azure Logic App
First, I defined a new Logic App in the Azure Portal.
Here’s the first new thing I saw: an updated “getting started” view. I could choose a “trigger” to start off my Logic App, or, choose from a base scenario template.
I chose the trigger “when an HTTP request is received” and got an initial shape on my Logic App. Now, here’s where I saw the second cool update: instead of manually building a JSON schema, I could paste in a sample and generate one. Rad.
Step 5 – Call out to Azure Functions from Logic App
After I received a message, I wanted to add it to DocumentDB. But first, I need my unique order ID. Recall that our Azure Function generated one. I chose to “add an action” and selected “Azure Functions” from the list. As you can see below, once I chose that action, I could browse the Function I already created. Note that a new feature of Logic Apps allows you to build (Node.js) Functions from within the Logic App designer itself. I wanted a C# Function, so that’s why I did it outside this UI.
Step 6 – Insert record into DocumentDB from Logic App
Next up, I picked the “DocumentDB” activity, and chose the “create or update document” action.
Unfortunately, Logic Apps doesn’t (yet) look up connection strings for me. I opened another browser tab and navigated back to the DocumentDB “blade” to get my account name and authorization key. Once I did that, the Logic Apps Designer interrogated my account and let me pick my database and collection. After that, I built the payload to store the database. Notice that I built up a JSON message using values from the inbound HTTP message, and Azure Function. I also set the partition key to the “category” value from the inbound message.
What I have above won’t work. Why? In the present format, the “id” value is invalid. It would contain the whole JSON result from the Azure Function. There’s no way (yet) to grab a part of the JSON in the Designer, but there is a way in code. After switching to “code view”, I added [‘orderid’] reference to the right spot …
When I switched back to the Designer view, I saw “orderid” the mapped value.
That finished the first part of the flow. In the second part, I wanted to do different things based on the “category” of the purchased product.
Step 7 – Add conditional flows to Logic App
Microsoft recently added a “switch” statement condition to the palette, so I chose that. After choosing the data field to “switch” on, I added a pair of paths for different categories of product.
Inside the “electronics” switch path, I wanted to check and see if this was a big order. If so, I’d drop a message to a Service Bus queue. At the moment, Logic Apps doesn’t let me create variables (coming soon!), so I needed another way to generate the total order amount. Azure Functions to the rescue! From within the Logic Apps Designer, I once again chose the Azure Functions activity, but this time, selected “Create New Function.” Here, I passed in the full body of the initial message.
Inside the Function, I wrote some code that multiplied the quantity by the unit price.
We’re nearly done! After this Function, I added an if/else conditional that checked the Function’s result, and if it’s over 100, I send a message to the Azure Service Bus.
Step 8 – Send a response back to the Logic App caller
Whew. Last step to do? Send an HTTP response back to the caller, containing the auto-generated order ID. Ok, my entire flow was finished. It took in a message, added it to DocumentDB, and based on a set of conditions, also shipped it over the Azure Service Bus.
Step 9 – Test this thing!
I grabbed the URL for the Logic App from the topmost shape, and popped it into Postman. After sending in the JSON payload, I got back a GUID representing the generated order ID.
That’s great and all, but I needed to confirm everything worked! DocumentDB with a Function-generated ID? Check.
Service Bus message viewable via the Service Bus Explorer? Check.
The Logic Apps overview page on the Azure Portal also shows a “run history” and lets you inspect the success/failure of each step. This is new, and very useful.
All in all, this was pretty straightfoward. The Azure Portal still has some UI quirks, but a decent Azure dev can crank out the above flow in 20 minutes. That’s pretty powerful. Keep an eye on Logic Apps, and consider taking it for a spin!
nice job richard…. always superbly clear write ups!
Nice work! Do know that DocumentDB will generate the GUID for you if you don’t supply the id property? 🙂
But I digress. It’s great to see how to use Logic Apps & Functions together.
I did not! Good to know, Ryan.
Yup. If you submit a document (using one of their client SDKs) without an ID field a new GUID will be created for you. If you call the REST API directly, then this is not the case and you need to supply the value yourself.
I see. I should try it with Logic Apps. I’d assume communication is going over the REST API, so a value would be required.
Great blog post Richard !!
The only thing I found to cause a failure when tried this scenario is- create document elements should be in double quotes to generate valid JASON.
when I added double quotes it worked well. 🙂
“customerId”: ” 116 “,
First let me say great post!.You said there is no way yet in designer to grab the just the JSON value. Not sure when you wrote this but as of Feb. 2017 In search I type the word Compose. Then choose Data Operations Compose Service and then choose Data Operations – Compose JSON. In here you can enter your JSON schema. Then in all subsequent steps you will see all the field names from your JSON schema. Using these fields names in any of the next steps will pass only the JSON value. I used this to pass values to an on prem SQL DB. Worked great.
I see. So you’re saying I could have taken the response from the function and passed it through here to get typed values? Neat.
This is great stuff.
Really nice to do these little baby steps in Azure.
If you have more of these nice little gems to get acquainted with Azure please add some more on your blog.
Really great. (Took 4 hours of my weekend, but i learned something)
Thanks! I’ll see what I can do about more “gems” 😉
Great article. I followed the steps. I am getting an error when inserting the document. “partitionkey extracted from document doesn’t match the one specified in the header”. Any thoughts?
You’re definitely setting the “partition key” property on the activity?
Sir, I am also getting the same error in spite of setting the ‘partition key’ property as the id. Could you suggest a work around?