@SamVanhoutte
Azure App Service
Building workflows, using Logic Apps
Nice to meet you
Sam VANHOUTTECTO, CoditIntegration MVP – BizTalk V-TSP
http://blog.codit.eu@SamVanhoutte
International Focus - HQ in BE
2000 Belgium2004 France2013 Portugal
Microsoft Integration
2012 & 2013
Partner of the Year
FinalistApplication Integration
Community
Agenda – Azure App Service
• Context & positioning• The architecture• A technical deep(er) dive in API apps• Logic Apps: overview• My thoughts
µazure microservicesazure app service
positioning
API APPSEasily build and
consume APIs in the cloud
WEB APPSWeb apps that scale with
your business
LOGIC APPSAutomate business
process across SaaS and on-premises
MOBILE APPSBuild Mobile apps for
any device
App Service
the microservice architectural style is an approach to developing a single application as a suite of small services
the microservice architectural style is an approach to developing a single application as a suite of small services, each running in its own process and communicating with lightweight mechanisms, often an HTTP resource API.
the microservice architectural style is an approach to developing a single application as a suite of small services, each running in its own process and communicating with lightweight mechanisms, often an HTTP resource API. These services are built around business capabilities
the microservice architectural style is an approach to developing a single application as a suite of small services, each running in its own process and communicating with lightweight mechanisms, often an HTTP resource API. These services are built around business capabilities and independently deployable by fully automated deployment machinery.
the microservice architectural style is an approach to developing a single application as a suite of small services, each running in its own process and communicating with lightweight mechanisms, often an HTTP resource API. These services are built around business capabilities and independently deployable by fully automated deployment machinery. There is a bare minimum of centralized management of these services
the microservice architectural style is an approach to developing a single application as a suite of small services, each running in its own process and communicating with lightweight mechanisms, often an HTTP resource API. These services are built around business capabilities and independently deployable by fully automated deployment machinery. There is a bare minimum of centralized management of these services, which may be written in different programming languages and use different data storage technologies.
What is a MicroserviceQuoting http://martinfowler.com/articles/microservices.html
Mapping concepts to implementation
Application of small services
Own process, lightweight communication
Focused on business capabilities
Independently deployable
Minimized centralized management
Different programming languages & storage
Compose business app from gallery
Azure Websites & HTTP gateway
Gallery with codeless services
MS’s are separately upgradable
API Gateway (security, deployment…)
Web Sites (C#, node.js, PHP…)
ConceptApp Service
µ demobuilding an api-app
µarchitecture
VS/CLI
API & Connector Gallery (nuget-
based)
Azure Marketplace
Publish
SyncAzure Portal
Resource Group
Microservice G
ateway
other Azure services…
Apps• Siena• Web• Desktop• Etc.
3rd party SaaS
Source
Code API Apps
From gallery
Direct deployed
Workflow (also from gallery)
Workflow Definitions
Mobile (also from gallery)
Codeless API Apps
From gallery
Direct deployed
Custom Code
Regular code
On-premises
VS/CLI
Microservice Gallery (nuget-based)
Azure Marketplace
Publish
SyncAzure Portal
Resource Group
Microservice G
ateway
other Azure services…
Apps• Siena• Web• Desktop• Etc.
3rd party SaaS
Source
Code Microservices
From gallery
Direct deployed
Workflow (also from gallery)
Workflow Definitions
Mobile (also from gallery)
Codeless Microservices
From gallery
Direct deployed
Custom Code
Regular code
On-premises
Isolated storageShared config
Secure token store
Microservice Gateway
Runtime• Name resolution• Isolated storage• Shared config
Proxy• API logging• API access level• Transforming API definition
Identity Broker• AAD & social login• Identity brokerage• Secure token store
All• external
inbound calls• calls between
microservicgo through the gateway
Simplifying the picture
Gallery
compiled packages
Customer A
resource group
EDI
e-Invoicing
FlightBookingCustomer B
resource group
Twitter FB E-I
E-I Twitter EDI
µ demouse gateway api-app
Gateway capabilities
• Platform Services– Discovery– Logging– Billing– Automatic Updates– Isolated Storage
• Metadata– Easily generate client libraries– Powers Siena and workflow
Manual vs Automatic update (thoughts)
Platform assesses if upgrade is safe vs dangerous
Change type Detection Safe/DangerousBreaking change When major version of API app changes DangerousNon-breaking change When minor verison of API app changes SafeFootprint/billing change Dependencies / ARM template changes DangerousBilling / license change License property changes or billing changes DangerousBasic manifest change Description, Author, etc Safe
The App Service SDK : Storage
• Microsoft.Azure.AppService.ApiApps.Service.dll• Encrypted Isolated storage (out of the box, light weight)
Runtime.FromAppSettings().IsolatedStorage
Runtime.GetUrlAsync("TwitterSearch");Runtime.SignHttpRequest(new HttpRequestMessage());
JObject response = await Runtime.InvokeAsync("TwitterSearch", // microservice id "Twitter_Search", // operationId of the API method to call new Dictionary<string, string> { { "keyword", "seahawks" } }); // parameters
public interface IIsolatedStorage { Task<string[]> EnumerateAsync(); // Return null if storage does not exist. Task<Stream> OpenReadAsync(string name); Task<Stream> OpenWriteAsync(string name); Task DeleteAsync(string name); }
The App Service SDK : API dependencies
• Dependencies to other API apps
Runtime.GetUrlAsync("TwitterSearch");Runtime.SignHttpRequest(new HttpRequestMessage());
JObject response = await Runtime.InvokeAsync("TwitterSearch", // microservice id "Twitter_Search", // operationId of the API method to call new Dictionary<string, string> { { "keyword", "seahawks" } }); // parameters
The App Service SDK: Security & Identity
• Security & Identity– aad / facebook / google / twitter
• Use gateway login web page to get ZUMO token (mobile svcs)
• Get RAW tokens & claims for identity providersawait Runtime.FromAppSettings(Request).CurrentUser.GetRawTokenAsync("google");
Monitoring capabilities
• Monitor Running Applications– Installed applications– Number of calls to components– Network traffic including endpoints– Detailed performance data– Up time & crashes
• Component Author– Crash logs for components
µ democonsume an api-app
inside logic apps
LOGIC APPSAutomate business
process across SaaS and on-premises
New Logic Apps for easy automation
• No code designer for rapid creation
• Dozens of pre-built templates to get started
• Out of box support for popular SaaS and on-premises apps
• Use with custom API apps of your own
• BizTalk APIs for expert integration scenarios
All of the Azure-native capabilities
• Full audit logs of all management operations• Role-based access control • Deployment lifecycle with Resource Manager• Resource Management API + resource
PowerShell • On-prem support with next release of Azure
Pack
ARM
Same underlying engine…
Azure Resource Manager➔ 8 functions for basic referencing
and string functions
➔ Can only PUT resources into resource groups
➔ Auth must be through AAD
➔ Triggered manual through API
Azure Logic Apps➔ Over 50 functions from string
manipulations to math, to sets operations, to logical operators
➔ All HTTP operations supported on any arbitrary endpoint
➔ Supports many OAuth providers, AAD, Cert auth, or Basic auth
➔ 4 different ways to be triggered
{ "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json#", "contentVersion": "1.0.0.0", "variables": { "myWorkerSize": 0 }, "parameters": { "siteName": { "type": "string" }, "hostingPlanName": { "type": "string" }, "siteLocation": { "type": "string" }, "sku": { "type": "string", "allowedValues": [ "Free", "Shared", "Basic", "Standard" ], "defaultValue": "Free" }, "workerSize": { "type": "string", "allowedValues": [ "0", "1", "2" ], "defaultValue": "0" } }, "resources": [ { "name": "myplan1", "type": "Microsoft.Web/serverfarms", "apiVersion": "2014-04-01-preview", "location": "West US", "tags": { "dept": "test" }, "properties": { "Name": "myplan1", "sku": "Free", "workerSize": "[variables('myWorkerSize')]", "numberOfWorkers": 1 } }, { "name": "[parameters('siteName')]", "type": "Microsoft.Web/sites", "apiVersion": "2014-04-01-preview", "location": "[parameters('siteLocation')]", "tags": { "[concat('hidden-related:', resourceGroup().id, '/providers/Microsoft.Web/serverfarms/', parameters('hostingPlanName'))]": "Resource" }, "dependsOn": [ "[concat('Microsoft.Web/serverfarms/', parameters('hostingPlanName'))]" ], "properties": { "name": "[parameters('siteName')]", "serverFarm": "[parameters('hostingPlanName')]" }, "resources": [ { "name": "MSDeploy", "type": "Extensions", "apiVersion": "2014-04-01-preview", "dependsOn": [ "[concat('Microsoft.Web/Sites/', parameters('siteName'))]" ], "properties": { "packageUri": "https://auxmktplceprod.blob.core.windows.net/packages/ASPNETEmptySite.zip", "dbType": "None", "connectionString": "", "setParameters": { "Application Path": "[parameters('siteName')]" } } } ] } ]}
{ "$schema": "http://schema.management.azure.com/providers/Microsoft.Logic/schemas/2014-12-01-preview/workflowdefinition.json#", "contentVersion": "1.0.0.0", "parameters": { "keyword": { "defaultValue": "logicapps", "type": "string" } }, "triggers": { "twitterconnector": { "recurrence": { "frequency": "Hour", "interval": 1 }, "type": "ApiApp", "inputs": { "apiVersion": "2015-01-14", "host": { "id": "/subscriptions/423db32d-4f58-4220-961c-b59f14c962f1/resourcegroups/bpmdemo003/providers/Microsoft.AppService/apiapps/twitterconnector", "gateway": "https://bpmdemo003423db32d4f584220961cb59f14c962f1.azurewebsites.net" }, "operation": "TriggerOnNewTweet", "parameters": { "triggerId": "@workflow().name", "parameters": { "callbackUrl": "@accessKeys('default').primary.secretRunUri", "inputs": { "Keywords": "@parameters('keyword')" } } }, "authentication": { "type": "Raw", "scheme": "Zumo", "parameter": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJtc25hbWUiOiJFTUEuUmVzb3VyY2VQcm92aWRlciIsImZ1bGxyb3ciOiJhbGwiLCJ2ZXIiOiIzIiwidWlkIjoic2lkOjE0Mjc0NzcwNjcxNDAiLCJpc3MiOiJ1cm46bWljcm9zb2Z0OndpbmRvd3MtYXp1cmU6enVtbyIsImF1ZCI6InVybjptaWNyb3NvZnQ6d2luZG93cy1henVyZTp6dW1vIiwibmJmIjoxNDI3NDc3MDY5fQ.ihuWiXgyOpsG64Du6sAnRXxZGM_wtrJF0CJH0y-Rxfs" } }, "conditions": [ { "expression": "@bool('false')" } ] } }, "actions": { "dropboxconnector": { "type": "ApiApp", "inputs": { "apiVersion": "2015-01-14", "host": { "id": "/subscriptions/423db32d-4f58-4220-961c-b59f14c962f1/resourcegroups/bpmdemo003/providers/Microsoft.AppService/apiapps/dropboxconnector", "gateway": "https://bpmdemo003423db32d4f584220961cb59f14c962f1.azurewebsites.net" }, "operation": "UploadFile", "parameters": { "FilePath": "@concat('tweets/logicapps/',triggers().outputs.body.Tweet_ID)", "content": { "Content": "@triggers().outputs.body.TweetText", "ContentTransferEncoding": "None" }, "overwrite": true }, "authentication": { "type": "Raw", "scheme": "Zumo", "parameter": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJtc25hbWUiOiJFTUEuUmVzb3VyY2VQcm92aWRlciIsImZ1bGxyb3ciOiJhbGwiLCJ2ZXIiOiIzIiwidWlkIjoic2lkOjE0Mjc0NzcwNjcxNDAiLCJpc3MiOiJ1cm46bWljcm9zb2Z0OndpbmRvd3MtYXp1cmU6enVtbyIsImF1ZCI6InVybjptaWNyb3NvZnQ6d2luZG93cy1henVyZTp6dW1vIiwibmJmIjoxNDI3NDc3MDY5fQ.ihuWiXgyOpsG64Du6sAnRXxZGM_wtrJF0CJH0y-Rxfs" } }, "conditions": [ ] } }, "outputs": { }}
logic apps workflow functions
Collection (first, contains, length, intersection, take, skip…)
String (concat, substring, replace)
Logical (equals, less, greater, lessOrEquals, and, or, not…)
Conversion (int, string, float, bool, coalesce, base64)
Math (add, sub, mul, div, mod, min, max, range)
Date (utcnow, addseconds, addminutes, addhours, adddays)
µ demobuilding a logic app
Dependencies & sequencing
Implicitly whenever you reference the output of an action you’ll depend on that action executing first
Explicit “dependsOn” conditionyou can mark certain actions to run only after previous ones have completed“dependsOn” : “twitterconnector”
Explicit “expression” conditiona complex function that evaluates properties of other actions“expression” : “@equals(actions(‘twitterconnector’).code, ‘InternalServerError’)”
Triggering a Logic app
Manual
RecurrenceAPI App TriggerAPI Polling
200: run202: wait
trigger state
WebHook
POST{ “outputs”: { “par”: 20 }}
• Loop a single action over a list of items• Runs the action N times• You can get at all of the statuses for each action
• Tip: when you have multiple collections use:
Repeating
"repeat" : "@range(0,length(body('connector1')))“"inputs" : "@concat(body('connector1')[repeatItem()], body('connector2')[repeatItem()])"
Conditionals
• Logic on a trigger or action– For triggers conditionals are post-conditions– For actions conditionals are pre-conditions
• You can do conditionals inside of repeats to perform as a filter
@parameters('hasSpecialAction') parameters
@greater(actions('a1').output.value, parameters('thrshold'))
@or(greater(actions('a1').output.value,parameters('thrshold')),less(actions('a1').output.value, 100)) or
@equals(length(actions('a1').outputs.errors), 0)) ex.handling
@not(equals(triggers().outputs.body.articleId, triggers().previous.outputs.body.articleId)) value change
Parameters
• Re-using values, or even complex objects, throughout the definition, which makes it easier to comprehend
• Separate out config from the definition itself, making sharing easy, as well as across different environments.
Dev Workflow Prod Workflow
DefinitionDeclares parameters
Uri: @parameters (‘endpoint’)
Definition(identical)
Declares same parameters
Uri: @parameters (‘endpoint’)
ParametersProvides DEV config
Endpoint : “http://int.mysite.ne
t”
ParametersProvides PROD
config
Endpoint : “http://mysite.net”
Messages
• Large message support is built-in (<100 MB) • To handle binary blobs of data you can:
– 1. Externalize state (save it to Azure storage)– 2. Base64 encode it and return it directly in the
workflow (workflows are JSON)
• All messages are archived– Retention period depends on the App Service plan
Debugging tips
• Try calling the API App directly:– POST {gatewayURI}/api/service/invoke/{api app
name}/{operation name}?api-version=2015-01-14– x-zumo-auth : {your token}– This may be a faster way to iterate if you are seeing failures
• Use requestb.in to debug triggers – you can inspect all incoming requests
• Enable logging for the Web app hosting the API App• Cancel a Run if it is failed
µ demoend to end travel app
my initial thoughts
µThe challenges
Right Messaging Engine for
integration?
Complex scenarios Granularity
Tools & management Billing model
µWhat I love about it
Partner eco-system
Small unit deployment Scalability
ExtensibilityDeployment
modelOn prem
symmetry
Provide your instant session feedback!
41
To help us in our journey to host the best developer conference in Europe, we want your feedback.
Rate all sessions via the Techorama schedule page!
More information on http://www.techorama.be/techorama-2015/feedback/
http://techorama2015.sched.org
#techorama
42
A big thank you to our partners
Gold Partners
Silver & Social Partners
Platinum Partners