BizTalk Migrator Dependency - Azure Templates

  • 1
  • 2
  • 3

1.0.0 | Updated: 28 Sep 2021

Downloads:

424

Downloads of v 1.0.0:

112

Software Author(s):

  • Microsoft

  • 1
  • 2
  • 3
BizTalk Migrator Dependency - Azure Templates 1.0.0

  • 1
  • 2
  • 3

All Checks are Passing

3 Passing Tests


Validation Testing Passed


Verification Testing Passed

Details

Scan Testing Successful:

No detections found in any package files

Details
Learn More

Deployment Method: Individual Install, Upgrade, & Uninstall

To install BizTalk Migrator Dependency - Azure Templates, run the following command from the command line or from PowerShell:

>

To upgrade BizTalk Migrator Dependency - Azure Templates, run the following command from the command line or from PowerShell:

>

To uninstall BizTalk Migrator Dependency - Azure Templates, run the following command from the command line or from PowerShell:

>

Deployment Method:

📝 NOTE: This applies to both open source and commercial editions of Chocolatey.

1. Enter Your Internal Repository Url

(this should look similar to https://community.chocolatey.org/api/v2/)


2. Setup Your Environment

1. Ensure you are set for organizational deployment

Please see the organizational deployment guide

2. Get the package into your environment

  • Open Source or Commercial:
    • Proxy Repository - Create a proxy nuget repository on Nexus, Artifactory Pro, or a proxy Chocolatey repository on ProGet. Point your upstream to https://community.chocolatey.org/api/v2/. Packages cache on first access automatically. Make sure your choco clients are using your proxy repository as a source and NOT the default community repository. See source command for more information.
    • You can also just download the package and push it to a repository Download

3. Copy Your Script

choco upgrade biztalkmigrator-azure -y --source="'INTERNAL REPO URL'" [other options]

See options you can pass to upgrade.

See best practices for scripting.

Add this to a PowerShell script or use a Batch script with tools and in places where you are calling directly to Chocolatey. If you are integrating, keep in mind enhanced exit codes.

If you do use a PowerShell script, use the following to ensure bad exit codes are shown as failures:


choco upgrade biztalkmigrator-azure -y --source="'INTERNAL REPO URL'" 
$exitCode = $LASTEXITCODE

Write-Verbose "Exit code was $exitCode"
$validExitCodes = @(0, 1605, 1614, 1641, 3010)
if ($validExitCodes -contains $exitCode) {
  Exit 0
}

Exit $exitCode

- name: Install biztalkmigrator-azure
  win_chocolatey:
    name: biztalkmigrator-azure
    version: '1.0.0'
    source: INTERNAL REPO URL
    state: present

See docs at https://docs.ansible.com/ansible/latest/modules/win_chocolatey_module.html.


chocolatey_package 'biztalkmigrator-azure' do
  action    :install
  source   'INTERNAL REPO URL'
  version  '1.0.0'
end

See docs at https://docs.chef.io/resource_chocolatey_package.html.


cChocoPackageInstaller biztalkmigrator-azure
{
    Name     = "biztalkmigrator-azure"
    Version  = "1.0.0"
    Source   = "INTERNAL REPO URL"
}

Requires cChoco DSC Resource. See docs at https://github.com/chocolatey/cChoco.


package { 'biztalkmigrator-azure':
  ensure   => '1.0.0',
  provider => 'chocolatey',
  source   => 'INTERNAL REPO URL',
}

Requires Puppet Chocolatey Provider module. See docs at https://forge.puppet.com/puppetlabs/chocolatey.


4. If applicable - Chocolatey configuration/installation

See infrastructure management matrix for Chocolatey configuration elements and examples.

This package was approved by moderator TheCakeIsNaOH on 28 Sep 2021.

Description

Azure templates to migrate BizTalk applications to Microsoft Azure Integration Services.


tools\LICENSE.txt
    MIT License

    Copyright (c) Microsoft Corporation.

    Permission is hereby granted, free of charge, to any person obtaining a copy
    of this software and associated documentation files (the "Software"), to deal
    in the Software without restriction, including without limitation the rights
    to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
    copies of the Software, and to permit persons to whom the Software is
    furnished to do so, subject to the following conditions:

    The above copyright notice and this permission notice shall be included in all
    copies or substantial portions of the Software.

    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
    AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
    SOFTWARE
tools\templates\application\applicationgroup\applicationgroup.dev.parameters.json.liquid
 
tools\templates\application\applicationgroup\applicationgroup.json.liquid
 
tools\templates\application\applicationgroup\applicationgroup.prod.parameters.json.liquid
 
tools\templates\application\applicationgroup\Deploy-10-ApplicationGroup.ps1.liquid
 
tools\templates\application\applicationgroup\New-ApplicationGroup.ps1.liquid
 
tools\templates\application\applicationgroup\Remove-ApplicationGroup.ps1.liquid
 
tools\templates\application\applicationgroup\TearDown-10-ApplicationGroup.ps1.liquid
 
tools\templates\application\config\configurationentries\configurationentry.appcfg.dev.psparameters.json.liquid
 
tools\templates\application\config\configurationentries\configurationentry.appcfg.prod.psparameters.json.liquid
 
tools\templates\application\config\configurationentries\Deploy-105-ConfigurationEntry-AppConfig.ps1.liquid
 
tools\templates\application\config\configurationentries\New-ConfigurationEntry-AppConfig.ps1
<#
.SYNOPSIS
Creates a configuration entry in application configuration.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key for the configuration item.

.PARAMETER value
The value for the configuration item

.PARAMETER type
The type assigned to the configuration item.

.PARAMETER label
The label for the configuration item.

.PARAMETER tags
The tags to apply to the configuration item.

.EXAMPLE
.\New-ConfigurationEntry-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -value "{ ""samplekey"": ""samplevalue"" }" -type configType -label "sample label"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $value,
    [parameter(Mandatory = $true)]
    [string] $type,
    [parameter(Mandatory = $true)]
    [string] $label,
    [parameter(Mandatory = $false)]
    [string[]] $tags = ""
)

Write-Host "Deploying the configuraton entry key $key"

az appconfig kv set --name $configStoreName --key $key --value $value --content-type $type --label $label --tags $tags --yes 

Write-Host "Deployment complete for the configuration entry key $key"
tools\templates\application\config\configurationentries\Remove-ConfigurationEntry-AppConfig.ps1
<#
.SYNOPSIS
Removes a configuration entry from the application configuration.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key of the item remove from the configuration store.

.PARAMETER label
The label of the item remove from the configuration store.

.EXAMPLE
.\TearDown-100-ConfigurationEntry-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -label "SampleLabel"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $label
)

Write-Host "Removing the configuration entry for key $key"

az appconfig kv delete --name $configStoreName --key $key --label $label --yes

Write-Host "Removed the configuration entry for key $key"
tools\templates\application\config\configurationentries\TearDown-105-ConfigurationEntry-AppConfig.ps1.liquid
 
tools\templates\application\config\routingproperties\route\Deploy-105-RoutingProperties-AppConfig.ps1.liquid
 
tools\templates\application\config\routingproperties\route\New-RoutingProperties-AppConfig.ps1
<#
.SYNOPSIS
Creates routing properties in app config.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key for the configuration item.

.PARAMETER value
The value for the configuration item

.PARAMETER type
The type assigned to the configuration item.

.PARAMETER label
The label for the configuration item.

.PARAMETER tags
The tags to apply to the configuration item.

.EXAMPLE
.\New-RoutingProperties-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -value "{ ""samplekey"": ""samplevalue"" }" -type configType -label "sample label"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $value,
    [parameter(Mandatory = $true)]
    [string] $type,
    [parameter(Mandatory = $true)]
    [string] $label,
    [parameter(Mandatory = $false)]
    [string[]] $tags = ""
)

Write-Host "Deploying routing properties with the key $key"

az appconfig kv set --name $configStoreName --key $key --value $value --content-type $type --label $label --tags $tags --yes 

Write-Host "Deployment complete routing properties with the key $key"
tools\templates\application\config\routingproperties\route\Remove-RoutingProperties-AppConfig.ps1
<#
.SYNOPSIS
Removes routing properties from app config.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key of the item remove from the configuration store.

.PARAMETER label
The label of the item remove from the configuration store.

.EXAMPLE
.\TearDown-100-RoutingProperties-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -label "SampleLabel"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $label
)

Write-Host "Removing routing properties with the key $key"

az appconfig kv delete --name $configStoreName --key $key --label $label --yes

Write-Host "Removed routing properties with the key $key"
tools\templates\application\config\routingproperties\route\routingproperties.appcfg.dev.psparameters.json.liquid
 
tools\templates\application\config\routingproperties\route\routingproperties.appcfg.prod.psparameters.json.liquid
 
tools\templates\application\config\routingproperties\route\TearDown-105-RoutingProperties-AppConfig.ps1.liquid
 
tools\templates\application\config\routingproperties\schema\Deploy-105-RoutingProperties-AppConfig.ps1.liquid
 
tools\templates\application\config\routingproperties\schema\New-RoutingProperties-AppConfig.ps1
<#
.SYNOPSIS
Creates routing properties in app config.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key for the configuration item.

.PARAMETER value
The value for the configuration item

.PARAMETER type
The type assigned to the configuration item.

.PARAMETER label
The label for the configuration item.

.PARAMETER tags
The tags to apply to the configuration item.

.EXAMPLE
.\New-RoutingProperties-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -value "{ ""samplekey"": ""samplevalue"" }" -type configType -label "sample label"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $value,
    [parameter(Mandatory = $true)]
    [string] $type,
    [parameter(Mandatory = $true)]
    [string] $label,
    [parameter(Mandatory = $false)]
    [string[]] $tags = ""
)

Write-Host "Deploying the routing properties for key $key"

az appconfig kv set --name $configStoreName --key $key --value $value --content-type $type --label $label --tags $tags --yes 

Write-Host "Deployment complete for the routing properties for key $key"
tools\templates\application\config\routingproperties\schema\Remove-RoutingProperties-AppConfig.ps1
<#
.SYNOPSIS
Removes routing properties from app config.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key of the item remove from the configuration store.

.PARAMETER label
The label of the item remove from the configuration store.

.EXAMPLE
.\TearDown-100-RoutingProperties-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -label "SampleLabel"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $label
)

Write-Host "Removing the routing properties for key $key"

az appconfig kv delete --name $configStoreName --key $key --label $label --yes

Write-Host "Removed routing properties for the key $key"
tools\templates\application\config\routingproperties\schema\routingproperties.appcfg.dev.psparameters.json.liquid
 
tools\templates\application\config\routingproperties\schema\routingproperties.appcfg.prod.psparameters.json.liquid
 
tools\templates\application\config\routingproperties\schema\TearDown-105-RoutingProperties-AppConfig.ps1.liquid
 
tools\templates\application\config\routingslips\Deploy-105-RoutingSlip-AppConfig.ps1.liquid
 
tools\templates\application\config\routingslips\New-RoutingSlip-AppConfig.ps1
<#
.SYNOPSIS
Creates routing slip configuration in application configuration.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key for the configuration item.

.PARAMETER value
The value for the configuration item

.PARAMETER type
The type assigned to the configuration item.

.PARAMETER label
The label for the configuration item.

.PARAMETER tags
The tags to apply to the configuration item.

.EXAMPLE
.\New-RoutingSlip-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -value "{ ""samplekey"": ""samplevalue"" }" -type configType -label "sample label"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $value,
    [parameter(Mandatory = $true)]
    [string] $type,
    [parameter(Mandatory = $true)]
    [string] $label,
    [parameter(Mandatory = $false)]
    [string[]] $tags = ""
)

Write-Host "Deploying the routing slip configuration key $key"

az appconfig kv set --name $configStoreName --key $key --value $value --content-type $type --label $label --tags $tags --yes 

Write-Host "Deployment complete for the routing slip configuration key $key"
tools\templates\application\config\routingslips\Remove-RoutingSlip-AppConfig.ps1
<#
.SYNOPSIS
Removes routing slip configuration from the application configuration.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER configStoreName
The name of the application configuration store.

.PARAMETER key
The key of the item remove from the configuration store.

.PARAMETER label
The label of the item remove from the configuration store.

.EXAMPLE
.\TearDown-100-RoutingSlip-AppConfig.ps1 -configStoreName "appcfg-aimroutestore-dev" -key "SampleConfigKey" -label "SampleLabel"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $configStoreName,
    [parameter(Mandatory = $true)]
    [string] $key,
    [parameter(Mandatory = $true)]
    [string] $label
)

Write-Host "Removing the routing slip configuration for key $key"

az appconfig kv delete --name $configStoreName --key $key --label $label --yes

Write-Host "Removed routing slip configuration for key $key"
tools\templates\application\config\routingslips\routingslip.appcfg.dev.psparameters.json.liquid
 
tools\templates\application\config\routingslips\routingslip.appcfg.prod.psparameters.json.liquid
 
tools\templates\application\config\routingslips\TearDown-105-RoutingSlip-AppConfig.ps1.liquid
 
tools\templates\application\standard\application.logic.dev.parameters.json.liquid
 
tools\templates\application\standard\application.logic.prod.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\.funcignore
 
tools\templates\application\standard\application.logic.workflows\.vscode\extensions.json
{
  "recommendations": [
    "ms-azuretools.vscode-azurefunctions"
  ]
}
tools\templates\application\standard\application.logic.workflows\.vscode\launch.json
{
  "version": "0.2.0",
  "configurations": [
    {
      "name": "Attach to .NET Functions",
      "type": "coreclr",
      "request": "attach",
      "processId": "${command:azureLogicAppsStandard.pickProcess}"
    }
  ]
}
tools\templates\application\standard\application.logic.workflows\.vscode\settings.json
{
  "azureLogicAppsStandard.deploySubpath": ".",
  "azureLogicAppsStandard.projectLanguage": "JavaScript",
  "azureLogicAppsStandard.projectRuntime": "~3",
  "debug.internalConsoleOptions": "neverOpen"
}
tools\templates\application\standard\application.logic.workflows\.vscode\tasks.json
{
  "version": "2.0.0",
  "tasks": [
    {
      "label": "generateDebugSymbols",
      "command": "dotnet",
      "args": [
        "${input:getDebugSymbolDll}"
      ],
      "type": "process",
      "problemMatcher": "$msCompile"
    },
    {
      "type": "func",
      "command": "host start",
      "problemMatcher": "$func-watch",
      "isBackground": true
    }
  ],
  "inputs": [
    {
      "id": "getDebugSymbolDll",
      "type": "command",
      "command": "azureLogicAppsStandard.getDebugSymbolDll"
    }
  ]
}
tools\templates\application\standard\application.logic.workflows\base.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\base.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\base.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\base.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filereceiveadapter\filereceiveadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filereceiveadapter\filereceiveadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filereceiveadapter\filereceiveadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filereceiveadapter\filereceiveadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filereceiveadapter\filereceiveadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filereceiveadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filesendadapter\filesendadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filesendadapter\filesendadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filesendadapter\filesendadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filesendadapter\filesendadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filesendadapter\filesendadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\filesendadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpreceiveadapter\ftpreceiveadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpreceiveadapter\ftpreceiveadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpreceiveadapter\ftpreceiveadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpreceiveadapter\ftpreceiveadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpreceiveadapter\ftpreceiveadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpreceiveadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpsendadapter\ftpsendadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpsendadapter\ftpsendadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpsendadapter\ftpsendadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpsendadapter\ftpsendadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpsendadapter\ftpsendadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\ftpsendadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\host.json
{
  "version": "2.0",
  "extensionBundle": {
    "id": "Microsoft.Azure.Functions.ExtensionBundle.Workflows",
    "version": "[1.*, 2.0.0)"
  }
}
tools\templates\application\standard\application.logic.workflows\httpreceiveadapter\httpreceiveadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpreceiveadapter\httpreceiveadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpreceiveadapter\httpreceiveadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpreceiveadapter\httpreceiveadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpreceiveadapter\httpreceiveadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpreceiveadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpsendadapter\httpsendadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpsendadapter\httpsendadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpsendadapter\httpsendadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpsendadapter\httpsendadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpsendadapter\httpsendadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\httpsendadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpreceiveadapter\sftpreceiveadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpreceiveadapter\sftpreceiveadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpreceiveadapter\sftpreceiveadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpreceiveadapter\sftpreceiveadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpreceiveadapter\sftpreceiveadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpreceiveadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpsendadapter\sftpsendadapter.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpsendadapter\sftpsendadapter.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpsendadapter\sftpsendadapter.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpsendadapter\sftpsendadapter.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpsendadapter\sftpsendadapter.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\sftpsendadapter\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\topicsubscriber\topicsubscriber.appsettings.json.liquid
 
tools\templates\application\standard\application.logic.workflows\topicsubscriber\topicsubscriber.appsettings.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\topicsubscriber\topicsubscriber.connections.json.liquid
 
tools\templates\application\standard\application.logic.workflows\topicsubscriber\topicsubscriber.parameters.json.liquid
 
tools\templates\application\standard\application.logic.workflows\topicsubscriber\topicsubscriber.parameters.local.json.liquid
 
tools\templates\application\standard\application.logic.workflows\topicsubscriber\workflow.json.liquid
 
tools\templates\application\standard\application.logic.workflows\workflow-designtime\host.json
{
  "version": "2.0",
  "extensionBundle": {
    "id": "Microsoft.Azure.Functions.ExtensionBundle.Workflows",
    "version": "[1.*, 2.0.0)"
  },
  "extensions": {
    "workflow": {
      "settings": {
        "Runtime.WorkflowOperationDiscoveryHostMode": "true"
      }
    }
  }
}
tools\templates\application\standard\application.logic.workflows\workflow-designtime\local.settings.json
{
  "IsEncrypted": false,
  "Values": {
    "AzureWebJobsSecretStorageType": "Files",
    "FUNCTIONS_WORKER_RUNTIME": "node"
  }
}
tools\templates\application\standard\base.application.logic.json.liquid
 
tools\templates\application\standard\Deploy-105-Application-LogicApp.ps1.liquid
 
tools\templates\application\standard\Deploy-110-Application-LogicApp-Configuration.ps1.liquid
 
tools\templates\application\standard\Deploy-115-Application-LogicApp-Workflows.ps1.liquid
 
tools\templates\application\standard\Deploy-120-Application-ClearUrlCache.ps1.liquid
 
tools\templates\application\standard\New-Application-ClearUrlCache.ps1
<#
.SYNOPSIS
Clears the Url Cache for a given Workflow in this Logic App.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the Logic App is located.

.PARAMETER resourceName
Name of the Logic App.

.PARAMETER workflowName
Name of the Workflow.

.PARAMETER apimInstanceName
Name of the APIM instance used to clear the cache.

.PARAMETER keyVaultName
The name of the key vault store.

.PARAMETER keyVaultApimSubscriptionSecretName
The name of secret in key vault which stores the apim subscription.

.EXAMPLE
.\New-Application-ClearUrlCache.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -resourceName "logic-application-dev-xxxxx" -workflowName "workflowname" -apimInstanceName "apim-aimmsgbussvc-dev-xxxxx" -keyVaultName "kv-aimrstore-dev-xxxxx" -keyVaultApimSubscriptionSecretName "aim-apim-subscriptionkey-unlimited"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName,
	[parameter(Mandatory = $true)]
    [string] $workflowName,
    [parameter(Mandatory = $true)]    
    [string] $apimInstanceName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName
)

Write-Host "Getting the subscription from Key Vault for APIM"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

$apimBaseUrl = "https://$apimInstanceName.azure-api.net/aimroutingmanager/standardlogicappcallbackurl/$resourceGroupName/$resourceName"
Write-Host "Using base url: $apimBaseUrl"

Write-Host "Clearing cache for Workflow"

Write-Host "$workflowName"
az rest --method get --url "$apimBaseUrl/$workflowName?clearCache=true" --headers "Ocp-Apim-Subscription-Key=$apimSubscriptionKey" --skip-authorization-header --output none

Write-Host "Cache Clearing complete"
tools\templates\application\standard\New-Application-LogicApp-Configuration.ps1
<#
.SYNOPSIS
Creates the Application Logic App Configuration.
This script will merge the individual workflow config files into single files,
prior to the workflows app being uploaded to the Logic App in Azure.
Note that if you want to open this Logic App project in VS Code,
you need to run this script first.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER workflowFolder
Location of the folder containing the Logic App Workflows.

.EXAMPLE
.\New-Application-LogicApp-Configuration.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -resourceName "logic-application-dev-xxxxx" -workflowFolder "$PSScriptRoot\application.logic.workflows"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName,	
	[parameter(Mandatory = $true)]
    [string] $workflowFolder
)

Write-Host "Merging Parameters Files"

# Check if we've already done a merge
if (!(Test-Path -Path "$workflowFolder\parameters.json" -PathType Leaf))
{
	# We're using PowerShell Hashtables to merge the Json files.
	# We're not using Newtonsoft's Json.NET JObject.Merge() option here
	# as we can't guarantee the version of PowerShell being used has access to Json.NET.
	$mergedParameters = [ordered]@{}

	Get-ChildItem "$workflowFolder\*.parameters.json" -Recurse | 
	Foreach-Object {
		$parameterFile = Get-Content $_.FullName -Raw | ConvertFrom-Json -AsHashtable
		
		# Remove any duplicate property names - have to do this or the merge will fail
		# as we'll be generating invalid Json
		foreach ($jsonPropertyName in $parameterFile.Keys) {
			if ($mergedParameters.Contains($jsonPropertyName)) {
				$mergedParameters.Remove($jsonPropertyName);
			}
		}
		
		# Union the two hashtables together
		$mergedParameters = $mergedParameters + $parameterFile;
		
		# Delete this file
		Remove-Item -Path $_.FullName
	}

	# Output a new merged parameters file
	ConvertTo-Json $mergedParameters -Depth 10 | Set-Content "$workflowFolder\parameters.json"
}
else
{
	Write-Host "Parameters File has already been merged - no work to do"	
}

Write-Host "Parameters File Merging Complete"

Write-Host "Merging Local Parameters Files"

# Check if we've already done a merge
if (!(Test-Path -Path "$workflowFolder\parameters.local.json" -PathType Leaf))
{
	# We're using PowerShell Hashtables to merge the Json files.
	# We're not using Newtonsoft's Json.NET JObject.Merge() option here
	# as we can't guarantee the version of PowerShell being used has access to Json.NET.
	$mergedLocalParameters = [ordered]@{}

	Get-ChildItem "$workflowFolder\*.parameters.local.json" -Recurse | 
	Foreach-Object {
		$localParameterFile = Get-Content $_.FullName -Raw | ConvertFrom-Json -AsHashtable
		
		# Remove any duplicate property names - have to do this or the merge will fail
		# as we'll be generating invalid Json
		foreach ($jsonPropertyName in $localParameterFile.Keys) {
			if ($mergedLocalParameters.Contains($jsonPropertyName)) {
				$mergedLocalParameters.Remove($jsonPropertyName);
			}
		}
		
		# Union the two hashtables together
		$mergedLocalParameters = $mergedLocalParameters + $localParameterFile;
		
		# Delete this file
		Remove-Item -Path $_.FullName
	}

	# Output a new merged local parameters file
	ConvertTo-Json $mergedLocalParameters -Depth 10 | Set-Content "$workflowFolder\parameters.local.json"
}
else
{
	Write-Host "Local Parameters File has already been merged - no work to do"	
}

Write-Host "Local Parameters File Merging Complete"

Write-Host "Merging Connections Files"

# Check if we've already done a merge
if (!(Test-Path -Path "$workflowFolder\connections.json" -PathType Leaf))
{
	# We're using PowerShell Hashtables to merge the Json files.
	# We're not using Newtonsoft's Json.NET JObject.Merge() option here
	# as we can't guarantee the version of PowerShell being used has access to Json.NET.
	$serviceProviderConnections = [ordered]@{}
	$managedApiConnections = [ordered]@{}

	Get-ChildItem "$PSScriptRoot\*.connections.json" -Recurse | 
	Foreach-Object {
		$connectionsFile = Get-Content $_.FullName -Raw | ConvertFrom-Json -AsHashtable
		
		if ($connectionsFile.Contains("serviceProviderConnections"))
		{
			$tempServiceProviderConnections = $connectionsFile["serviceProviderConnections"]
			foreach ($serviceProviderConnectionKey in $tempServiceProviderConnections.Keys) {
				if (-Not $serviceProviderConnections.Contains($serviceProviderConnectionKey))
				{
					$serviceProviderConnections[$serviceProviderConnectionKey] = $tempServiceProviderConnections[$serviceProviderConnectionKey]
				}
			}
		}
		
		if ($connectionsFile.Contains("managedApiConnections"))
		{
			$tempManagedApiConnections = $connectionsFile["managedApiConnections"]
			foreach ($managedApiConnectionKey in $tempManagedApiConnections.Keys) {
				if (-Not $managedApiConnections.Contains($managedApiConnectionKey))
				{
					$managedApiConnections[$managedApiConnectionKey] = $tempManagedApiConnections[$managedApiConnectionKey]
				}
			}
		}
		
		# Delete this file
		Remove-Item -Path $_.FullName
	}

	$connections = [ordered]@{}
	$connections["serviceProviderConnections"] = $serviceProviderConnections
	$connections["managedApiConnections"] = $managedApiConnections

	ConvertTo-Json $connections -Depth 10 | Set-Content "$workflowFolder\connections.json"
}
else
{
	Write-Host "Connections File has already been merged - no work to do"	
}

Write-Host "Connections File Merging Complete"

Write-Host "Merging Local AppSettings Files"

# Check if we've already done a merge
if (!(Test-Path -Path "$workflowFolder\local.settings.json" -PathType Leaf))
{
	# We're using PowerShell Hashtables to merge the Json files.
	# We're not using Newtonsoft's Json.NET JObject.Merge() option here
	# as we can't guarantee the version of PowerShell being used has access to Json.NET.
	$mergedLocalAppSettings = [ordered]@{}

	Get-ChildItem "$workflowFolder\*.appsettings.local.json" -Recurse | 
	Foreach-Object {
		$localAppSettingsFile = Get-Content $_.FullName -Raw | ConvertFrom-Json -AsHashtable
		
		# Remove any duplicate property names - have to do this or the merge will fail
		# as we'll be generating invalid Json
		foreach ($jsonPropertyName in $localAppSettingsFile.Keys) {
			if ($mergedLocalAppSettings.Contains($jsonPropertyName)) {
				$mergedLocalAppSettings.Remove($jsonPropertyName);
			}
		}
		
		# Union the two hashtables together
		$mergedLocalAppSettings = $mergedLocalAppSettings + $localAppSettingsFile;
		
		# Delete this file
		Remove-Item -Path $_.FullName
	}

	# Create Local App Settings format
	$localAppSettings = [ordered]@{}
	$localAppSettings["IsEncrypted"] = $false
	$localAppSettings["Values"] = $mergedLocalAppSettings

	# Output a new merged local appsettings file
	ConvertTo-Json $localAppSettings -Depth 10 | Set-Content "$workflowFolder\local.settings.json"
}
else
{
	Write-Host "Local App Settings File has already been merged - no work to do"	
}

Write-Host "Local AppSettings File Merging Complete"
tools\templates\application\standard\New-Application-LogicApp-Workflows.ps1
<#
.SYNOPSIS
Creates the Application Logic App Workflows.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER workflowFolder
Location of the folder containing the Logic App Workflows.

.EXAMPLE
.\New-Application-LogicApp-Workflows.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -resourceName "logic-application-dev-xxxxx" -workflowFolder "$PSScriptRoot\application.logic.workflows"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName,	
	[parameter(Mandatory = $true)]
    [string] $workflowFolder
)

Write-Host "Creating a ZIP file from the workflow folder"
# create the zip
$zipFile = "$workflowFolder.zip"
if(Test-path $zipFile) {Remove-item $zipFile}
Add-Type -assembly "system.io.compression.filesystem"
[io.compression.zipfile]::CreateFromDirectory($workflowFolder, $zipFile)

Write-Host "Zip File creation complete"

Write-Host "Uploading the application logic app zip package $zipFile"

if (!(Test-Path $zipFile)) {
    throw "Zip file $zipFile doesn't exist, unable to upload"
}

az logicapp deployment source config-zip --resource-group $resourceGroupName --name $resourceName --src "$zipFile"

Write-Host "Upload complete"
tools\templates\application\standard\New-Application-LogicApp.ps1
<#
.SYNOPSIS
Creates the Application Logic App.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER keyVaultName
The name of the key vault store.

.PARAMETER keyVaultApimSubscriptionSecretName
The name of secret in key vault which stores the apim subscription.

.PARAMETER workflowFolder
Location of the folder containing the Logic App Workflows.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-Application-LogicApp.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -resourceName "logic-application-dev-xxxxx" -templateFile "$PSScriptRoot\application.logic.json" -templateParameterFile "$PSScriptRoot\application.logicapp.dev.parameters.json" -keyVaultName "kv-aimrstore-dev-xxxxx" -keyVaultApimSubscriptionSecretName "aim-apim-subscriptionkey-unlimited" -workflowFolder "$PSScriptRoot\application.logic.workflows" -deploymentName "application.logicapp.uksouth.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName,	
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName,
	[parameter(Mandatory = $true)]
    [string] $workflowFolder,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Getting the subscription from Key Vault for APIM"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

Write-Host "Merging AppSetting Files"

# We're using PowerShell Arrays to merge the Json AppSettings files.
# We're not using Newtonsoft's Json.NET JObject.Merge() option here
# as we can't guarantee the version of PowerShell being used has access to Json.NET.
$mergedAppSettings = @()

Get-ChildItem "$workflowFolder\*.appsettings.json" -Recurse | 
Foreach-Object {
    $appSettingsFile = Get-Content $_.FullName -Raw | ConvertFrom-Json -AsHashtable
	
	# Union the two arrays together
	$mergedAppSettings += $appSettingsFile;
	
	# Delete this file
	Remove-Item -Path $_.FullName
}

$templatePath = Split-Path -Path $templateFile
$templateFileName = Split-Path -Path $templateFile -Leaf
$baseTemplateFile = "$templatePath\base.$templateFileName"

# Load in the original template, and add in the updated AppSettings
if (Test-Path -Path $baseTemplateFile -PathType Leaf) {
	$applicationTemplate = Get-Content $baseTemplateFile -Raw | ConvertFrom-Json
	
	# Look for the web site resource
	foreach ($resource in $applicationTemplate.resources) {
			if ($resource.type -eq "Microsoft.Web/sites") {
				$resource.properties.siteConfig.appSettings += $mergedAppSettings
			}
	}

	# Write out a new template
	ConvertTo-Json $applicationTemplate -Depth 10 | Set-Content $templateFile
	
	# Delete the base template file
	Remove-Item -Path $baseTemplateFile
}

Write-Host "Finished AppSetting File Merge"

Write-Host "Deploying the Application Logic App`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --parameters "apimSubscriptionKey=$apimSubscriptionKey" --name $deploymentName 

Write-Host "Deployment complete"
tools\templates\application\standard\Remove-Application-LogicApp.ps1
<#
.SYNOPSIS
Tears down the Application Logic App.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER logicAppName
The name of the Logic App to find the resource.

.EXAMPLE
.\Remove-Application-LogicApp.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -logicAppName "logic-application-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $logicAppName
)

$resourceExists = az resource show --resource-group $resourceGroupName  --name $logicAppName --resource-type "Microsoft.Web/sites"

if ($resourceExists) {
    Write-Host "Removing the Logic App $logicAppName"

    az resource delete --resource-group $resourceGroupName --name $logicAppName --resource-type "Microsoft.Web/sites"

    Write-Host "Removed the Logic App $logicAppName"
}
else {
    Write-Host "The Logic App $logicAppName does not exist in resource group $resourceGroupName"
}
tools\templates\application\standard\TearDown-100-Application-LogicApp.ps1.liquid
 
tools\templates\application\workflows\messageresponsehandler\Deploy-80-MessageResponseHandlerServiceBus-ApiConnection.ps1.liquid
 
tools\templates\application\workflows\messageresponsehandler\Deploy-85-MessageResponseHandler-LogicApp.ps1.liquid
 
tools\templates\application\workflows\messageresponsehandler\Deploy-90-MessageResponseHandlerServiceBus-ApiConnPolicy.ps1.liquid
 
tools\templates\application\workflows\messageresponsehandler\messageresponsehandler.logicapp.dev.parameters.json.liquid
 
tools\templates\application\workflows\messageresponsehandler\messageresponsehandler.logicapp.json
{
    "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "logicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of this LogicApp."
            }
        },
        "logicAppLocation": {
            "defaultValue": "[resourceGroup().location]",
            "type": "string",
            "metadata": {
                "description": "Location (region) or ISE that this LogicApp is to be deployed to. Defaults to the ResourceGroup location."
            }
        },
        "logicAppStartupState": {
            "type": "string",
            "defaultValue": "Enabled",
            "allowedValues": [ "Enabled", "Disabled" ],
            "metadata": {
                "description": "Initial state of the LogicApp after it is deployed."
            }
        },
        "messageBusResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that MessageBus artifacts are deployed to (e.g. APIM or RoutingSlipRouter LogicApp)."
            }
        },
        "apimServiceName": {
            "type": "string",
            "metadata": {
                "description": "Name of the APIM Service used for MessageBus operations."
            }
        },
        "apimSubscriptionKey": {
            "type": "securestring",
            "metadata": {
                "description": "Subscription Key used to access APIM."
            }
        },
        "apimRetryPolicy": {
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "type": "object",
            "metadata": {
                "description": "Retry Policy to use when calling APIM."
            }
        },
        "serviceBusTopicSubscribeApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for ServiceBus Response Subscribe operations."
            }
        },
        "scenarioStep": {
            "defaultValue": "messageResponseHandler",
            "type": "string",
            "metadata": {
                "description": "The step within a Scenario that this LogicApp is running under e.g. messageResponseHandler."
            }
        },
        "tags": {
            "type": "object"
        }
    },
    "variables": {
        "apimServiceResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.ApiManagement/service', parameters('apimServiceName'))]",
        "configurationManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimconfigurationmanager')]",
        "serviceBusTopicSubscribeApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('serviceBusTopicSubscribeApiConnectionName'))]"
    },
    "resources": [
        {
            "type": "Microsoft.Logic/workflows",
            "apiVersion": "2017-07-01",
            "name": "[parameters('logicAppName')]",
            "location": "[parameters('logicAppLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "state": "[parameters('logicAppStartupState')]",
                "definition": {
                    "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
                    "contentVersion": "1.0.0.0",
                    "parameters": {
                        "$connections": {
                            "defaultValue": {},
                            "type": "Object"
                        },
                        "scenarioStep": {
                            "type": "String",
                            "description": "The step within a Scenario that this LogicApp is running under e.g. messageResponseHandler."
                        },
                        "apimSubscriptionKey": {
                            "type": "SecureString",
                            "description": "Subscription Key used to access APIM."
                        }
                    },
                    "triggers": {
                        "manual": {
                            "correlation": {},
                            "type": "Request",
                            "operationOptions": "EnableSchemaValidation",
                            "kind": "Http",
                            "inputs": {
                                "schema": {
                                    "properties": {
                                        "correlationId": {
                                            "type": "string"
                                        },
                                        "responseSubscriptionName": {
                                            "type": "string"
                                        },
                                        "responseTimeoutInMinutes": {
                                            "type": "integer"
                                        },
                                        "responseTopicName": {
                                            "type": "string"
                                        }
                                    },
                                    "required": [
                                        "correlationId",
                                        "responseTopicName",
                                        "responseSubscriptionName",
                                        "responseTimeoutInMinutes"
                                    ],
                                    "type": "object"
                                }
                            }
                        }
                    },
                    "actions": {
                        "Initialize_StatusCode_variable": {
                            "runAfter": {},
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "StatusCode",
                                        "type": "integer",
                                        "value": 500
                                    }
                                ]
                            }
                        },
                        "Initialize_FaultMessage_variable": {
                            "runAfter": {
                                "Initialize_StatusCode_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "FaultMessage",
                                        "type": "object",
                                        "value": null
                                    }
                                ]
                            }
                        },
                        "Initialize_ErrorMessage_variable": {
                            "runAfter": {
                                "Initialize_FaultMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ErrorMessage",
                                        "type": "string",
                                        "value": "An error occurred in the @{workflow()?['name']} (@{workflow()?['run']?['name']}) LogicApp"
                                    }
                                ]
                            }
                        },
                        "Initialize_Checkpoint_variable": {
                            "runAfter": {
                                "Initialize_ErrorMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Checkpoint",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_ResponseBodyArray_variable": {
                            "runAfter": {
                                "Initialize_Checkpoint_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ResponseBodyArray",
                                        "type": "array"
                                    }
                                ]
                            }
                        },
                        "Initialize_ResponseCount_variable": {
                            "runAfter": {
                                "Initialize_ResponseBodyArray_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ResponseCount",
                                        "type": "integer",
                                        "value": 0
                                    }
                                ]
                            }
                        },
                        "SendResponse:_Check_Outcome": {
                            "actions": {
                                "SendResponse:_Switch_on_Checkpoint": {
                                    "cases": {
                                        "Success": {
                                            "case": "WaitForResponseSuccess",
                                            "actions": {
                                                "SendResponse:Success:_Complete_each_Response_Message": {
                                                    "actions": {
                                                        "SendResponse:Success:_Complete_Current_Response_message": {
                                                            "inputs": {
                                                                "host": {
                                                                    "connection": {
                                                                        "name": "@parameters('$connections')['servicebussubscribe']['connectionId']"
                                                                    }
                                                                },
                                                                "method": "delete",
                                                                "path": "/@{encodeURIComponent(triggerBody()?['responseTopicName'])}/subscriptions/@{encodeURIComponent(triggerBody()?['responseSubscriptionName'])}/messages/complete",
                                                                "queries": {
                                                                    "lockToken": "@items('SendResponse:Success:_Complete_each_Response_Message')?['LockToken']",
                                                                    "sessionId": "@items('SendResponse:Success:_Complete_each_Response_Message')?['SessionId']",
                                                                    "subscriptionType": "Main"
                                                                },
                                                                "retryPolicy": {
                                                                    "type": "none"
                                                                }
                                                            },
                                                            "runAfter": {},
                                                            "type": "ApiConnection"
                                                        }
                                                    },
                                                    "foreach": "@variables('ResponseBodyArray')",
                                                    "runAfter": {},
                                                    "type": "Foreach"
                                                },
                                                "SendResponse:Success:_Build_Response": {
                                                    "inputs": {
                                                        "$content-type": "@variables('ResponseBodyArray')?[0]?['ContentType']",
                                                        "$content": "@variables('ResponseBodyArray')?[0]?['ContentData']",
                                                        "$content-encoding": "@variables('ResponseBodyArray')?[0]?['ContentTransferEncoding']"
                                                    },
                                                    "runAfter": {
                                                        "SendResponse:Success:_Complete_each_Response_Message": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "Compose"
                                                },
                                                "SendResponse:Success:_Send_Response": {
                                                    "runAfter": {
                                                        "SendResponse:Success:_Build_Response": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "Response",
                                                    "kind": "Http",
                                                    "inputs": {
                                                        "body": "@outputs('SendResponse:Success:_Build_Response')",
                                                        "headers": {
                                                            "Content-Type": "application/json"
                                                        },
                                                        "statusCode": 200
                                                    }
                                                },
                                                "SendResponse:Success:_Send_Fault_Response": {
                                                    "runAfter": {
                                                        "SendResponse:Success:_Complete_each_Response_Message": [
                                                            "Failed",
                                                            "Skipped",
                                                            "TimedOut"
                                                        ]
                                                    },
                                                    "type": "Response",
                                                    "kind": "Http",
                                                    "inputs": {
                                                        "body": {
                                                            "fault": {
                                                                "faultActor": "@{workflow()['name']} (@{workflow()?['run']?['name']})",
                                                                "faultCategory": "Error",
                                                                "faultCode": "500",
                                                                "faultMessage": "An error occurred trying to complete the response messages received for this session.",
                                                                "faultReason": ""
                                                            }
                                                        },
                                                        "headers": {
                                                            "Content-Type": "application/json"
                                                        },
                                                        "statusCode": 500
                                                    }
                                                }
                                            }
                                        },
                                        "Failure": {
                                            "case": "WaitForResponseFailure",
                                            "actions": {
                                                "SendResponse:Failure:_Send_Fault_Response": {
                                                    "runAfter": {},
                                                    "type": "Response",
                                                    "kind": "Http",
                                                    "inputs": {
                                                        "body": "@variables('FaultMessage')",
                                                        "headers": {
                                                            "Content-Type": "application/json"
                                                        },
                                                        "statusCode": 500
                                                    }
                                                }
                                            }
                                        },
                                        "Timeout": {
                                            "case": "WaitForResponseTimeout",
                                            "actions": {
                                                "SendResponse:Timeout:_Send_Fault_Response": {
                                                    "runAfter": {},
                                                    "type": "Response",
                                                    "kind": "Http",
                                                    "inputs": {
                                                        "body": {
                                                            "fault": {
                                                                "faultActor": "@{workflow()['name']} (@{workflow()?['run']?['name']})",
                                                                "faultCategory": "Error",
                                                                "faultCode": "504",
                                                                "faultMessage": "Timed out waiting for a response message.",
                                                                "faultReason": ""
                                                            }
                                                        },
                                                        "headers": {
                                                            "Content-Type": "application/json"
                                                        },
                                                        "statusCode": 504
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "SendResponse:UnknownCheckpoint:_Send_Fault_Response": {
                                                "runAfter": {},
                                                "type": "Response",
                                                "kind": "Http",
                                                "inputs": {
                                                    "body": {
                                                        "fault": {
                                                            "faultActor": "@{workflow()['name']} (@{workflow()?['run']?['name']})",
                                                            "faultCategory": "Error",
                                                            "faultCode": "500",
                                                            "faultMessage": "Unexpected Checkpoint value of '@{variables('Checkpoint')}' in LogicApp @{workflow()['name']}. Unable to continue.",
                                                            "faultReason": ""
                                                        }
                                                    },
                                                    "headers": {
                                                        "Content-Type": "application/json"
                                                    },
                                                    "statusCode": 500
                                                }
                                            }
                                        }
                                    },
                                    "runAfter": {},
                                    "expression": "@variables('Checkpoint')",
                                    "type": "Switch"
                                }
                            },
                            "runAfter": {
                                "Step:_Wait_for_Response": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "else": {
                                "actions": {
                                    "Failure:_Do_we_have_a_Fault": {
                                        "actions": {
                                            "Failure:NoFault:_Send_Fault_Response": {
                                                "runAfter": {},
                                                "type": "Response",
                                                "kind": "Http",
                                                "inputs": {
                                                    "body": {
                                                        "fault": {
                                                            "faultActor": "@{workflow()['name']} (@{workflow()?['run']?['name']})",
                                                            "faultCategory": "Error",
                                                            "faultCode": "500",
                                                            "faultMessage": "An error occurred in LogicApp @{workflow()['name']}. Unable to continue. Expected a Checkpoint of WaitForResponseSuccess/WaitForResponseFailure/WaitForResponseTimeout but received a Checkpoint of '@{variables('Checkpoint')}'.",
                                                            "faultReason": ""
                                                        }
                                                    },
                                                    "headers": {
                                                        "Content-Type": "application/json"
                                                    },
                                                    "statusCode": 500
                                                }
                                            }
                                        },
                                        "else": {
                                            "actions": {
                                                "Failure:HaveFault:_Send_Fault_Response": {
                                                    "runAfter": {},
                                                    "type": "Response",
                                                    "kind": "Http",
                                                    "inputs": {
                                                        "body": "@variables('FaultMessage')",
                                                        "headers": {
                                                            "Content-Type": "application/json"
                                                        },
                                                        "statusCode": 500
                                                    }
                                                }
                                            }
                                        },
                                        "runAfter": {},
                                        "expression": {
                                            "and": [
                                                {
                                                    "equals": [
                                                        "@coalesce(variables('FaultMessage'), '')",
                                                        ""
                                                    ]
                                                }
                                            ]
                                        },
                                        "type": "if"
                                    }
                                }
                            },
                            "expression": {
                                "or": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "WaitForResponseSuccess"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "WaitForResponseFailure"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "WaitForResponseTimeout"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Wait_for_Response": {
                            "actions": {
                                "WaitForResponse:_Loop_until_we_get_Response_or_TimeOut": {
                                    "actions": {
                                        "WaitForResponse:_Get_Response_Message_from_Topic": {
                                            "inputs": {
                                                "host": {
                                                    "connection": {
                                                        "name": "@parameters('$connections')['servicebussubscribe']['connectionId']"
                                                    }
                                                },
                                                "method": "get",
                                                "path": "/@{encodeURIComponent(encodeURIComponent(triggerBody()?['responseTopicName']))}/subscriptions/@{encodeURIComponent(triggerBody()?['responseSubscriptionName'])}/messages/batch/peek",
                                                "queries": {
                                                    "maxMessageCount": 1,
                                                    "sessionId": "@{triggerBody()?['correlationId']}",
                                                    "subscriptionType": "Main"
                                                },
                                                "retryPolicy": {
                                                    "type": "none"
                                                }
                                            },
                                            "runAfter": {},
                                            "type": "ApiConnection"
                                        },
                                        "WaitForResponse:_Set_StatusCode_variable": {
                                            "runAfter": {
                                                "WaitForResponse:_Get_Response_Message_from_Topic": [
                                                    "Succeeded",
                                                    "Failed",
                                                    "Skipped",
                                                    "TimedOut"
                                                ]
                                            },
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "StatusCode",
                                                "value": "@coalesce(outputs('WaitForResponse:_Get_Response_Message_from_Topic')?['statusCode'], 500)"
                                            }
                                        },
                                        "WaitForResponse:_Check_Status_Code": {
                                            "runAfter": {
                                                "WaitForResponse:_Set_StatusCode_variable": [
                                                    "Succeeded"
                                                ]
                                            },
                                            "cases": {
                                                "Success": {
                                                    "case": 200,
                                                    "actions": {
                                                        "WaitForResponse:Success:_Set_ResponseBodyArray_variable": {
                                                            "inputs": {
                                                                "name": "ResponseBodyArray",
                                                                "value": "@array(body('WaitForResponse:_Get_Response_Message_from_Topic'))"
                                                            },
                                                            "runAfter": {},
                                                            "type": "SetVariable"
                                                        },
                                                        "WaitForResponse:Success:_Set_ResponseCount_variable": {
                                                            "inputs": {
                                                                "name": "ResponseCount",
                                                                "value": "@length(variables('ResponseBodyArray'))"
                                                            },
                                                            "runAfter": {
                                                                "WaitForResponse:Success:_Set_ResponseBodyArray_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable"
                                                        }
                                                    }
                                                }
                                            },
                                            "default": {
                                                "actions": {
                                                    "WaitForResponse:Failure:_Create_Fault_Message": {
                                                        "runAfter": {},
                                                        "type": "Compose",
                                                        "inputs": {
                                                            "fault": {
                                                                "faultActor": "@{workflow()?['name']}[email protected]{actions('WaitForResponse:_Get_Response_Message_from_Topic')?['name']} (@{workflow()?['run']?['name']})",
                                                                "faultCategory": "Error",
                                                                "faultCode": "@{coalesce(outputs('WaitForResponse:_Get_Response_Message_from_Topic')?['statusCode'], outputs('WaitForResponse:_Get_Response_Message_from_Topic')?['body']?['statusCode'], actions('WaitForResponse:_Get_Response_Message_from_Topic')?['error']?['code'])}",
                                                                "faultMessage": "@{coalesce(outputs('WaitForResponse:_Get_Response_Message_from_Topic')?['error']?['message'], body('WaitForResponse:_Get_Response_Message_from_Topic')?['message'], body('WaitForResponse:_Get_Response_Message_from_Topic')?['error']?['message'], actions('WaitForResponse:_Get_Response_Message_from_Topic')?['error']?['message'])}",
                                                                "faultReason": "@{actions('WaitForResponse:_Get_Response_Message_from_Topic')?['status']}"
                                                            }
                                                        }
                                                    },
                                                    "WaitForResponse:Failure:_Set_FaultMessage_variable": {
                                                        "runAfter": {
                                                            "WaitForResponse:Failure:_Create_Fault_Message": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@outputs('WaitForResponse:Failure:_Create_Fault_Message')"
                                                        }
                                                    },
                                                    "WaitForResponse:Failure:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "WaitForResponse:Failure:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred executing the @{actions('WaitForResponse:_Get_Response_Message_from_Topic')?['name']} action to get the response message."
                                                        }
                                                    },
                                                    "WaitForResponse:Failure:_Set_Checkpoint_variable": {
                                                        "inputs": {
                                                            "name": "Checkpoint",
                                                            "value": "WaitForResponseFailure"
                                                        },
                                                        "runAfter": {
                                                            "WaitForResponse:Failure:_Set_ErrorMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable"
                                                    }
                                                }
                                            },
                                            "expression": "@variables('StatusCode')",
                                            "type": "Switch"
                                        }
                                    },
                                    "expression": "@or(greater(variables('ResponseCount'), 0), equals(variables('Checkpoint'), 'WaitForResponseFailure'))",
                                    "limit": {
                                        "count": "@mul(coalesce(triggerBody()?['responseTimeoutInMinutes'], 3), 2)",
                                        "timeout": "[email protected]{coalesce(triggerBody()?['responseTimeoutInMinutes'], 3)}M"
                                    },
                                    "runAfter": {},
                                    "type": "Until"
                                },
                                "WaitForResponse:_Check_Outcome": {
                                    "actions": {
                                        "WaitForResponse:Success:_Set_Checkpoint_variable": {
                                            "inputs": {
                                                "name": "Checkpoint",
                                                "value": "WaitForResponseSuccess"
                                            },
                                            "runAfter": {},
                                            "type": "SetVariable"
                                        }
                                    },
                                    "else": {
                                        "actions": {
                                            "WaitForResponse:TimeOut:_Set_Checkpoint_variable": {
                                                "inputs": {
                                                    "name": "Checkpoint",
                                                    "value": "WaitForResponseTimeout"
                                                },
                                                "runAfter": {},
                                                "type": "SetVariable"
                                            }
                                        }
                                    },
                                    "runAfter": {
                                        "WaitForResponse:_Loop_until_we_get_Response_or_TimeOut": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "equals": [
                                                    "@variables('Checkpoint')",
                                                    ""
                                                ]
                                            },
                                            {
                                                "greater": [
                                                    "@variables('ResponseCount')",
                                                    0
                                                ]
                                            }
                                        ]
                                    },
                                    "type": "if"
                                }
                            },
                            "runAfter": {
                                "Initialize_ResponseCount_variable": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            ""
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        }
                    },
                    "outputs": {}
                },
                "parameters": {
                    "$connections": {
                        "value": {
                            "servicebussubscribe": {
                                "connectionId": "[variables('serviceBusTopicSubscribeApiConnectionResourceId')]",
                                "connectionName": "[parameters('serviceBusTopicSubscribeApiConnectionName')]",
                                "id": "[concat(subscription().id, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/servicebus')]"
                            }
                        }
                    },
                    "scenarioStep": {
                        "value": "[parameters('scenarioStep')]"
                    },
                    "apimSubscriptionKey": {
                        "value": "[parameters('apimSubscriptionKey')]"
                    }
                }
            }
        }
    ]
}
tools\templates\application\workflows\messageresponsehandler\messageresponsehandler.logicapp.prod.parameters.json.liquid
 
tools\templates\application\workflows\messageresponsehandler\messageresponsehandlerservicebus.apiconnection.dev.parameters.json.liquid
 
tools\templates\application\workflows\messageresponsehandler\messageresponsehandlerservicebus.apiconnection.json.liquid
 
tools\templates\application\workflows\messageresponsehandler\messageresponsehandlerservicebus.apiconnection.prod.parameters.json.liquid
 
tools\templates\application\workflows\messageresponsehandler\messageresponsehandlerservicebus.apiconnpolicy.dev.parameters.json.liquid
 
tools\templates\application\workflows\messageresponsehandler\messageresponsehandlerservicebus.apiconnpolicy.json
{
	"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
	"contentVersion": "1.0.0.0",
	"parameters": {
		"apiConnectionName": {
			"type": "string",
			"metadata": {
				"description": "Resource Name of the API Connection"
			}
		},
		"apiConnectionDisplayName": {
			"type": "string",
			"defaultValue": "[parameters('apiConnectionName')]",
			"metadata": {
				"description": "Display Name of the API Connection"
			}
		},
		"apiConnectionLocation": {
			"type": "string",
			"defaultValue": "[resourceGroup().location]",
			"metadata": {
				"description": "Location that we're deploying this resource to."
			}
		},
		"logicAppName": {
			"type": "String",
			"metadata": {
				"description": "Name of the LogicApp that we're creating a policy for."
			}
		},
		"tags": {
			"type": "object"
		}
	},
	"variables": {},
	"resources": [
		{
			"type": "Microsoft.Web/connections/accessPolicies",
			"apiVersion": "2016-06-01",
			"name": "[concat(parameters('apiConnectionName'),'/', parameters('logicAppName'))]",
			"location": "[parameters('apiConnectionLocation')]",
			"dependsOn": [],
			"properties": {
				"principal": {
					"type": "ActiveDirectory",
					"identity": {
						"tenantId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.tenantId]",
						"objectId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.principalId]"
					}
				}
			}
		}
	],
	"outputs": {}
}
tools\templates\application\workflows\messageresponsehandler\messageresponsehandlerservicebus.apiconnpolicy.prod.parameters.json.liquid
 
tools\templates\application\workflows\messageresponsehandler\New-MessageResponseHandler-LogicApp.ps1
<#
.SYNOPSIS
Creates a Logic App.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER keyVaultName
The name of the key vault store.

.PARAMETER keyVaultApimSubscriptionSecretName
The name of secret in key vault which stores the apim subscription.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-MessageResponseHandler-LogicApp.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -templateFile ".\messageresponsehandler.logicapp.json" -templateParameterFile ".\messagereponsehandler.logicapp.dev.parameters" -keyVaultName "kv-aimrstore-dev-xxxxx" -keyVaultApimSubscriptionSecretName "aim-apim-subscriptionkey-unlimited" -deploymentName "messagereponsehandler.logicapp.uksouth.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName,
    [parameter(Mandatory = $true)]
    [string] $deploymentName    
)

Write-Host "Getting the subscription key from Key Vault for APIM"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

Write-Host "Deploying the message response handler Logic App`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --parameters "apimSubscriptionKey=$apimSubscriptionKey" --name $deploymentName 

Write-Host "Deployment complete"
tools\templates\application\workflows\messageresponsehandler\New-MessageResponseHandlerServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Creates a service bus api connection for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-MessageResponseHandlerServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -templateFile ".\messageresponsehandlersb.apiconnection.json" -templateParameterFile ".\messageresponsehandlersb.apiconnection.dev.parameters.json" -deploymentName "messageresponsehandlersb.apiconnection.xxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying a service bus api connection`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\application\workflows\messageresponsehandler\New-MessageResponseHandlerServiceBus-ApiConnPolicy.ps1
<#
.SYNOPSIS
Creates a message response handler service bus api connection access policy.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-MessageResponseHandlerServiceBus-ApiConnPolicy.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -templateFile ".\messageresponsehandlerservicebus.apiconnpolicy.json" -templateParameterFile ".\messageresponsehandlerservicebus.apiconnpolicy.dev.parameters.json" -deploymentName "messageresponsehandlerservicebus.apicaccesspolicy.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an api connection access policy`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\application\workflows\messageresponsehandler\Remove-MessageResponseHandler-LogicApp.ps1
<#
.SYNOPSIS
Tears down the Logic App.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER workflowName
The name of the Logic App to find the resource.

.EXAMPLE
.\Remove-MessageResponseHandler-LogicApp.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -workflowName "logic-messageresponsehandler-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $workflowName
)

$resourceExists = az resource show --resource-group $resourceGroupName  --name $workflowName --namespace "Microsoft.Logic" --resource-type "workflows"

if ($resourceExists) {
    Write-Host "Removing the Logic App $workflowName"

    az resource delete --resource-group $resourceGroupName --name $workflowName --namespace "Microsoft.Logic" --resource-type "workflows"

    Write-Host "Removed the Logic App $workflowName"
}
else {
    Write-Host "The Logic App $workflowName does not exist in resource group $resourceGroupName"
}
tools\templates\application\workflows\messageresponsehandler\Remove-MessageResponseHandlerServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the message response handlers service bus api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-MessageResponseHandlerServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -resourceName "apic-aimsmessageresponsehandlerconnector-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the message response handler service bus api connection resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the message response handler service bus api connection resource: $resourceName"
}
else {
    Write-Host "The message response handlers service bus api connection resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\application\workflows\messageresponsehandler\TearDown-80-MessageResponseHandlerServiceBus-ApiConnection.ps1.liquid
 
tools\templates\application\workflows\messageresponsehandler\TearDown-85-MessageResponseHandler-LogicApp.ps1.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\Deploy-80-MessageSuspendProcessorServiceBus-ApiConnection.ps1.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\Deploy-85-MessageSuspendProcessor-LogicApp.ps1.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\messagesuspendprocessor.logicapp.dev.parameters.json.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\messagesuspendprocessor.logicapp.json
{
    "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "logicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of this LogicApp."
            }
        },
        "logicAppLocation": {
            "defaultValue": "[resourceGroup().location]",
            "type": "string",
            "metadata": {
                "description": "Location (region) or ISE that this LogicApp is to be deployed to. Defaults to the ResourceGroup location."
            }
        },
        "logicAppStartupState": {
            "type": "string",
            "defaultValue": "Enabled",
            "allowedValues": [ "Enabled", "Disabled" ],
            "metadata": {
                "description": "Initial state of the LogicApp after it is deployed."
            }
        },
        "messageBusResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that MessageBus artifacts are deployed to (e.g. APIM or RoutingSlipRouter LogicApp)."
            }
        },
        "apimServiceName": {
            "type": "string",
            "metadata": {
                "description": "Name of the APIM Service used for MessageBus operations."
            }
        },
        "apimSubscriptionKey": {
            "type": "securestring",
            "metadata": {
                "description": "Subscription Key used to access APIM."
            }
        },
        "apimRetryPolicy": {
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "type": "object",
            "metadata": {
                "description": "Retry Policy to use when calling APIM."
            }
        },
        "serviceBusTopicPublishApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for ServiceBus SuspendQueue Publish operations."
            }
        },
        "scenarioStep": {
            "defaultValue": "messageSuspendProcessor",
            "type": "string",
            "metadata": {
                "description": "The step within a Scenario that this LogicApp is running under e.g. messageSuspendProcessor."
            }
        },
        "tags": {
            "type": "object"
        }
    },
    "variables": {
        "apimServiceResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.ApiManagement/service', parameters('apimServiceName'))]",
        "configurationManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimconfigurationmanager')]",
        "serviceBusTopicPublishApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('serviceBusTopicPublishApiConnectionName'))]"
    },
    "resources": [
        {
            "type": "Microsoft.Logic/workflows",
            "apiVersion": "2017-07-01",
            "name": "[parameters('logicAppName')]",
            "location": "[parameters('logicAppLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "state": "[parameters('logicAppStartupState')]",
                "definition": {
                    "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
                    "contentVersion": "1.0.0.0",
                    "parameters": {
                        "$connections": {
                            "defaultValue": {},
                            "type": "Object"
                        },
                        "scenarioStep": {
                            "type": "String",
                            "description": "The step within a Scenario that this LogicApp is running under e.g. messageSuspendProcessor."
                        },
                        "apimSubscriptionKey": {
                            "type": "SecureString",
                            "description": "Subscription Key used to access APIM."
                        }
                    },
                    "triggers": {
                        "manual": {
                            "correlation": {
                                "clientTrackingId": "@coalesce(triggerBody()?['header']?['properties']?['trackingId'], guid())"
                            },
                            "type": "Request",
                            "operationOptions": "EnableSchemaValidation",
                            "kind": "Http",
                            "inputs": {
                                "schema": {
                                    "properties": {
                                        "nackMessage": {
                                            "properties": {},
                                            "type": "object"
                                        },
                                        "originalMessage": {
                                            "properties": {},
                                            "type": "object"
                                        },
                                        "suspendQueueTopicName": {
                                            "type": "string"
                                        },
                                        "failedMessageRouting": {
                                            "type": "boolean"
                                        },
                                        "scenario": {
                                            "type": "string"
                                        }
                                    },
                                    "required": [
                                        "nackMessage",
                                        "suspendQueueTopicName",
                                        "failedMessageRouting",
                                        "scenario"
                                    ],
                                    "type": "object"
                                }
                            }
                        }
                    },
                    "actions": {
                        "Initialize_StatusCode_variable": {
                            "runAfter": {},
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "StatusCode",
                                        "type": "integer",
                                        "value": 500
                                    }
                                ]
                            }
                        },
                        "Initialize_FaultMessage_variable": {
                            "runAfter": {
                                "Initialize_StatusCode_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "FaultMessage",
                                        "type": "object",
                                        "value": null
                                    }
                                ]
                            }
                        },
                        "Initialize_ErrorMessage_variable": {
                            "runAfter": {
                                "Initialize_FaultMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ErrorMessage",
                                        "type": "string",
                                        "value": "An error occurred in the @{workflow()?['name']} (@{workflow()?['run']?['name']}) LogicApp"
                                    }
                                ]
                            }
                        },
                        "Initialize_Checkpoint_variable": {
                            "runAfter": {
                                "Initialize_ErrorMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Checkpoint",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_NackMessage_variable": {
                            "runAfter": {
                                "Initialize_Checkpoint_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "NackMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_OriginalMessage_variable": {
                            "runAfter": {
                                "Initialize_NackMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "OriginalMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "MessageSender:_Were_we_Successful": {
                            "actions": {
                                "Success:_Build_ACK_message": {
                                    "runAfter": {},
                                    "type": "Compose",
                                    "inputs": {
                                        "body": [
                                            {
                                                "$content": { "result": "Successfully published a [email protected]{if(equals(variables('Checkpoint'), 'SuspendOriginalMessage'), ' and Original message', '')} to the SuspendQueue in ServiceBus" },
                                                "$contentType": "application/json",
                                                "$part": 1,
                                                "$partType": "http://schemas.microsoft.com/aim#ack"
                                            }
                                        ],
                                        "header": {
                                            "properties": {
                                                "createDate": "@utcNow()",
                                                "envelopeType": "ack",
                                                "messageId": "@guid()",
                                                "rootPart": 1,
                                                "trackingId": "@variables('NackMessage')?['header']?['properties']?['trackingId']"
                                            },
                                            "routing": {
                                                "messageType": "http://schemas.microsoft.com/aim#ack"
                                            },
                                            "routingSlip": {},
                                            "state": {}
                                        }
                                    }
                                },
                                "Routing:Success:_Send_ACK-Content_response": {
                                    "runAfter": {
                                        "Success:_Build_ACK_message": [
                                            "Succeeded"
                                        ]
                                    },
                                    "type": "Response",
                                    "kind": "Http",
                                    "inputs": {
                                        "body": "@outputs('Success:_Build_ACK_message')",
                                        "headers": {
                                            "Aim-Tracking-Id": "@{variables('NackMessage')?['header']?['properties']?['trackingId']}",
                                            "Aim-Clear-Cache": "@coalesce(trigger()?['headers']?['Aim-Clear-Cache'], 'false')",
                                            "Aim-Enable-Trace": "@coalesce(trigger()?['headers']?['Aim-Enable-Trace'], 'false')",
                                            "Content-Type": "application/json"
                                        },
                                        "statusCode": 200
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Suspend_Original_Message": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "else": {
                                "actions": {
                                    "Failure:_Build_NACK_message": {
                                        "runAfter": {},
                                        "type": "Compose",
                                        "inputs": {
                                            "body": [
                                                {
                                                    "$content": {
                                                        "code": "500",
                                                        "message": "@variables('ErrorMessage')",
                                                        "lastCheckpoint": "@variables('Checkpoint')",
                                                        "fault": "@variables('FaultMessage')"
                                                    },
                                                    "$contentType": "application/json",
                                                    "$part": 1,
                                                    "$partType": "http://schemas.microsoft.com/aim#nack"
                                                }
                                            ],
                                            "header": {
                                                "properties": {
                                                    "createDate": "@utcNow()",
                                                    "envelopeType": "nack",
                                                    "messageId": "@guid()",
                                                    "rootPart": 1,
                                                    "trackingId": "@variables('NackMessage')?['header']?['properties']?['trackingId']"
                                                },
                                                "routing": {
                                                    "messageType": "http://schemas.microsoft.com/aim#nack"
                                                },
                                                "routingSlip": {},
                                                "state": {}
                                            }
                                        }
                                    },
                                    "Failure:_Send_NACK_response": {
                                        "runAfter": {
                                            "Failure:_Build_NACK_message": [
                                                "Succeeded"
                                            ]
                                        },
                                        "type": "Response",
                                        "kind": "Http",
                                        "inputs": {
                                            "body": "@outputs('Failure:_Build_NACK_message')",
                                            "headers": {
                                                "Aim-Tracking-Id": "@{variables('NackMessage')?['header']?['properties']?['trackingId']}",
                                                "Aim-Clear-Cache": "@coalesce(trigger()?['headers']?['Aim-Clear-Cache'], 'false')",
                                                "Aim-Enable-Trace": "@coalesce(trigger()?['headers']?['Aim-Enable-Trace'], 'false')",
                                                "Content-Type": "application/json"
                                            },
                                            "statusCode": 200
                                        }
                                    }
                                }
                            },
                            "expression": {
                                "or": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "SuspendOriginalMessage"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "SkippedSuspendOriginalMessage"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_Messages": {
                            "actions": {
                                "GetMessages:_Set_NackMessage_variable": {
                                    "runAfter": {},
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "NackMessage",
                                        "value": "@triggerBody()?['nackMessage']"
                                    }
                                },
                                "GetMessages:_Set_OriginalMessage_variable": {
                                    "runAfter": {
                                        "GetMessages:_Set_NackMessage_variable": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "OriginalMessage",
                                        "value": "@triggerBody()?['originalMessage']"
                                    }
                                },
                                "GetMessages:_Have_Valid_Messages": {
                                    "actions": {
                                        "GetMessages:Success:_Set_Checkpoint_variable": {
                                            "runAfter": {},
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "Checkpoint",
                                                "value": "GetMessages"
                                            }
                                        }
                                    },
                                    "runAfter": {
                                        "GetMessages:_Set_OriginalMessage_variable": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "else": {
                                        "actions": {
                                            "GetMessages:Failure:_Set_Checkpoint_variable": {
                                                "runAfter": {},
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ErrorMessage",
                                                    "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}): no messages supplied in triggerBody - need either or both of NACK message or Original message"
                                                }
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "not": {
                                                    "equals": [
                                                        "@coalesce(variables('NackMessage'), '')",
                                                        ""
                                                    ]
                                                }
                                            },
                                            {
                                                "not": {
                                                    "equals": [
                                                        "@coalesce(variables('OriginalMessage'), '')",
                                                        ""
                                                    ]
                                                }
                                            }
                                        ]
                                    },
                                    "type": "If"
                                }
                            },
                            "runAfter": {
                                "Initialize_OriginalMessage_variable": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            ""
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Suspend_NACK": {
                            "actions": {
                                "SuspendNack:_Check_Status_Code": {
                                    "runAfter": {
                                        "SuspendNack:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "SuspendNack:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "SuspendNack"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "SuspendNack:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "SuspendNack:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "SuspendNack:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to publish a NACK to the SuspendQueue in ServiceBus"
                                                        }
                                                    },
                                                    "SuspendNack:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('SuspendNack:_Send_to_ServiceBus')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "SuspendNack:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()['name'], '.', actions('SuspendNack:_Send_to_ServiceBus')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('SuspendNack:_Send_to_ServiceBus')?['statusCode'], outputs('SuspendNack:_Send_to_ServiceBus')?['body']?['statusCode'], actions('SuspendNack:_Send_to_ServiceBus')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('SuspendNack:_Send_to_ServiceBus')?['error']?['message'], outputs('SuspendNack:_Send_to_ServiceBus')?['body']?['message'], actions('SuspendNack:_Send_to_ServiceBus')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('SuspendNack:_Send_to_ServiceBus')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "SuspendNack:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "SuspendNack:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to publish a NACK to the SuspendQueue in ServiceBus"
                                                            }
                                                        },
                                                        "SuspendNack:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "SuspendNack:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('SuspendNack:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('SuspendNack:_Send_to_ServiceBus')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "SuspendNack:_Send_to_ServiceBus": {
                                    "runAfter": {},
                                    "type": "ApiConnection",
                                    "inputs": {
                                        "body": {
                                            "ContentData": "@{base64(variables('NackMessage'))}",
                                            "ContentType": "application/json",
                                            "MessageId": "@coalesce(variables('NackMessage')?['header']?['properties']?['messageId'], guid())",
                                            "Properties": "@variables('NackMessage')?['header']?['routing']",
                                            "SessionId": "none"
                                        },
                                        "host": {
                                            "connection": {
                                                "name": "@parameters('$connections')['servicebuspublish']['connectionId']"
                                            }
                                        },
                                        "method": "post",
                                        "path": "/@{encodeURIComponent(coalesce(triggerBody()?['suspendQueueTopicName'], '(suspendqueue topic name not set)'))}/messages",
                                        "queries": {
                                            "systemProperties": "None"
                                        }
                                    }
                                },
                                "SuspendNack:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "SuspendNack:_Send_to_ServiceBus": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('SuspendNack:_Send_to_ServiceBus')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Get_Messages": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetMessages"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Suspend_Original_Message": {
                            "actions": {
                                "SuspendOriginalMessage:_Check_FailedMessageRouting_value": {
                                    "actions": {
                                        "SuspendOriginalMessage:_Check_Status_Code": {
                                            "runAfter": {
                                                "SuspendOriginalMessage:_Set_StatusCode_variable": [
                                                    "Succeeded"
                                                ]
                                            },
                                            "cases": {
                                                "Success": {
                                                    "case": 200,
                                                    "actions": {
                                                        "SuspendOriginalMessage:Success:_Set_Checkpoint_variable": {
                                                            "runAfter": {},
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "Checkpoint",
                                                                "value": "SuspendOriginalMessage"
                                                            }
                                                        }
                                                    }
                                                }
                                            },
                                            "default": {
                                                "actions": {
                                                    "SuspendOriginalMessage:Failure:_Do_we_have_a_Fault_Message": {
                                                        "actions": {
                                                            "SuspendOriginalMessage:Fault:_Set_ErrorMessage_variable": {
                                                                "runAfter": {
                                                                    "SuspendOriginalMessage:Fault:_Set_FaultMessage_variable": [
                                                                        "Succeeded"
                                                                    ]
                                                                },
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "ErrorMessage",
                                                                    "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to publish an original message to the SuspendQueue in ServiceBus"
                                                                }
                                                            },
                                                            "SuspendOriginalMessage:Fault:_Set_FaultMessage_variable": {
                                                                "runAfter": {},
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "FaultMessage",
                                                                    "value": "@body('SuspendOriginalMessage:_Send_to_ServiceBus')"
                                                                }
                                                            }
                                                        },
                                                        "runAfter": {},
                                                        "else": {
                                                            "actions": {
                                                                "SuspendOriginalMessage:NoFault:_Create_Fault_Message": {
                                                                    "runAfter": {},
                                                                    "type": "Compose",
                                                                    "inputs": {
                                                                        "fault": {
                                                                            "faultActor": "@concat(workflow()['name'], '.', actions('SuspendOriginalMessage:_Send_to_ServiceBus')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                            "faultCategory": "Error",
                                                                            "faultCode": "@{coalesce(outputs('SuspendOriginalMessage:_Send_to_ServiceBus')?['statusCode'], outputs('SuspendOriginalMessage:_Send_to_ServiceBus')?['body']?['statusCode'], actions('SuspendOriginalMessage:_Send_to_ServiceBus')?['error']?['code'])}",
                                                                            "faultMessage": "@{coalesce(outputs('SuspendOriginalMessage:_Send_to_ServiceBus')?['error']?['message'], outputs('SuspendOriginalMessage:_Send_to_ServiceBus')?['body']?['message'], actions('SuspendOriginalMessage:_Send_to_ServiceBus')?['error']?['message'])}",
                                                                            "faultReason": "@{actions('SuspendOriginalMessage:_Send_to_ServiceBus')?['status']}"
                                                                        }
                                                                    }
                                                                },
                                                                "SuspendOriginalMessage:NoFault:_Set_ErrorMessage_variable": {
                                                                    "runAfter": {
                                                                        "SuspendOriginalMessage:NoFault:_Set_FaultMessage_variable": [
                                                                            "Succeeded"
                                                                        ]
                                                                    },
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "ErrorMessage",
                                                                        "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to publish an original message to the SuspendQueue in ServiceBus"
                                                                    }
                                                                },
                                                                "SuspendOriginalMessage:NoFault:_Set_FaultMessage_variable": {
                                                                    "runAfter": {
                                                                        "SuspendOriginalMessage:NoFault:_Create_Fault_Message": [
                                                                            "Succeeded"
                                                                        ]
                                                                    },
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "FaultMessage",
                                                                        "value": "@outputs('SuspendOriginalMessage:NoFault:_Create_Fault_Message')"
                                                                    }
                                                                }
                                                            }
                                                        },
                                                        "expression": {
                                                            "and": [
                                                                {
                                                                    "not": {
                                                                        "equals": [
                                                                            "@body('SuspendOriginalMessage:_Send_to_ServiceBus')?['fault']",
                                                                            null
                                                                        ]
                                                                    }
                                                                }
                                                            ]
                                                        },
                                                        "type": "If"
                                                    }
                                                }
                                            },
                                            "expression": "@variables('StatusCode')",
                                            "type": "Switch"
                                        },
                                        "SuspendOriginalMessage:_Send_to_ServiceBus": {
                                            "runAfter": {},
                                            "type": "ApiConnection",
                                            "inputs": {
                                                "body": {
                                                    "ContentData": "@{base64(variables('OriginalMessage'))}",
                                                    "ContentType": "application/json",
                                                    "MessageId": "@coalesce(variables('OriginalMessage')?['header']?['properties']?['messageId'], guid())",
                                                    "Properties": {
                                                        "messageType": "@variables('OriginalMessage')?['header']?['properties']?['messageType']",
                                                        "errorType": "FailedMessage"
                                                    },
                                                    "SessionId": "none"
                                                },
                                                "host": {
                                                    "connection": {
                                                        "name": "@parameters('$connections')['servicebuspublish']['connectionId']"
                                                    }
                                                },
                                                "method": "post",
                                                "path": "/@{encodeURIComponent(coalesce(triggerBody()?['suspendQueueTopicName'], '(suspendqueue topic name not set)'))}/messages",
                                                "queries": {
                                                    "systemProperties": "None"
                                                }
                                            }
                                        },
                                        "SuspendOriginalMessage:_Set_StatusCode_variable": {
                                            "runAfter": {
                                                "SuspendOriginalMessage:_Send_to_ServiceBus": [
                                                    "Succeeded",
                                                    "Failed",
                                                    "Skipped",
                                                    "TimedOut"
                                                ]
                                            },
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "StatusCode",
                                                "value": "@coalesce(outputs('SuspendOriginalMessage:_Send_to_ServiceBus')?['statusCode'], 500)"
                                            }
                                        }
                                    },
                                    "runAfter": {},
                                    "else": {
                                        "actions": {
                                            "SuspendOriginalMessage:Skipped:_Set_Checkpoint_variable": {
                                                "runAfter": {},
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "Checkpoint",
                                                    "value": "SkippedSuspendOriginalMessage"
                                                }
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "equals": [
                                                    "@coalesce(triggerBody()?['failedMessageRouting'], false)",
                                                    true
                                                ]
                                            }
                                        ]
                                    },
                                    "type": "if"
                                }
                            },
                            "runAfter": {
                                "Step:_Suspend_NACK": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "SuspendNack"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        }
                    },
                    "outputs": {}
                },
                "parameters": {
                    "$connections": {
                        "value": {
                            "servicebuspublish": {
                                "connectionId": "[variables('serviceBusTopicPublishApiConnectionResourceId')]",
                                "connectionName": "[parameters('serviceBusTopicPublishApiConnectionName')]",
                                "id": "[concat(subscription().id, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/servicebus')]"
                            }
                        }
                    },
                    "scenarioStep": {
                        "value": "[parameters('scenarioStep')]"
                    },
                    "apimSubscriptionKey": {
                        "value": "[parameters('apimSubscriptionKey')]"
                    }
                }
            }
        }
    ]
}
tools\templates\application\workflows\messagesuspendprocessor\messagesuspendprocessor.logicapp.prod.parameters.json.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\messagesuspendprocessorservicebus.apiconnection.dev.parameters.json.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\messagesuspendprocessorservicebus.apiconnection.json.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\messagesuspendprocessorservicebus.apiconnection.prod.parameters.json.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\New-MessageSuspendProcessor-LogicApp.ps1
<#
.SYNOPSIS
Creates a Logic App.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER keyVaultName
The name of the key vault store.

.PARAMETER keyVaultApimSubscriptionSecretName
The name of secret in key vault which stores the apim subscription.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-MessageSuspendProcessor-LogicApp.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -templateFile ".\xmlmessagesuspendprocessor.logicapp.json" -templateParameterFile ".\xmlmessageprocessor.logicapp.dev.parameters" -keyVaultName "kv-aimrstore-dev-xxxxx" -keyVaultApimSubscriptionSecretName "aim-apim-subscriptionkey-unlimited" -deploymentName "xmlmessagesuspendprocessor.logicapp.uksouth.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName,
    [parameter(Mandatory = $true)]
    [string] $deploymentName    
)

Write-Host "Getting the subscription key from Key Vault for APIM"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

Write-Host "Deploying the xml message suspend processor Logic App`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --parameters "apimSubscriptionKey=$apimSubscriptionKey" --name $deploymentName 

Write-Host "Deployment complete"
tools\templates\application\workflows\messagesuspendprocessor\New-MessageSuspendProcessorServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Creates a service bus api connection for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-MessageSuspendProcessorServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -templateFile ".\messagesuspendprocessorrsb.apiconnection.json" -templateParameterFile ".\messagesuspendprocessorsb.apiconnection.dev.parameters.json" -deploymentName "messagesuspendprocessorsb.apiconnection.xxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying a service bus api connection`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\application\workflows\messagesuspendprocessor\Remove-MessageSuspendProcessor-LogicApp.ps1
<#
.SYNOPSIS
Tears down the Logic App.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER workflowName
The name of the Logic App to find the resource.

.EXAMPLE
.\Remove-MessageSuspendProcessor-LogicApp.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -workflowName "logic-messagesuspendprocessor-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $workflowName
)

$resourceExists = az resource show --resource-group $resourceGroupName  --name $workflowName --namespace "Microsoft.Logic" --resource-type "workflows"

if ($resourceExists) {
    Write-Host "Removing the Logic App $workflowName"

    az resource delete --resource-group $resourceGroupName --name $workflowName --namespace "Microsoft.Logic" --resource-type "workflows"

    Write-Host "Removed the Logic App $workflowName"
}
else {
    Write-Host "The Logic App $workflowName does not exist in resource group $resourceGroupName"
}
tools\templates\application\workflows\messagesuspendprocessor\Remove-MessageSuspendProcessorServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the message response handlers service bus api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-MessageSuspendProcessorServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimmsgbus-dev-uksouth-xxxxx" -resourceName "apic-aimsuspendprocessorconnector-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the message suspend processor service bus api connection resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the message suspend processor service bus api connection resource: $resourceName"
}
else {
    Write-Host "The message suspend processor service bus api connection resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\application\workflows\messagesuspendprocessor\TearDown-80-MessageSuspendProcessorServiceBus-ApiConnection.ps1.liquid
 
tools\templates\application\workflows\messagesuspendprocessor\TearDown-85-MessageSuspendProcessor-LogicApp.ps1.liquid
 
tools\templates\channels\topicchannel\Deploy-20-TopicChannel-ServiceBus.ps1.liquid
 
tools\templates\channels\topicchannel\namespace\Deploy-15-Namespace-ServiceBus.ps1.liquid
 
tools\templates\channels\topicchannel\namespace\namespace.sb.dev.psparameters.json.liquid
 
tools\templates\channels\topicchannel\namespace\namespace.sb.prod.psparameters.json.liquid
 
tools\templates\channels\topicchannel\namespace\New-Namespace-ServiceBus.ps1
<#
.SYNOPSIS
Creates a Service Bus Namespace resource for use by various AIM components.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER location
The location to create the service bus in.

.PARAMETER namespace
Namespace to create the service bus with.

.PARAMETER sku
The SKU level for the namespace.

.PARAMETER tags
The tags to apply to the namespace.

.EXAMPLE
.\New-Namespace-ServiceBus.ps1 -resourceGroupName "rg-aimapp-systemapplication-dev-uksouth" -location "uksouth" -namespace "sb-aimmsgbox-dev-uksouth" -sku "Standard" 
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $location,
    [parameter(Mandatory = $true)]
    [string] $namespace,
    [parameter(Mandatory = $false)]
    [string] $sku = "Basic",
    [parameter(Mandatory = $false)]
    [string[]] $tags = ""
)

Write-Host "Deploying the namespace: $namespace"

az servicebus namespace create --resource-group $resourceGroupName --name $namespace --location $location --sku $sku --tags $tags

Write-Host "Deployment Complete"
tools\templates\channels\topicchannel\namespace\Remove-Namespace-ServiceBus.ps1
<#
.SYNOPSIS
Removes the namespace resource.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
The resource group the namespace is in.

.PARAMETER namespace.
The name of the namespace.

.EXAMPLE
.\Remove-Namespace-ServiceBus.ps1 -namespace "sb-aimmsgbox-dev-uksouth" -resourceGroupName "rg-aimapp-systemapplication-dev-uksouth"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $namespace
)

$resourceExists = az servicebus namespace list --resource-group $resourceGroupName --query "[?name=='$namespace'].{name:name}" -o tsv

if ($resourceExists) {
    Write-Host "Removing the namespace resource: $namespace"

    az servicebus namespace delete --name $namespace --resource-group $resourceGroupName
    
    Write-Host "Removed the namespace resource: $namespace"
}
else {
    Write-Host "The namespace resource $namespace does not exist in resource group $resourceGroupName"
}
tools\templates\channels\topicchannel\namespace\TearDown-15-Namespace-ServiceBus.ps1.liquid
 
tools\templates\channels\topicchannel\New-TopicChannel-ServiceBus.ps1
<#
.SYNOPSIS
Creates a Topic Channel resource for use by various AIM components.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER namespace
Namespace to create the topic on.

.PARAMETER topic
Topic name to create in the namespace.

.PARAMETER enablePartitioning
Defines if partitioning should be enabled (true) or not on the topic.

.PARAMETER tags
The tags to apply to the namespace.

.EXAMPLE
.\New-TopicChannel-ServiceBus.ps1 -resourceGroupName "rg-aimapp-systemapplication-dev-uksouth" -namespace "sb-aimmsgbox-dev-uksouth" -topic "messagebox"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $namespace,
    [parameter(Mandatory = $true)]
    [string] $topic,
    [parameter(Mandatory = $true)]
    [bool] $enablePartitioning,
    [parameter(Mandatory = $false)]
    [string[]] $tags = ""
)

Write-Host "Deploying the topic: $topic"

az servicebus topic create --resource-group $resourceGroupName --namespace-name $namespace --name $topic --enable-partitioning $enablePartitioning

Write-Host "Deployment Complete"
tools\templates\channels\topicchannel\Remove-TopicChannel-ServiceBus.ps1
<#
.SYNOPSIS
Removes the topic channel resource.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
The resource group name.

.PARAMETER namespace
The name of the namespace the topic is on.

.PARAMETER topic.
The topic to remove.

.EXAMPLE
.\Remove-TopicChannel-ServiceBus.ps1 -$resourceName "sb-aimmsgbox-dev-uksouth" -resourceGroupName "rg-aimapp-systemapplication-dev-uksouth" -topic "messagebox"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $namespace,
    [parameter(Mandatory = $true)]
    [string] $topic
)

$namespaceResourceExists = az servicebus namespace list --resource-group $resourceGroupName --query "[?name=='$namespace'].{name:name}" -o tsv

if ($namespaceResourceExists) {

    $topicResourceExists = az servicebus topic list --resource-group $resourceGroupName --namespace-name $namespace --query "[?name=='$topic'].{name:name}" -o tsv
 
    if ($topicResourceExists) {

        Write-Host "Removing the topic resource: $topic"

        az servicebus topic delete --resource-group $resourceGroupName --namespace-name $namespace --name $topic

        Write-Host "Removed the topic resource: $topic"
    }
    else {
        Write-Host "The topic resource $topic does not exist in resource group $resourceGroupName with the namespace $namespace"
    }
}
else {
    Write-Host "The namespace $namespace does not exist in resource group $resourceGroupName when attempting to remove the topic $topic"
}
tools\templates\channels\topicchannel\subscriptions\Deploy-30-TopicChannelSubscription-ServiceBus.ps1.liquid
 
tools\templates\channels\topicchannel\subscriptions\New-TopicChannelSubscription-ServiceBus.ps1
<#
.SYNOPSIS
Creates a topic subscription and rules resources.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER name
Name of the subscription that will be created.

.PARAMETER serviceBusNamespace
Name of the Azure Service Bus namespace.

.PARAMETER serviceBusTopic
Name of the Azure Service Bus topic.

.PARAMETER serviceBusSessionsEnabled
Identifies if sessions are enabled (true) or not (false).

.PARAMETER rules
The rules to set on the subscription.

.EXAMPLE
./New-TopicChannelSubscription-ServiceBus.ps1 -resourceGroupName "rg-aimapp-app1-dev-uksouth" -name "sbs-aimmsgbox-ftp-passthru" -serviceBusNamespace "sb-aimmsgbox-dev-uksouth" -serviceBusTopic "messagebox" -serviceBusSessionsEnabled "true" -rules @{<rulesarray>}
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $name,
    [parameter(Mandatory = $true)]
    [string] $serviceBusNamespace,
    [parameter(Mandatory = $true)]
    [string] $serviceBusTopic,
    [parameter(Mandatory = $true)]
    [bool] $serviceBusSessionsEnabled,
    [parameter(Mandatory = $true)]
    [object[]] $rules
)

# --------------------------------------------------------------------------

Write-Host "Deploying the topic subscription $name"

az servicebus topic subscription create --name $name --resource-group $resourceGroupName --namespace-name $serviceBusNamespace --topic-name $serviceBusTopic --enable-session $serviceBusSessionsEnabled
if (!$?) {
    throw "Deployment failed, aborting"
}

Write-Host "Deployment complete"

# --------------------------------------------------------------------------

Write-Host "Creating rules for subscription $name"

ForEach ($rule in $rules) {
    $ruleName = $rule.name

    Write-Host "Creating rule $ruleName in subscription $name"

    az servicebus topic subscription rule create --name $ruleName --resource-group $resourceGroupName --namespace-name $serviceBusNamespace --topic-name $serviceBusTopic --subscription-name $name --filter-sql-expression $rule.expression
    if (!$?) {
        throw "Deployment failed, aborting"
    }
}

Write-Host "Created rules for subscription $name"
tools\templates\channels\topicchannel\subscriptions\Remove-TopicChannelSubscription-ServiceBus.ps1
<#
.SYNOPSIS
Removes a topic subscription.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be deleted.

.PARAMETER name
Name of the subscription that will be deleted.

.PARAMETER serviceBusNamespace
Name of the Azure Service Bus namespace.

.PARAMETER serviceBusTopic
Name of the Azure Service Bus topic.

.EXAMPLE
./Remove-TopicChannelSubscription-ServiceBus.ps1 -resourceGroupName "rg-aimapp-app1-dev-uksouth" -resourceName "sbs-aimmsgbox-ftp-passthru" -serviceBusNamespace "sb-aimmsgbox-dev-uksouth" -serviceBusTopic "messagebox"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName,
    [parameter(Mandatory = $true)]
    [string] $serviceBusNamespace,
    [parameter(Mandatory = $true)]
    [string] $serviceBusTopic
)

$resourceExists = az servicebus topic subscription show --name $resourceName --resource-group $resourceGroupName --namespace-name $serviceBusNamespace --topic-name $serviceBusTopic

if ($resourceExists) {
    Write-Host "Removing the topic subscription resource: $resourceName"

    az servicebus topic subscription delete --name $resourceName --resource-group $resourceGroupName --namespace-name $serviceBusNamespace --topic-name $serviceBusTopic

    Write-Host "Removed the topic subscription resource: $resourceName"
}
else {
    Write-Host "The topic subscription resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\channels\topicchannel\subscriptions\TearDown-30-TopicChannelSubscription-ServiceBus.ps1.liquid
 
tools\templates\channels\topicchannel\subscriptions\topicchannelsubscription.sbs.dev.psparameters.json.liquid
 
tools\templates\channels\topicchannel\subscriptions\topicchannelsubscription.sbs.prod.psparameters.json.liquid
 
tools\templates\channels\topicchannel\TearDown-20-TopicChannel-ServiceBus.ps1.liquid
 
tools\templates\channels\topicchannel\topicchannel.sb.dev.psparameters.json.liquid
 
tools\templates\channels\topicchannel\topicchannel.sb.prod.psparameters.json.liquid
 
tools\templates\deploy\consumption\Deploy-All-Unattended.bat
@ECHO OFF
SETLOCAL
SET "PowerShellCoreInstalled="
SET "PowerShellInstalled="

REM Check if PowerShell Core is installed
WHERE pwsh >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellCoreInstalled=Y"
)

REM Check if PowerShell is installed
WHERE PowerShell >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellInstalled=Y"
)

REM If PowerShell Core installed, use that
IF DEFINED PowerShellCoreInstalled (
	ECHO PowerShell Core is installed - using this to execute script.
	pwsh -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
	PAUSE
	GOTO:EOF
)

REM Check if PowerShell is installed
IF NOT DEFINED PowerShellInstalled GOTO PowerShellNotInstalled

ECHO PowerShell is installed. Checking what version is installed.

REM Get the version of PowerShell installed - this doesn't include PowerShell Core
FOR /f %%i IN ('PowerShell -command "[int]([System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor))"') DO SET PowerShellVersion=%%i

FOR /f %%i IN ('PowerShell -command "[System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, '.', (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor)"') DO SET PowerShellVersionText=%%i

REM Check the version of PowerShell installed
IF %PowerShellVersion% LEQ 62 GOTO PowerShellOldVersion

REM Use PowerShell to execute script
ECHO PowerShell v6.2+ is installed - using this to execute script.
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
PAUSE
GOTO:EOF

:PowerShellNotInstalled
ECHO Neither PowerShell nor PowerShell Core is installed on this system.
ECHO In order to run this script, you need either PowerShell v6.2+ or PowerShell Core (v7.x+).
PAUSE
GOTO:EOF

:PowerShellOldVersion
ECHO An older version of PowerShell is installed.
ECHO In order to run this script, you need at least PowerShell v6.2+.
ECHO You currently have v%PowerShellVersionText% installed.
PAUSE
GOTO:EOF

tools\templates\deploy\consumption\Deploy-All.bat
@ECHO OFF
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1'"
pause
tools\templates\deploy\consumption\Deploy-All.ps1.liquid
 
tools\templates\deploy\consumption\TearDown-All.bat
@ECHO OFF
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './TearDown-All.ps1'"
pause
tools\templates\deploy\consumption\TearDown-All.ps1.liquid
 
tools\templates\deploy\consumptionlite\Deploy-All-Unattended.bat
@ECHO OFF
SETLOCAL
SET "PowerShellCoreInstalled="
SET "PowerShellInstalled="

REM Check if PowerShell Core is installed
WHERE pwsh >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellCoreInstalled=Y"
)

REM Check if PowerShell is installed
WHERE PowerShell >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellInstalled=Y"
)

REM If PowerShell Core installed, use that
IF DEFINED PowerShellCoreInstalled (
	ECHO PowerShell Core is installed - using this to execute script.
	pwsh -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
	PAUSE
	GOTO:EOF
)

REM Check if PowerShell is installed
IF NOT DEFINED PowerShellInstalled GOTO PowerShellNotInstalled

ECHO PowerShell is installed. Checking what version is installed.

REM Get the version of PowerShell installed - this doesn't include PowerShell Core
FOR /f %%i IN ('PowerShell -command "[int]([System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor))"') DO SET PowerShellVersion=%%i

FOR /f %%i IN ('PowerShell -command "[System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, '.', (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor)"') DO SET PowerShellVersionText=%%i

REM Check the version of PowerShell installed
IF %PowerShellVersion% LEQ 62 GOTO PowerShellOldVersion

REM Use PowerShell to execute script
ECHO PowerShell v6.2+ is installed - using this to execute script.
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
PAUSE
GOTO:EOF

:PowerShellNotInstalled
ECHO Neither PowerShell nor PowerShell Core is installed on this system.
ECHO In order to run this script, you need either PowerShell v6.2+ or PowerShell Core (v7.x+).
PAUSE
GOTO:EOF

:PowerShellOldVersion
ECHO An older version of PowerShell is installed.
ECHO In order to run this script, you need at least PowerShell v6.2+.
ECHO You currently have v%PowerShellVersionText% installed.
PAUSE
GOTO:EOF

tools\templates\deploy\consumptionlite\Deploy-All.bat
@ECHO OFF
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1'"
pause
tools\templates\deploy\consumptionlite\Deploy-All.ps1.liquid
 
tools\templates\deploy\consumptionlite\TearDown-All.bat
@ECHO OFF
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './TearDown-All.ps1'"
pause
tools\templates\deploy\consumptionlite\TearDown-All.ps1.liquid
 
tools\templates\deploy\standard\Deploy-All-Unattended.bat
@ECHO OFF
SETLOCAL
SET "PowerShellCoreInstalled="
SET "PowerShellInstalled="

REM Check if PowerShell Core is installed
WHERE pwsh >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellCoreInstalled=Y"
)

REM Check if PowerShell is installed
WHERE PowerShell >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellInstalled=Y"
)

REM If PowerShell Core installed, use that
IF DEFINED PowerShellCoreInstalled (
	ECHO PowerShell Core is installed - using this to execute script.
	pwsh -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
	PAUSE
	GOTO:EOF
)

REM Check if PowerShell is installed
IF NOT DEFINED PowerShellInstalled GOTO PowerShellNotInstalled

ECHO PowerShell is installed. Checking what version is installed.

REM Get the version of PowerShell installed - this doesn't include PowerShell Core
FOR /f %%i IN ('PowerShell -command "[int]([System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor))"') DO SET PowerShellVersion=%%i

FOR /f %%i IN ('PowerShell -command "[System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, '.', (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor)"') DO SET PowerShellVersionText=%%i

REM Check the version of PowerShell installed
IF %PowerShellVersion% LEQ 62 GOTO PowerShellOldVersion

REM Use PowerShell to execute script
ECHO PowerShell v6.2+ is installed - using this to execute script.
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
PAUSE
GOTO:EOF

:PowerShellNotInstalled
ECHO Neither PowerShell nor PowerShell Core is installed on this system.
ECHO In order to run this script, you need either PowerShell v6.2+ or PowerShell Core (v7.x+).
PAUSE
GOTO:EOF

:PowerShellOldVersion
ECHO An older version of PowerShell is installed.
ECHO In order to run this script, you need at least PowerShell v6.2+.
ECHO You currently have v%PowerShellVersionText% installed.
PAUSE
GOTO:EOF

tools\templates\deploy\standard\Deploy-All.bat
@ECHO OFF
SETLOCAL
SET "PowerShellCoreInstalled="
SET "PowerShellInstalled="

REM Check if PowerShell Core is installed
WHERE pwsh >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellCoreInstalled=Y"
)

REM Check if PowerShell is installed
WHERE PowerShell >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellInstalled=Y"
)

REM If PowerShell Core installed, use that
IF DEFINED PowerShellCoreInstalled (
	ECHO PowerShell Core is installed - using this to execute script.
	pwsh -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1'"
	PAUSE
	GOTO:EOF
)

REM Check if PowerShell is installed
IF NOT DEFINED PowerShellInstalled GOTO PowerShellNotInstalled

ECHO PowerShell is installed. Checking what version is installed.

REM Get the version of PowerShell installed - this doesn't include PowerShell Core
FOR /f %%i IN ('PowerShell -command "[int]([System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor))"') DO SET PowerShellVersion=%%i

FOR /f %%i IN ('PowerShell -command "[System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, '.', (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor)"') DO SET PowerShellVersionText=%%i

REM Check the version of PowerShell installed
IF %PowerShellVersion% LEQ 62 GOTO PowerShellOldVersion

REM Use PowerShell to execute script
ECHO PowerShell v6.2+ is installed - using this to execute script.
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1'"
PAUSE
GOTO:EOF

:PowerShellNotInstalled
ECHO Neither PowerShell nor PowerShell Core is installed on this system.
ECHO In order to run this script, you need either PowerShell v6.2+ or PowerShell Core (v7.x+).
PAUSE
GOTO:EOF

:PowerShellOldVersion
ECHO An older version of PowerShell is installed.
ECHO In order to run this script, you need at least PowerShell v6.2+.
ECHO You currently have v%PowerShellVersionText% installed.
PAUSE
GOTO:EOF

tools\templates\deploy\standard\Deploy-All.ps1.liquid
 
tools\templates\deploy\standard\TearDown-All.bat
@ECHO OFF
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './TearDown-All.ps1'"
pause
tools\templates\deploy\standard\TearDown-All.ps1.liquid
 
tools\templates\deploy\standardlite\Deploy-All-Unattended.bat
@ECHO OFF
SETLOCAL
SET "PowerShellCoreInstalled="
SET "PowerShellInstalled="

REM Check if PowerShell Core is installed
WHERE pwsh >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellCoreInstalled=Y"
)

REM Check if PowerShell is installed
WHERE PowerShell >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellInstalled=Y"
)

REM If PowerShell Core installed, use that
IF DEFINED PowerShellCoreInstalled (
	ECHO PowerShell Core is installed - using this to execute script.
	pwsh -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
	PAUSE
	GOTO:EOF
)

REM Check if PowerShell is installed
IF NOT DEFINED PowerShellInstalled GOTO PowerShellNotInstalled

ECHO PowerShell is installed. Checking what version is installed.

REM Get the version of PowerShell installed - this doesn't include PowerShell Core
FOR /f %%i IN ('PowerShell -command "[int]([System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor))"') DO SET PowerShellVersion=%%i

FOR /f %%i IN ('PowerShell -command "[System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, '.', (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor)"') DO SET PowerShellVersionText=%%i

REM Check the version of PowerShell installed
IF %PowerShellVersion% LEQ 62 GOTO PowerShellOldVersion

REM Use PowerShell to execute script
ECHO PowerShell v6.2+ is installed - using this to execute script.
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1' -runUnattended 1"
PAUSE
GOTO:EOF

:PowerShellNotInstalled
ECHO Neither PowerShell nor PowerShell Core is installed on this system.
ECHO In order to run this script, you need either PowerShell v6.2+ or PowerShell Core (v7.x+).
PAUSE
GOTO:EOF

:PowerShellOldVersion
ECHO An older version of PowerShell is installed.
ECHO In order to run this script, you need at least PowerShell v6.2+.
ECHO You currently have v%PowerShellVersionText% installed.
PAUSE
GOTO:EOF

tools\templates\deploy\standardlite\Deploy-All.bat
@ECHO OFF
SETLOCAL
SET "PowerShellCoreInstalled="
SET "PowerShellInstalled="

REM Check if PowerShell Core is installed
WHERE pwsh >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellCoreInstalled=Y"
)

REM Check if PowerShell is installed
WHERE PowerShell >nul 2>nul
IF %ERRORLEVEL% EQU 0 (
	SET "PowerShellInstalled=Y"
)

REM If PowerShell Core installed, use that
IF DEFINED PowerShellCoreInstalled (
	ECHO PowerShell Core is installed - using this to execute script.
	pwsh -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1'"
	PAUSE
	GOTO:EOF
)

REM Check if PowerShell is installed
IF NOT DEFINED PowerShellInstalled GOTO PowerShellNotInstalled

ECHO PowerShell is installed. Checking what version is installed.

REM Get the version of PowerShell installed - this doesn't include PowerShell Core
FOR /f %%i IN ('PowerShell -command "[int]([System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor))"') DO SET PowerShellVersion=%%i

FOR /f %%i IN ('PowerShell -command "[System.String]::Concat((Get-Variable PSVersionTable -ValueOnly).PSVersion.Major, '.', (Get-Variable PSVersionTable -ValueOnly).PSVersion.Minor)"') DO SET PowerShellVersionText=%%i

REM Check the version of PowerShell installed
IF %PowerShellVersion% LEQ 62 GOTO PowerShellOldVersion

REM Use PowerShell to execute script
ECHO PowerShell v6.2+ is installed - using this to execute script.
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './Deploy-All.ps1'"
PAUSE
GOTO:EOF

:PowerShellNotInstalled
ECHO Neither PowerShell nor PowerShell Core is installed on this system.
ECHO In order to run this script, you need either PowerShell v6.2+ or PowerShell Core (v7.x+).
PAUSE
GOTO:EOF

:PowerShellOldVersion
ECHO An older version of PowerShell is installed.
ECHO In order to run this script, you need at least PowerShell v6.2+.
ECHO You currently have v%PowerShellVersionText% installed.
PAUSE
GOTO:EOF

tools\templates\deploy\standardlite\Deploy-All.ps1.liquid
 
tools\templates\deploy\standardlite\TearDown-All.bat
@ECHO OFF
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& './TearDown-All.ps1'"
pause
tools\templates\deploy\standardlite\TearDown-All.ps1.liquid
 
tools\templates\endpoints\file\datagateway\datagateway.onpremisedatagateway.dev.parameters.json.liquid
 
tools\templates\endpoints\file\datagateway\datagateway.onpremisedatagateway.dev.psparameters.json.liquid
 
tools\templates\endpoints\file\datagateway\datagateway.onpremisedatagateway.json
{
    "$schema": "https://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "dataGatewayName": {
            "type": "String"
        },
        "dataGatewayLocation": {
            "type": "String"
        },
        "connectionGatewayInstallationId": {
            "type": "String"
        },
        "connectionGatewayInstallationLocation": {
            "type": "String"
        },
        "tags": {
            "type": "object"
        }
    },
    "resources": [
        {
            "type": "Microsoft.Web/connectionGateways",
            "name": "[parameters('dataGatewayName')]",
            "apiVersion": "2016-06-01",
            "location": "[parameters('dataGatewayLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "connectionGatewayInstallation": {
                    "id": "[concat(subscription().id, '/providers/Microsoft.Web/locations/', parameters('connectionGatewayInstallationLocation'), '/connectionGatewayInstallations/', parameters('connectionGatewayInstallationId'))]"
                }
            }
        }
    ],
    "outputs": {
    }
}
tools\templates\endpoints\file\datagateway\datagateway.onpremisedatagateway.prod.parameters.json.liquid
 
tools\templates\endpoints\file\datagateway\datagateway.onpremisedatagateway.prod.psparameters.json.liquid
 
tools\templates\endpoints\file\datagateway\Deploy-30-DataGateway.ps1.liquid
 
tools\templates\endpoints\file\datagateway\New-DataGateway.ps1
<#
.SYNOPSIS
Creates an on-premise data gateway.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
The name of the Azure resource group to deploy the data gateway to.

.PARAMETER subscriptionId
"<azure-subs-id>"

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER connectionGatewayInstallationDisplayName
The name of the connection gateway installation to link the new data gateway to.

.PARAMETER connectionGatewayInstallationLocation
The location of the connection gateway installation to link the new data gateway to.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.
    
.EXAMPLE
.\New-DataGateway.ps1 -resourceGroupName $params.resourceGroupName -subscriptionId "<azure-subs-id>" -connectionGatewayInstallationDisplayName "cgw-aimmsgbus-dev-uksouth-xxxx" -connectionGatewayInstallationLocation "uksouth" -templateFile "datagateway.onpremisedatagateway.json" -templateParameterFile "datagateway.onpremisedatagateway.dev.parameters.json" -deploymentName "datagateway.uksouth.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [AllowNull()]
    [AllowEmptyString()]
    [string] $subscriptionId,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,        
    [parameter(Mandatory = $true)]    
    [string] $connectionGatewayInstallationDisplayName,
    [parameter(Mandatory = $true)]    
    [string] $connectionGatewayInstallationLocation,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

if ($subscriptionId -eq "") {
    Write-Host "No Azure subscription ID specified, finding from current active subscription"

    $subscriptionId = az account show | ConvertFrom-Json | Select-Object -ExpandProperty id
    
    if ($subscriptionId) {
        Write-Host "Found subscription ID $subscriptionId"
    }
    else {
        throw "No subscription ID found, an active subscription may not have been set in the Azure CLI"
    }
}

$connectionGatewayInstallationName = az rest --method get --uri /subscriptions/$subscriptionId/providers/Microsoft.Web/locations/$connectionGatewayInstallationLocation/connectionGatewayInstallations?api-version=2016-06-01 --query "value[?properties.displayName=='$connectionGatewayInstallationDisplayName'].{Name:name} | [0]" -o tsv

if ($connectionGatewayInstallationName -eq "") {
    throw "No connection gateway installation found in location: $connectionGatewayInstallationLocation with the display name: $connectionGatewayInstallationDisplayName "
}

Write-Host "Deploying the data gateway `r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName" 

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --parameters "connectionGatewayInstallationId=$connectionGatewayInstallationName" --parameters "connectionGatewayInstallationLocation=$connectionGatewayInstallationLocation" --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\datagateway\Remove-DataGateway.ps1
<#
.SYNOPSIS
Removes an on-premise data gateway,.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
The name of the resource group name the connection gateway exists in.

.PARAMETER dataGatewayName
The name of the data gateway to remove.

.EXAMPLE
.\Remove-DataGateway.ps1 -resourceGroupName "rg-aimmsgbus-dev" -dataGatewayName "cgw-aimmsgbus-dev-uksouth-xxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $dataGatewayName
)

$resourceExists = az resource show --resource-group $resourceGroupName  --name $dataGatewayName --namespace "Microsoft.Web" --resource-type "connectionGateways"

if ($resourceExists) {
    Write-Host "Removing the On-premises Data Gateway $dataGatewayName"

    az resource delete --resource-group $resourceGroupName --name $dataGatewayName --namespace "Microsoft.Web" --resource-type "connectionGateways"

    Write-Host "Removed the On-premises Data Gateway $dataGatewayName"
}
else {
    Write-Host "The On-premises Data Gateway $dataGatewayName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\file\datagateway\TearDown-30-DataGateway.ps1.liquid
 
tools\templates\endpoints\file\receive\Deploy-100-FileReceiveAdapterFileSystem-ApiConnection.ps1.liquid
 
tools\templates\endpoints\file\receive\Deploy-100-FileReceiveAdapterServiceBus-ApiConnection.ps1.liquid
 
tools\templates\endpoints\file\receive\Deploy-105-FileReceiveAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\file\receive\Deploy-110-FileReceiveAdapterFileSystem-ApiConnPolicy.ps1.liquid
 
tools\templates\endpoints\file\receive\Deploy-110-FileReceiveAdapterServiceBus-ApiConnPolicy.ps1.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapter.logicapp.dev.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapter.logicapp.json
{
    "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "logicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of this LogicApp."
            }
        },
        "logicAppLocation": {
            "defaultValue": "[resourceGroup().location]",
            "type": "string",
            "metadata": {
                "description": "Location (region) or ISE that this LogicApp is to be deployed to. Defaults to the ResourceGroup location."
            }
        },
        "logicApStartupState": {
            "type": "string",
            "defaultValue": "Enabled",
            "allowedValues": [ "Enabled", "Disabled" ],
            "metadata": {
                "description": "Initial state of the LogicApp after it is deployed."
            }
        },
        "messageBusResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that MessageBus artifacts are deployed to (e.g. APIM or RoutingSlipRouter LogicApp)."
            }
        },
        "systemApplicationResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that SystemApplication artifacts are deployed to (e.g. ServiceBus or MessageConstructor LogicApp)."
            }
        },
        "integrationAccountName": {
            "type": "string",
            "metadata": {
                "description": "Name of the IntegrationAccount connected to this LogicApp."
            }
        },
        "messageConstructorLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to handle File Message Construction and Sending."
            }
        },
        "messageSuspendProcessorLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to handle suspending of messages."
            }
        },
        "suspendQueueTopicName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ServiceBus Topic that suspended messages are sent to."
            }
        },
        "apimServiceName": {
            "type": "string",
            "metadata": {
                "description": "Name of the APIM Service used for MessageBus operations."
            }
        },
        "apimSubscriptionKey": {
            "type": "securestring",
            "metadata": {
                "description": "Subscription Key used to access APIM."
            }
        },
        "apimRetryPolicy": {
            "type": "object",
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "metadata": {
                "description": "Retry Policy to use when calling APIM."
            }
        },
        "fileSystemReceiveApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for Filesystem Receive operations."
            }
        },
        "fileReceiveFolder": {
            "type": "string",
            "metadata": {
                "description": "The path where the File connector looks for new/updated files."
            }
        },
        "fileMaxFileCount": {
            "defaultValue": 10,
            "type": "int",
            "metadata": {
                "description": "The max number of files the File Connector will retrieve per polling interval."
            }
        },
        "fileRecurrenceFrequency": {
            "type": "string",
            "allowedValues": [ "Second", "Minute", "Hour", "Day", "Month", "Year" ],
            "metadata": {
                "description": "The frequency with which to check for new files on the File server."
            }
        },
        "fileRecurrenceInterval": {
            "type": "int",
            "metadata": {
                "description": "The interval with which to check for new files on the File server."
            }
        },
        "serviceBusTopicPublishApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for ServiceBus SuspendQueue Publish operations."
            }
        },
        "scenario": {
            "type": "string",
            "metadata": {
                "description": "The name of the Scenario that this LogicApp is running under e.g. ApplicationName + ReceivePort/Location Name."
            }
        },
        "scenarioStep": {
            "defaultValue": "fileReceiveAdapter",
            "type": "string",
            "metadata": {
                "description": "The step within a Scenario that this LogicApp is running under e.g. fileReceiveAdapter."
            }
        },
        "tags": {
            "type": "object"
        }
    },
    "variables": {
        "apimServiceResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.ApiManagement/service', parameters('apimServiceName'))]",
        "configurationManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimconfigurationmanager')]",
        "messageConstructorLogicAppResourceId": "[resourceId(parameters('systemApplicationResourceGroupName'), 'Microsoft.Logic/workflows', parameters('messageConstructorLogicAppName'))]",
        "messageSuspendProcessorLogicAppResourceId": "[resourceId(parameters('systemApplicationResourceGroupName'), 'Microsoft.Logic/workflows', parameters('messageSuspendProcessorLogicAppName'))]",
        "fileSystemApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('fileSystemReceiveApiConnectionName'))]",
        "integrationAccountResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.Logic/integrationAccounts', parameters('integrationAccountName'))]",
        "serviceBusTopicPublishApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('serviceBusTopicPublishApiConnectionName'))]"
    },
    "resources": [
        {
            "type": "Microsoft.Logic/workflows",
            "apiVersion": "2017-07-01",
            "name": "[parameters('logicAppName')]",
            "location": "[parameters('logicAppLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "state": "[parameters('logicApStartupState')]",
                "integrationAccount": {
                    "id": "[variables('integrationAccountResourceId')]"
                },
                "definition": {
                    "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
                    "contentVersion": "1.0.0.0",
                    "parameters": {
                        "$connections": {
                            "defaultValue": {},
                            "type": "Object"
                        },
                        "fileReceiveFolder": {
                            "type": "String",
                            "description": "The path where the File connector looks for new/updated files."
                        },
                        "fileMaxFileCount": {
                            "type": "Int",
                            "description": "The max number of files the File Connector will retrieve per polling interval."
                        },
                        "fileRecurrenceFrequency": {
                            "type": "string",
                            "allowedValues": [ "Second", "Minute", "Hour", "Day", "Month", "Year" ],
                            "description": "The frequency with which to check for new files on the File server."
                        },
                        "fileRecurrenceInterval": {
                            "type": "int",
                            "description": "The interval with which to check for new files on the File server."
                        },
                        "apimSubscriptionKey": {
                            "type": "SecureString",
                            "description": "Subscription Key used to access APIM."
                        },
                        "scenario": {
                            "type": "String",
                            "description": "The name of the Scenario that this LogicApp is running under e.g. ApplicationName + ReceivePort/Location Name."
                        },
                        "scenarioStep": {
                            "type": "String",
                            "description": "The step within a Scenario that this LogicApp is running under e.g. FileReceiveAdapter."
                        },
                        "clearCache": {
                            "defaultValue": true,
                            "type": "Bool",
                            "description": "Indicates if we should clear APIM cache before retrieved config items e.g. configurationEntries or routingSlips."
                        },
                        "suspendQueueTopicName": {
                            "type": "String",
                            "description": "Name of the ServiceBus Topic that suspended messages are sent to."
                        }
                    },
                    "triggers": {
                        "When_a_file_is_added_or_modified_(properties_only)": {
                            "inputs": {
                                "host": {
                                    "connection": {
                                        "name": "@parameters('$connections')['filesystemreceive']['connectionId']"
                                    }
                                },
                                "method": "get",
                                "path": "/datasets/default/triggers/batch/onupdatedfile",
                                "queries": {
                                    "folderId": "@{parameters('fileReceiveFolder')}",
                                    "maxFileCount": "@parameters('fileMaxFileCount')"
                                }
                            },
                            "recurrence": {
                                "frequency": "@parameters('fileRecurrenceFrequency')",
                                "interval": "@parameters('fileRecurrenceInterval')"
                            },
                            "splitOn": "@triggerBody()",
                            "type": "ApiConnection"
                        }
                    },
                    "actions": {
                        "Initialize_StatusCode_variable": {
                            "runAfter": {},
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "StatusCode",
                                        "type": "integer",
                                        "value": 500
                                    }
                                ]
                            }
                        },
                        "Initialize_FaultMessage_variable": {
                            "runAfter": {
                                "Initialize_StatusCode_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "FaultMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_ErrorMessage_variable": {
                            "runAfter": {
                                "Initialize_FaultMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ErrorMessage",
                                        "type": "string",
                                        "value": "An error occurred in the @{workflow()?['name']} (@{workflow()?['run']?['name']}) LogicApp"
                                    }
                                ]
                            }
                        },
                        "Initialize_ResponseMessage_variable": {
                            "runAfter": {
                                "Initialize_ErrorMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ResponseMessage",
                                        "type": "object",
                                        "value": null
                                    }
                                ]
                            }
                        },
                        "Initialize_Checkpoint_variable": {
                            "runAfter": {
                                "Initialize_ResponseMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Checkpoint",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_Configuration_variable": {
                            "runAfter": {
                                "Initialize_Checkpoint_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Configuration",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Compose_FileNameMask": {
                            "runAfter": {
                                "Initialize_Configuration_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "Compose",
                            "inputs": "@{coalesce(variables('Configuration')?['scenarioStep']?['fileNameMask'], '*.*')}"
                        },
                        "Respond:_Were_we_successful": {
                            "actions": {
                                "Terminate_with_ACK": {
                                    "runAfter": {},
                                    "type": "Terminate",
                                    "inputs": {
                                        "runStatus": "Succeeded"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Construct_Message": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "else": {
                                "actions": {
                                    "Failure:_Do_we_have_a_NACK": {
                                        "actions": {},
                                        "runAfter": {},
                                        "else": {
                                            "actions": {
                                                "Failure:_Build_NACK_message": {
                                                    "runAfter": {},
                                                    "type": "Compose",
                                                    "inputs": {
                                                        "body": [
                                                            {
                                                                "$content": {
                                                                    "code": "500",
                                                                    "message": "@variables('ErrorMessage')",
                                                                    "lastCheckpoint": "@variables('Checkpoint')",
                                                                    "fault": "@variables('FaultMessage')"
                                                                },
                                                                "$contentType": "application/json",
                                                                "$part": 1,
                                                                "$partType": "http://schemas.microsoft.com/aim#nack"
                                                            }
                                                        ],
                                                        "header": {
                                                            "properties": {
                                                                "createDate": "@utcNow()",
                                                                "envelopeType": "nack",
                                                                "messageId": "@guid()",
                                                                "rootPart": 1,
                                                                "trackingId": "@triggerBody()?['header']?['properties']?['trackingId']"
                                                            },
                                                            "routing": {
                                                                "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                            },
                                                            "routingSlip": {},
                                                            "state": {}
                                                        }
                                                    }
                                                },
                                                "Failure:_Set_ResponseMessage_variable": {
                                                    "runAfter": {
                                                        "Failure:_Build_NACK_message": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "ResponseMessage",
                                                        "value": "@outputs('Failure:_Build_NACK_message')"
                                                    }
                                                }
                                            }
                                        },
                                        "expression": {
                                            "and": [
                                                {
                                                    "equals": [
                                                        "@{coalesce(variables('ResponseMessage')?['header']?['properties']?['envelopeType'], '(unknown)')}",
                                                        "nack"
                                                    ]
                                                }
                                            ]
                                        },
                                        "type": "If"
                                    },
                                    "Failure:_Send_NACK_to_SuspendQueue": {
                                        "runAfter": {
                                            "Failure:_Do_we_have_a_NACK": [
                                                "Succeeded"
                                            ]
                                        },
                                        "type": "Workflow",
                                        "inputs": {
                                            "body": {
                                                "nackMessage": "@variables('ResponseMessage')",
                                                "originalMessage": "@triggerBody()",
                                                "suspendQueueTopicName": "@{parameters('suspendQueueTopicName')}",
                                                "failedMessageRouting": "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['failedMessageRouting'], false)",
                                                "scenario": "@{parameters('scenario')}"
                                            },
                                            "headers": {
                                                "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                            },
                                            "host": {
                                                "triggerName": "manual",
                                                "workflow": {
                                                    "id": "[variables('messageSuspendProcessorLogicAppResourceId')]"
                                                }
                                            }
                                        }
                                    },
                                    "Terminate_with_NACK": {
                                        "runAfter": {
                                            "Failure:_Send_NACK_to_SuspendQueue": [
                                                "Succeeded",
                                                "Failed",
                                                "TimedOut"
                                            ]
                                        },
                                        "type": "Terminate",
                                        "inputs": {
                                            "runError": {
                                                "code": "@{coalesce(variables('ResponseMessage')?['body']?[0]?['$content']?['code'], '500')}",
                                                "message": "@{coalesce(variables('ResponseMessage')?['body']?[0]?['$content']?['message'], '(unknown error)')}"
                                            },
                                            "runStatus": "Failed"
                                        }
                                    }
                                }
                            },
                            "expression": {
                                "or": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "IgnoreFile"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "ConstructMessageACK"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_Configuration": {
                            "actions": {
                                "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": {
                                    "runAfter": {},
                                    "type": "ApiManagement",
                                    "inputs": {
                                        "api": {
                                            "id": "[variables('configurationManagerApiResourceId')]"
                                        },
                                        "method": "get",
                                        "pathTemplate": {
                                            "parameters": {
                                                "scenario": "@{encodeURIComponent(parameters('scenario'))}",
                                                "step": "@{encodeURIComponent(parameters('scenarioStep'))}"
                                            },
                                            "template": "/aimconfigurationmanager/configuration/{scenario}/{step}"
                                        },
                                        "queries": {
                                            "clearCache": "@parameters('clearCache')"
                                        },
                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                    }
                                },
                                "GetConfiguration:_Check_Status_Code": {
                                    "runAfter": {
                                        "GetConfiguration:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "GetConfiguration:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {
                                                        "GetConfiguration:Success:_Set_Configuration_variable": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "GetConfiguration"
                                                    }
                                                },
                                                "GetConfiguration:Success:_Set_Configuration_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Configuration",
                                                        "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "GetConfiguration:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "GetConfiguration:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "GetConfiguration:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                        }
                                                    },
                                                    "GetConfiguration:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "GetConfiguration:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['statusCode'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['message'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('GetConfiguration:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "GetConfiguration:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Compose_FileNameMask": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            ""
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Validate_Configuration": {
                            "actions": {
                                "ValidateConfiguration:_Have_Valid_Properties": {
                                    "actions": {
                                        "ValidateConfiguration:Success:_Set_Checkpoint_variable": {
                                            "runAfter": {},
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "Checkpoint",
                                                "value": "ValidateConfiguration"
                                            }
                                        }
                                    },
                                    "runAfter": {},
                                    "else": {
                                        "actions": {
                                            "ValidateConfiguration:Failure:_Set_Checkpoint_variable": {
                                                "runAfter": {},
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ErrorMessage",
                                                    "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}): property btsReceivePortName is not set in configuration"
                                                }
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "not": {
                                                    "equals": [
                                                        "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['btsReceivePortName'], '')",
                                                        ""
                                                    ]
                                                }
                                            }
                                        ]
                                    },
                                    "type": "If"
                                }
                            },
                            "runAfter": {
                                "Step:_Get_Configuration": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetConfiguration"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Should_we_process_file": {
                            "actions": {
                                "ShouldWeProcessFile:_Check_FileMask": {
                                    "inputs": {
                                        "code": "var escapedFileMask = workflowContext.actions.Compose_FileNameMask.outputs;\r\nvar fileMaskRegex = \"^\" + escapedFileMask.replace(\".\", \"[.]\").replace(\"*\", \".*\").replace(\"?\", \".\") + \"$\";\r\nreturn workflowContext.trigger.outputs.body.Name.match(fileMaskRegex) !== null;"
                                    },
                                    "runAfter": {},
                                    "type": "JavaScriptCode"
                                },
                                "ShouldWeProcessFile:Failure:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "ShouldWeProcessFile:_Check_FileMask": [
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": 500
                                    }
                                },
                                "ShouldWeProcessFile:Success:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "ShouldWeProcessFile:_Check_FileMask": [
                                            "Succeeded"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": 200
                                    }
                                },
                                "ShouldWeProcessFile:_Check_StatusCode": {
                                    "runAfter": {
                                        "ShouldWeProcessFile:Failure:_Set_StatusCode_variable": [
                                            "Succeeded",
                                            "Skipped"
                                        ],
                                        "ShouldWeProcessFile:Success:_Set_StatusCode_variable": [
                                            "Succeeded",
                                            "Skipped"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "ShouldWeProcessFile:Success:_Does_FileMask_match": {
                                                    "actions": {
                                                        "ShouldWeProcessFile:Process:_Set_Checkpoint_variable": {
                                                            "runAfter": {},
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "Checkpoint",
                                                                "value": "ProcessFile"
                                                            }
                                                        }
                                                    },
                                                    "runAfter": {},
                                                    "else": {
                                                        "actions": {
                                                            "ShouldWeProcessFile:Ignore:_Set_Checkpoint_variable": {
                                                                "runAfter": {},
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "Checkpoint",
                                                                    "value": "IgnoreFile"
                                                                }
                                                            }
                                                        }
                                                    },
                                                    "expression": {
                                                        "and": [
                                                            {
                                                                "equals": [
                                                                    "@outputs('ShouldWeProcessFile:_Check_FileMask')?['body']",
                                                                    true
                                                                ]
                                                            }
                                                        ]
                                                    },
                                                    "type": "If"
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "ShouldWeProcessFile:Failure:_Create_Fault_message": {
                                                "runAfter": {},
                                                "type": "Compose",
                                                "inputs": {
                                                    "fault": {
                                                        "faultActor": "@concat(workflow()?['name'], '.', actions('ShouldWeProcessFile:_Check_FileMask')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                        "faultCategory": "Error",
                                                        "faultCode": "@{coalesce(outputs('ShouldWeProcessFile:_Check_FileMask')?['statusCode'], outputs('ShouldWeProcessFile:_Check_FileMask')?['body']?['statusCode'], actions('ShouldWeProcessFile:_Check_FileMask')?['error']?['code'])}",
                                                        "faultMessage": "@{coalesce(outputs('ShouldWeProcessFile:_Check_FileMask')?['error']?['message'], outputs('ShouldWeProcessFile:_Check_FileMask')?['body']?['message'], actions('ShouldWeProcessFile:_Check_FileMask')?['error']?['message'])}",
                                                        "faultReason": "@{actions('ShouldWeProcessFile:_Check_FileMask')?['status']}"
                                                    }
                                                }
                                            },
                                            "ShouldWeProcessFile:Failure:_Set_ErrorMessage_variable": {
                                                "runAfter": {
                                                    "ShouldWeProcessFile:Failure:_Set_FaultMessage_variable": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ErrorMessage",
                                                    "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to execute the FileMask Javascript"
                                                }
                                            },
                                            "ShouldWeProcessFile:Failure:_Set_FaultMessage_variable": {
                                                "runAfter": {
                                                    "ShouldWeProcessFile:Failure:_Create_Fault_message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "FaultMessage",
                                                    "value": "@outputs('ShouldWeProcessFile:Failure:_Create_Fault_message')"
                                                }
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                }
                            },
                            "runAfter": {
                                "Step:_Validate_Configuration": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "ValidateConfiguration"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Construct_Message": {
                            "actions": {
                                "ConstructMessage:_Call_MessageConstructor": {
                                    "runAfter": {
                                        "ConstructMessage:_Get_file_content": [
                                            "Succeeded"
                                        ]
                                    },
                                    "type": "Workflow",
                                    "inputs": {
                                        "body": {
                                            "$content": "@{body('ConstructMessage:_Get_file_content')}",
                                            "$contentTransferEncoding": "none",
                                            "$contentType": "@triggerBody()?['MediaType']",
                                            "properties": {
                                                "receivedFileName": "@{triggerBody()?['Name']}",
                                                "scenario": "@{parameters('scenario')}",
                                                "btsReceivePortName": "@{coalesce(variables('Configuration')?[parameters('scenarioStep')]?['btsReceivePortName'], '(unknownReceivePortName)')}",
                                                "btsReceivePortId": "@{coalesce(variables('Configuration')?[parameters('scenarioStep')]?['btsReceivePortId'], '(unknownReceivePortId)')}"
                                            }
                                        },
                                        "headers": {
                                            "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                            "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                        },
                                        "host": {
                                            "triggerName": "manual",
                                            "workflow": {
                                                "id": "[variables('messageConstructorLogicAppResourceId')]"
                                            }
                                        }
                                    }
                                },
                                "ConstructMessage:_Check_StatusCode": {
                                    "runAfter": {
                                        "ConstructMessage:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "ConstructMessage:Success:_Check_EnvelopeType": {
                                                    "runAfter": {},
                                                    "cases": {
                                                        "ACK": {
                                                            "case": "ack",
                                                            "actions": {
                                                                "ACK:_Set_ResponseMessage_variable": {
                                                                    "runAfter": {},
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "ResponseMessage",
                                                                        "value": "@body('ConstructMessage:_Call_MessageConstructor')"
                                                                    }
                                                                },
                                                                "ACK:_Set_Checkpoint_variable": {
                                                                    "runAfter": {
                                                                        "ACK:_Set_ResponseMessage_variable": [
                                                                            "Succeeded"
                                                                        ]
                                                                    },
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "Checkpoint",
                                                                        "value": "ConstructMessageACK"
                                                                    }
                                                                }
                                                            }
                                                        },
                                                        "NACK": {
                                                            "case": "nack",
                                                            "actions": {
                                                                "NACK:_Set_ResponseMessage_variable": {
                                                                    "runAfter": {},
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "ResponseMessage",
                                                                        "value": "@body('ConstructMessage:_Call_MessageConstructor')"
                                                                    }
                                                                },
                                                                "NACK:_Set_Checkpoint_variable": {
                                                                    "runAfter": {
                                                                        "NACK:_Set_ResponseMessage_variable": [
                                                                            "Succeeded"
                                                                        ]
                                                                    },
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "Checkpoint",
                                                                        "value": "ConstructMessageNACK"
                                                                    }
                                                                }
                                                            }
                                                        }
                                                    },
                                                    "default": {
                                                        "actions": {
                                                            "ConstructMessage:UnknownEnvelope:_Compose_NACK_Message": {
                                                                "runAfter": {},
                                                                "type": "Compose",
                                                                "inputs": {
                                                                    "body": [
                                                                        {
                                                                            "$content": {
                                                                                "code": "500",
                                                                                "message": "@concat('Body returned by action ', actions('ConstructMessage:_Call_MessageConstructor')?['name'], ' is not an ACK or NACK. Envelope type is: ', coalesce(body('ConstructMessage:_Call_MessageConstructor')?['header']?['properties']?['envelopeType'], '(unknown)'))"
                                                                            },
                                                                            "$contentType": "application/json",
                                                                            "$part": 1,
                                                                            "$partType": "http://schemas.microsoft.com/aim#nack"
                                                                        }
                                                                    ],
                                                                    "header": {
                                                                        "properties": {
                                                                            "createDate": "@utcNow()",
                                                                            "envelopeType": "nack",
                                                                            "messageId": "@guid()",
                                                                            "rootPart": 1,
                                                                            "trackingId": ""
                                                                        },
                                                                        "routing": {
                                                                            "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                                        },
                                                                        "routingSlip": {},
                                                                        "state": {}
                                                                    }
                                                                }
                                                            },
                                                            "ConstructMessage:UnknownEnvelope:_Set_ResponseMessage_variable": {
                                                                "runAfter": {
                                                                    "ConstructMessage:UnknownEnvelope:_Compose_NACK_Message": [
                                                                        "Succeeded"
                                                                    ]
                                                                },
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "ResponseMessage",
                                                                    "value": "@outputs('ConstructMessage:UnknownEnvelope:_Compose_NACK_Message')"
                                                                }
                                                            },
                                                            "ConstructMessage:UnknownEnvelope:_Set_Checkpoint_variable": {
                                                                "runAfter": {
                                                                    "ConstructMessage:UnknownEnvelope:_Set_ResponseMessage_variable": [
                                                                        "Succeeded"
                                                                    ]
                                                                },
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "Checkpoint",
                                                                    "value": "ConstructMessageNACK"
                                                                }
                                                            }
                                                        }
                                                    },
                                                    "expression": "@body('ConstructMessage:_Call_MessageConstructor')?['header']?['properties']?['envelopeType']",
                                                    "type": "Switch"
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "ConstructMessage:Failure:_Create_NACK_Message": {
                                                "runAfter": {},
                                                "type": "Compose",
                                                "inputs": {
                                                    "body": [
                                                        {
                                                            "$content": {
                                                                "code": "500",
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('ConstructMessage:_Call_MessageConstructor')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('ConstructMessage:_Call_MessageConstructor')?['statusCode'], outputs('ConstructMessage:_Call_MessageConstructor')?['body']?['statusCode'])}",
                                                                    "faultMessage": "@{coalesce(outputs('ConstructMessage:_Call_MessageConstructor')?['error']?['message'], outputs('ConstructMessage:_Call_MessageConstructor')?['body']?['message'])}",
                                                                    "faultReason": ""
                                                                },
                                                                "message": "@concat('Action ', actions('ConstructMessage:_Call_MessageConstructor')?['name'], ' resulted in an error response.')"
                                                            },
                                                            "$contentType": "application/json",
                                                            "$part": 1,
                                                            "$partType": "http://schemas.microsoft.com/aim#nack"
                                                        }
                                                    ],
                                                    "header": {
                                                        "properties": {
                                                            "createDate": "@utcNow()",
                                                            "envelopeType": "nack",
                                                            "messageId": "@guid()",
                                                            "rootPart": 1,
                                                            "trackingId": ""
                                                        },
                                                        "routing": {
                                                            "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                        },
                                                        "routingSlip": {},
                                                        "state": {}
                                                    }
                                                }
                                            },
                                            "ConstructMessage:Failure:_Set_ResponseMessage_variable": {
                                                "runAfter": {
                                                    "ConstructMessage:Failure:_Create_NACK_Message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ResponseMessage",
                                                    "value": "@outputs('ConstructMessage:Failure:_Create_NACK_Message')"
                                                }
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "ConstructMessage:_Get_file_content": {
                                    "runAfter": {},
                                    "type": "ApiConnection",
                                    "inputs": {
                                        "host": {
                                            "connection": {
                                                "name": "@parameters('$connections')['filesystemreceive']['connectionId']"
                                            }
                                        },
                                        "method": "get",
                                        "path": "/datasets/default/files/@{encodeURIComponent(encodeURIComponent(triggerBody()?['Id']))}/content",
                                        "queries": {
                                            "inferContentType": true
                                        }
                                    }
                                },
                                "ConstructMessage:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "ConstructMessage:_Call_MessageConstructor": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('ConstructMessage:_Call_MessageConstructor')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Should_we_process_file": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "ProcessFile"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        }
                    },
                    "outputs": {}
                },
                "parameters": {
                    "$connections": {
                        "value": {
                            "filesystemreceive": {
                                "connectionId": "[variables('fileSystemApiConnectionResourceId')]",
                                "connectionName": "[parameters('fileSystemReceiveApiConnectionName')]",
                                "id": "[concat(subscription().id, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/filesystem')]"
                            }
                        }
                    },
                    "fileReceiveFolder": {
                        "value": "[parameters('fileReceiveFolder')]"
                    },
                    "fileMaxFileCount": {
                        "value": "[parameters('fileMaxFileCount')]"
                    },
                    "fileRecurrenceFrequency": {
                        "value": "[parameters('fileRecurrenceFrequency')]"
                    },
                    "fileRecurrenceInterval": {
                        "value": "[parameters('fileRecurrenceInterval')]"
                    },
                    "apimSubscriptionKey": {
                        "value": "[parameters('apimSubscriptionKey')]"
                    },
                    "scenario": {
                        "value": "[parameters('scenario')]"
                    },
                    "scenarioStep": {
                        "value": "[parameters('scenarioStep')]"
                    },
                    "suspendQueueTopicName": {
                        "value": "[parameters('suspendQueueTopicName')]"
                    }
                }
            }
        }
    ]
}
tools\templates\endpoints\file\receive\filereceiveadapter.logicapp.prod.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterfilesystem.apiconnection.dev.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterfilesystem.apiconnection.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterfilesystem.apiconnection.prod.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterfilesystem.apiconnpolicy.dev.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterfilesystem.apiconnpolicy.json
{
	"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
	"contentVersion": "1.0.0.0",
	"parameters": {
		"apiConnectionName": {
			"type": "string",
			"metadata": {
				"description": "Resource Name of the API Connection"
			}
		},
		"apiConnectionDisplayName": {
			"type": "string",
			"defaultValue": "[parameters('apiConnectionName')]",
			"metadata": {
				"description": "Display Name of the API Connection"
			}
		},
		"apiConnectionLocation": {
			"type": "string",
			"defaultValue": "[resourceGroup().location]",
			"metadata": {
				"description": "Location that we're deploying this resource to."
			}
		},
		"logicAppName": {
			"type": "String",
			"metadata": {
				"description": "Name of the LogicApp that we're creating a policy for."
			}
		},
		"tags": {
			"type": "object"
		}
	},
	"variables": {},
	"resources": [
		{
			"type": "Microsoft.Web/connections/accessPolicies",
			"apiVersion": "2016-06-01",
			"name": "[concat(parameters('apiConnectionName'),'/', parameters('logicAppName'))]",
			"location": "[parameters('apiConnectionLocation')]",
			"dependsOn": [],
			"properties": {
				"principal": {
					"type": "ActiveDirectory",
					"identity": {
						"tenantId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.tenantId]",
						"objectId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.principalId]"
					}
				}
			}
		}
	],
	"outputs": {}
}
tools\templates\endpoints\file\receive\filereceiveadapterfilesystem.apiconnpolicy.prod.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterservicebus.apiconnection.dev.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterservicebus.apiconnection.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterservicebus.apiconnection.prod.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterservicebus.apiconnpolicy.dev.parameters.json.liquid
 
tools\templates\endpoints\file\receive\filereceiveadapterservicebus.apiconnpolicy.json
{
	"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
	"contentVersion": "1.0.0.0",
	"parameters": {
		"apiConnectionName": {
			"type": "string",
			"metadata": {
				"description": "Resource Name of the API Connection"
			}
		},
		"apiConnectionDisplayName": {
			"type": "string",
			"defaultValue": "[parameters('apiConnectionName')]",
			"metadata": {
				"description": "Display Name of the API Connection"
			}
		},
		"apiConnectionLocation": {
			"type": "string",
			"defaultValue": "[resourceGroup().location]",
			"metadata": {
				"description": "Location that we're deploying this resource to."
			}
		},
		"logicAppName": {
			"type": "String",
			"metadata": {
				"description": "Name of the LogicApp that we're creating a policy for."
			}
		},
		"tags": {
			"type": "object"
		}
	},
	"variables": {},
	"resources": [
		{
			"type": "Microsoft.Web/connections/accessPolicies",
			"apiVersion": "2016-06-01",
			"name": "[concat(parameters('apiConnectionName'),'/', parameters('logicAppName'))]",
			"location": "[parameters('apiConnectionLocation')]",
			"dependsOn": [],
			"properties": {
				"principal": {
					"type": "ActiveDirectory",
					"identity": {
						"tenantId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.tenantId]",
						"objectId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.principalId]"
					}
				}
			}
		}
	],
	"outputs": {}
}
tools\templates\endpoints\file\receive\filereceiveadapterservicebus.apiconnpolicy.prod.parameters.json.liquid
 
tools\templates\endpoints\file\receive\New-FileReceiveAdapter-LogicApp.ps1
<#
.SYNOPSIS
Creates a file receive adapter for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER keyVaultName
The name of the key vault store.

.PARAMETER keyVaultApimSubscriptionSecretName
The name of secret in key vault which stores the apim subscription.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileReceiveAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth" -templateFile ".\filereceiveadapter.logicapp.json" -templateParameterFile ".\filereceiveadapter.logicapp.dev.parameters.json" -keyVaultName "kv-aimrstore-dev-xxxxx" -keyVaultApimSubscriptionSecretName "aim-apim-subscriptionkey-unlimited" -deploymentName "filereceiveadapter.logicapp.xxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Getting the subscription key from Key Vault for APIM"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

Write-Host "Deploying a file receive adapter`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --parameters "apimSubscriptionKey=$apimSubscriptionKey" --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\receive\New-FileReceiveAdapterFileSystem-ApiConnection.ps1
<#
.SYNOPSIS
Creates a file api connection for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileReceiveAdapterFileSystem-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth" -templateFile ".\filereceiveadapterfile.apiconnection.json" -templateParameterFile ".\filereceiveadapterfile.apiconnection.dev.parameters.json" -deployment -deploymentName "filereceiveadapterfile
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying a file system api connection`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\receive\New-FileReceiveAdapterFileSystem-ApiConnPolicy.ps1
<#
.SYNOPSIS
Creates a file receive api connection access policy.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileReceiveAdapterFileSystem-ApiConnPolicy.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -templateFile ".\filereceiveadapterfilesystem.apiconnpolicy.json" -templateParameterFile ".\filereceiveadapterfilesystem.apiconnpolicy.dev.parameters.json" -deploymentName "filereceiveadapterfile.apicaccesspolicy.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an api connection access policy`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\receive\New-FileReceiveAdapterServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Creates a service bus api connection for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileReceiveAdapterServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth" -templateFile ".\filereceiveadaptersb.apiconnection.json" -templateParameterFile ".\filereceiveadaptersb.apiconnection.dev.parameters.json" -deploymentName "filereceiveadaptersb.apiconnection.xxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying a service bus api connection`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\receive\New-FileReceiveAdapterServiceBus-ApiConnPolicy.ps1
<#
.SYNOPSIS
Creates a file receive service bus api connection access policy.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileReceiveAdapterServiceBus-ApiConnPolicy.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -templateFile ".\filereceiveadapterservicebus.apiconnpolicy.json" -templateParameterFile ".\filereceiveadapterservicebus.apiconnpolicy.dev.parameters.json" -deploymentName "filereceiveadapterservicebus.apicaccesspolicy.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an api connection access policy`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\receive\Remove-FileReceiveAdapter-LogicApp.ps1
<#
.SYNOPSIS
Tears down the file receive adapter.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FileReceiveAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth-xxxxx" -resourceName "logic-Aim-FilePassthru-ReceiveLocation-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

if ($resourceExists) {
    Write-Host "Removing the file receive adapter resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

    Write-Host "Removed the file receive adapter resource: $resourceName"
}
else {
    Write-Host "The file receive adapter resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\file\receive\Remove-FileReceiveAdapterFileSystem-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the file receive adapters file system api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FileReceiveAdapterFileSystem-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth" -resourceName "filereceiveconnector-Aim-filePassthru-ReceiveLocation-dev"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the file receive adapters file system api connection resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the file receive adapters file system api connection resource: $resourceName"
}
else {
    Write-Host "The file receive adapters file system api connection resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\file\receive\Remove-FileReceiveAdapterServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the file receive adapters service bus api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FileReceiveAdapterServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth" -resourceName "topicpublisherconnector-filereceiveadapater-dev"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the file receive adapters service bus api connection resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the file receive adapters service bus api connection resource: $resourceName"
}
else {
    Write-Host "The file receive adapters service bus api connection resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\file\receive\TearDown-100-FileReceiveAdapterFileSystem-ApiConnection.ps1.liquid
 
tools\templates\endpoints\file\receive\TearDown-100-FileReceiveAdapterServiceBus-ApiConnection.ps1.liquid
 
tools\templates\endpoints\file\receive\TearDown-105-FileReceiveAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\file\send\Deploy-100-FileSendAdapter-ApiConnection.ps1.liquid
 
tools\templates\endpoints\file\send\Deploy-105-FileSendAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\file\send\Deploy-110-FileSendAdapter-ApiConnPolicy.ps1.liquid
 
tools\templates\endpoints\file\send\filesendadapter.logicapp.dev.parameters.json.liquid
 
tools\templates\endpoints\file\send\filesendadapter.logicapp.json
{
    "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "logicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of this LogicApp."
            }
        },
        "logicAppLocation": {
            "defaultValue": "[resourceGroup().location]",
            "type": "string",
            "metadata": {
                "description": "Location (region) or ISE that this LogicApp is to be deployed to. Defaults to the ResourceGroup location."
            }
        },
        "logicAppStartupState": {
            "type": "string",
            "defaultValue": "Enabled",
            "allowedValues": [ "Enabled", "Disabled" ],
            "metadata": {
                "description": "Initial state of the LogicApp after it is deployed."
            }
        },
        "messageBusResourceGroupName": {
            "type": "String",
            "metadata": {
                "description": "Name of the ResourceGroup that MessageBus artifacts are deployed to (e.g. APIM or RoutingSlipRouter LogicApp)."
            }
        },
        "routingSlipRouterLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to route via the RoutingSlip."
            }
        },
        "routerRetryPolicy": {
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "type": "object",
            "metadata": {
                "description": "Retry Policy to use when calling RoutingSlipRouter."
            }
        },
        "apimServiceName": {
            "type": "string",
            "metadata": {
                "description": "Name of the APIM Service used for MessageBus operations."
            }
        },
        "apimSubscriptionKey": {
            "type": "securestring",
            "metadata": {
                "description": "Subscription Key used to access APIM."
            }
        },
        "apimRetryPolicy": {
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "type": "object",
            "metadata": {
                "description": "Retry Policy to use when calling APIM."
            }
        },
        "fileSystemSendApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for File Send operations."
            }
        },
        "scenarioStep": {
            "defaultValue": "fileSendAdapter",
            "type": "string",
            "metadata": {
                "description": "The step within a Scenario that this LogicApp is running under e.g. fileSendAdapter."
            }
        },
        "tags": {
            "type": "object"
        }
    },
    "variables": {
        "apimServiceResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.ApiManagement/service', parameters('apimServiceName'))]",
        "configurationManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimconfigurationmanager')]",
        "messagingManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimmessagingmanager')]",
        "fileSendApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('fileSystemSendApiConnectionName'))]",
        "routingSlipRouterLogicAppResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.Logic/workflows', parameters('routingSlipRouterLogicAppName'))]"
    },
    "resources": [
        {
            "type": "Microsoft.Logic/workflows",
            "apiVersion": "2017-07-01",
            "name": "[parameters('logicAppName')]",
            "location": "[parameters('logicAppLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "state": "[parameters('logicAppStartupState')]",
                "definition": {
                    "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
                    "contentVersion": "1.0.0.0",
                    "parameters": {
                        "$connections": {
                            "defaultValue": {},
                            "type": "Object"
                        },
                        "scenarioStep": {
                            "type": "String",
                            "description": "The step within a Scenario that this LogicApp is running under e.g. fileSendAdapter."
                        },
                        "apimSubscriptionKey": {
                            "type": "SecureString",
                            "description": "Subscription Key used to access APIM."
                        }
                    },
                    "triggers": {
                        "manual": {
                            "correlation": {
                                "clientTrackingId": "@coalesce(triggerBody()?['header']?['properties']?['trackingId'], guid())"
                            },
                            "type": "Request",
                            "kind": "Http",
                            "inputs": {
                                "schema": {}
                            }
                        }
                    },
                    "actions": {
                        "Initialize_StatusCode_variable": {
                            "runAfter": {},
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "StatusCode",
                                        "type": "integer",
                                        "value": 500
                                    }
                                ]
                            }
                        },
                        "Initialize_FaultMessage_variable": {
                            "runAfter": {
                                "Initialize_StatusCode_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "FaultMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_ErrorMessage_variable": {
                            "runAfter": {
                                "Initialize_FaultMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ErrorMessage",
                                        "type": "string",
                                        "value": "An error occurred in the @{workflow()?['name']} (@{workflow()?['run']?['name']}) LogicApp"
                                    }
                                ]
                            }
                        },
                        "Initialize_Checkpoint_variable": {
                            "runAfter": {
                                "Initialize_ErrorMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Checkpoint",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_Envelope_variable": {
                            "runAfter": {
                                "Initialize_Checkpoint_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Envelope",
                                        "type": "object",
                                        "value": "@triggerBody()"
                                    }
                                ]
                            }
                        },
                        "Initialize_Configuration_variable": {
                            "runAfter": {
                                "Initialize_Envelope_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Configuration",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_BodyContent_variable": {
                            "runAfter": {
                                "Initialize_Configuration_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "BodyContent",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_SendFileName_variable": {
                            "runAfter": {
                                "Initialize_BodyContent_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "SendFileName",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_CopyMode_variable": {
                            "runAfter": {
                                "Initialize_SendFileName_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "CopyMode",
                                        "type": "string",
                                        "value": "Create"
                                    }
                                ]
                            }
                        },
                        "MessageSender:_Were_we_Successful": {
                            "actions": {
                                "Routing:_Call_RoutingSlipRouter": {
                                    "runAfter": {},
                                    "type": "Workflow",
                                    "inputs": {
                                        "body": "@variables('Envelope')",
                                        "headers": {
                                            "Aim-Clear-Cache": "@coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], false)",
                                            "Aim-Enable-Trace": "@coalesce(triggerOutputs()?['headers']?['Aim-Enable-Trace'], false)",
                                            "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                            "Content-Type": "application/json"
                                        },
                                        "host": {
                                            "triggerName": "manual",
                                            "workflow": {
                                                "id": "[variables('routingSlipRouterLogicAppResourceId')]"
                                            }
                                        },
                                        "retryPolicy": "[parameters('routerRetryPolicy')]"
                                    }
                                },
                                "Routing:_Check_StatusCode": {
                                    "runAfter": {
                                        "Routing:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "Routing:Success:_Send_ACK-Content_response": {
                                                    "runAfter": {},
                                                    "type": "Response",
                                                    "kind": "Http",
                                                    "inputs": {
                                                        "body": "@body('Routing:_Call_RoutingSlipRouter')",
                                                        "headers": {
                                                            "Aim-Clear-Cache": "@coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], false)",
                                                            "Aim-Enable-Trace": "@coalesce(triggerOutputs()?['headers']?['Aim-Enable-Trace'], false)",
                                                            "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                                            "Content-Type": "application/json"
                                                        },
                                                        "statusCode": 200
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "Routing:Error:_Build_NACK_message": {
                                                "runAfter": {
                                                    "Routing:Error:_Do_we_have_a_Fault_Message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "Compose",
                                                "inputs": {
                                                    "body": [
                                                        {
                                                            "$content": {
                                                                "code": "500",
                                                                "message": "@variables('ErrorMessage')",
                                                                "lastCheckpoint": "@variables('Checkpoint')",
                                                                "fault": "@variables('FaultMessage')"
                                                            },
                                                            "$contentType": "application/json",
                                                            "$part": 1,
                                                            "$partType": "http://schemas.microsoft.com/aim#nack"
                                                        }
                                                    ],
                                                    "header": {
                                                        "properties": {
                                                            "createDate": "@utcNow()",
                                                            "envelopeType": "nack",
                                                            "messageId": "@guid()",
                                                            "rootPart": 1,
                                                            "trackingId": "@triggerBody()?['header']?['properties']?['trackingId']"
                                                        },
                                                        "routing": {
                                                            "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                        },
                                                        "routingSlip": {},
                                                        "state": {}
                                                    }
                                                }
                                            },
                                            "Routing:Error:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "Routing:Error:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "Routing:Error:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the RoutingSlipRouter Logic App"
                                                        }
                                                    },
                                                    "Routing:Error:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('Routing:_Call_RoutingSlipRouter')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "Routing:Error:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('Routing:_Call_RoutingSlipRouter')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('Routing:_Call_RoutingSlipRouter')?['statusCode'], outputs('Routing:_Call_RoutingSlipRouter')?['body']?['statusCode'], actions('Routing:_Call_RoutingSlipRouter')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('Routing:_Call_RoutingSlipRouter')?['error']?['message'], outputs('Routing:_Call_RoutingSlipRouter')?['body']?['message'], actions('Routing:_Call_RoutingSlipRouter')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('Routing:_Call_RoutingSlipRouter')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "Routing:Error:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "Routing:Error:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the RoutingSlipRouter Logic App"
                                                            }
                                                        },
                                                        "Routing:Error:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "Routing:Error:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('Routing:Error:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('Routing:_Call_RoutingSlipRouter')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            },
                                            "Routing:Error:_Send_NACK_response": {
                                                "runAfter": {
                                                    "Routing:Error:_Build_NACK_message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "Response",
                                                "kind": "Http",
                                                "inputs": {
                                                    "body": "@outputs('Routing:Error:_Build_NACK_message')",
                                                    "headers": {
                                                        "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                        "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')",
                                                        "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                                        "Content-Type": "application/json"
                                                    },
                                                    "statusCode": 200
                                                }
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "Routing:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "Routing:_Call_RoutingSlipRouter": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('Routing:_Call_RoutingSlipRouter')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_SendToFile": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "else": {
                                "actions": {
                                    "Failure:_Build_NACK_message": {
                                        "runAfter": {},
                                        "type": "Compose",
                                        "inputs": {
                                            "body": [
                                                {
                                                    "$content": {
                                                        "code": "500",
                                                        "message": "@variables('ErrorMessage')",
                                                        "lastCheckpoint": "@variables('Checkpoint')",
                                                        "fault": "@variables('FaultMessage')"
                                                    },
                                                    "$contentType": "application/json",
                                                    "$part": 1,
                                                    "$partType": "http://schemas.microsoft.com/aim#nack"
                                                }
                                            ],
                                            "header": {
                                                "properties": {
                                                    "createDate": "@utcNow()",
                                                    "envelopeType": "nack",
                                                    "messageId": "@guid()",
                                                    "rootPart": 1,
                                                    "trackingId": "@triggerBody()?['header']?['properties']?['trackingId']"
                                                },
                                                "routing": {
                                                    "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                },
                                                "routingSlip": {},
                                                "state": {}
                                            }
                                        }
                                    },
                                    "Failure:_Send_NACK_response": {
                                        "runAfter": {
                                            "Failure:_Build_NACK_message": [
                                                "Succeeded"
                                            ]
                                        },
                                        "type": "Response",
                                        "kind": "Http",
                                        "inputs": {
                                            "body": "@outputs('Failure:_Build_NACK_message')",
                                            "headers": {
                                                "Aim-Clear-Cache": "@coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], false)",
                                                "Aim-Enable-Trace": "@coalesce(triggerOutputs()?['headers']?['Aim-Enable-Trace'], false)",
                                                "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                                "Content-Type": "application/json"
                                            },
                                            "statusCode": 200
                                        }
                                    }
                                }
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "SendToFile"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_Configuration": {
                            "actions": {
                                "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": {
                                    "runAfter": {},
                                    "type": "ApiManagement",
                                    "inputs": {
                                        "api": {
                                            "id": "[variables('configurationManagerApiResourceId')]"
                                        },
                                        "method": "get",
                                        "pathTemplate": {
                                            "parameters": {
                                                "scenario": "@{encodeURIComponent(triggerBody()?['header']?['properties']?['scenario'])}",
                                                "step": "@{encodeURIComponent(parameters('scenarioStep'))}"
                                            },
                                            "template": "/aimconfigurationmanager/configuration/{scenario}/{step}"
                                        },
                                        "queries": {
                                            "clearCache": "@{coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], 'false')}"
                                        },
                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                    }
                                },
                                "GetConfiguration:_Check_Status_Code": {
                                    "runAfter": {
                                        "GetConfiguration:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "GetConfiguration:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {
                                                        "GetConfiguration:Success:_Set_Configuration_variable": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "GetConfiguration"
                                                    }
                                                },
                                                "GetConfiguration:Success:_Set_Configuration_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Configuration",
                                                        "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "GetConfiguration:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "GetConfiguration:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "GetConfiguration:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                        }
                                                    },
                                                    "GetConfiguration:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "GetConfiguration:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['statusCode'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['message'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('GetConfiguration:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "GetConfiguration:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Initialize_CopyMode_variable": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            ""
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Check_BodyContent": {
                            "actions": {
                                "CheckBodyContent:_Body_Content_is_missing": {
                                    "actions": {
                                        "CheckBodyContent:Missing:_Set_Checkpoint_variable": {
                                            "runAfter": {},
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "Checkpoint",
                                                "value": "NoBodyContent"
                                            }
                                        }
                                    },
                                    "runAfter": {
                                        "CheckBodyContent:_Select_Root_Part": [
                                            "Succeeded"
                                        ]
                                    },
                                    "else": {
                                        "actions": {
                                            "CheckBodyContent:Success:_Set_Checkpoint_variable": {
                                                "runAfter": {},
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "Checkpoint",
                                                    "value": "CheckBodyContent"
                                                }
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "equals": [
                                                    "@coalesce(body('CheckBodyContent:_Select_Root_Part')?[0]?['$content'], '')",
                                                    ""
                                                ]
                                            }
                                        ]
                                    },
                                    "type": "If"
                                },
                                "CheckBodyContent:_Select_Root_Part": {
                                    "runAfter": {},
                                    "type": "Query",
                                    "inputs": {
                                        "from": "@variables('Envelope')?['body']",
                                        "where": "@equals(item()?['$part'], variables('Envelope')?['header']?['properties']?['rootPart'])"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Get_Configuration": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetConfiguration"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_BodyContent": {
                            "actions": {
                                "GetBodyContent:_Call_APIM_MessageManager.GetBodyContent": {
                                    "runAfter": {},
                                    "type": "ApiManagement",
                                    "inputs": {
                                        "api": {
                                            "id": "[variables('messagingManagerApiResourceId')]"
                                        },
                                        "body": "@variables('Envelope')",
                                        "headers": {
                                            "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                            "Content-Type": "application/json"
                                        },
                                        "method": "post",
                                        "pathTemplate": {
                                            "parameters": {},
                                            "template": "/aimmessagingmanager/getbodycontent"
                                        },
                                        "queries": {
                                            "clearCache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                            "enableTrace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                        },
                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                    }
                                },
                                "GetBodyContent:_Check_Status_Code": {
                                    "runAfter": {
                                        "GetBodyContent:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "GetBodyContent:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {
                                                        "GetBodyContent:Success:_Set_BodyContent_variable": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "GetBodyContent"
                                                    }
                                                },
                                                "GetBodyContent:Success:_Set_BodyContent_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "BodyContent",
                                                        "value": "@{base64ToString(body('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['$content'])}"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "GetBodyContent:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "GetBodyContent:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "GetBodyContent:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the MessageManager GetBodyContent operation"
                                                        }
                                                    },
                                                    "GetBodyContent:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "GetBodyContent:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['statusCode'], outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['body']?['statusCode'], actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['error']?['message'], outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['body']?['message'], actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "GetBodyContent:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "GetBodyContent:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the MessageManager GetBodyContent operation"
                                                            }
                                                        },
                                                        "GetBodyContent:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "GetBodyContent:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('GetBodyContent:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "GetBodyContent:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "GetBodyContent:_Call_APIM_MessageManager.GetBodyContent": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Check_BodyContent": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "CheckBodyContent"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_GetSendFileName": {
                            "actions": {
                                "GetSendFileName:_Set_SendFileName_variable": {
                                    "description": "A full list of supported FileName macros can be found here: https://social.technet.microsoft.com/wiki/contents/articles/8823.biztalk-server-list-of-macros.aspx. At this time we are not supporting the Party macros.",
                                    "type": "SetVariable",
                                    "runAfter": {},
                                    "inputs": {
                                        "name": "SendFileName",
                                        "value": "@{replace(replace(replace(replace(replace(replace(replace(coalesce(variables('Configuration')?[parameters('scenarioStep')]?['fileName'], '%MessageID%.xml'), '%MessageID%', coalesce(triggerBody()?['header']?['properties']?['messageId'], guid())), '%SourceFileName%', coalesce(triggerBody()?['header']?['properties']?['receivedFileName'], 'myfile.txt')), '%datetime%', utcNow('yyyy-MM-ddThhmmss')), '%datetime_bts2000%', utcNow('yyyyMMddhhmmsss')), '%datetime.tz%', utcNow('yyyy-MM-ddThhmmssK')), '%time%', utcNow('hhmmss')), '%time.tz%', utcNow('hhmmssK'))}"
                                    }
                                },
                                "SendToFile:_Set_Checkpoint_variable": {
                                    "runAfter": {
                                        "GetSendFileName:_Set_SendFileName_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "Checkpoint",
                                        "value": "GetSendFileName"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Get_BodyContent": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "or": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetBodyContent"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "NoBodyContent"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_SendToFile": {
                            "actions": {
                                "SendToFile:_Check_Status_Code": {
                                    "runAfter": {
                                        "SendToFile:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "SendToFile:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "SendToFile"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "SendToFile:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "SendToFile:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "SendToFile:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to send a file using the FileSystem connector"
                                                        }
                                                    },
                                                    "SendToFile:Fault:_Create_Fault_Message": {
                                                        "runAfter": {},
                                                        "type": "Compose",
                                                        "inputs": {
                                                            "fault": {
                                                                "faultActor": "@concat(workflow()?['name'], '.', actions('SendToFile:_Create_File')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                "faultCategory": "Error",
                                                                "faultCode": "@{coalesce(outputs('SendToFile:_Create_File')?['statusCode'], outputs('SendToFile:_Create_File')?['body']?['statusCode'], actions('SendToFile:_Create_File')?['error']?['code'])}",
                                                                "faultMessage": "@{coalesce(outputs('SendToFile:_Create_File')?['error']?['message'], outputs('SendToFile:_Create_File')?['body']?['message'], actions('SendToFile:_Create_File')?['error']?['message'])}",
                                                                "faultReason": "@{actions('SendToFile:_Create_File')?['status']}"
                                                            }
                                                        }
                                                    },
                                                    "SendToFile:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {
                                                            "SendToFile:Fault:_Create_Fault_Message": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('SendToFile:Fault:_Create_Fault_Message')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "SendToFile:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('SendToFile:_Create_File')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('SendToFile:_Create_File')?['statusCode'], outputs('SendToFile:_Create_File')?['body']?['statusCode'])}",
                                                                    "faultMessage": "@{coalesce(outputs('SendToFile:_Create_File')?['error']?['message'], outputs('SendToFile:_Create_File')?['body']?['message'])}",
                                                                    "faultReason": "@actions('SendToFile:_Create_File')?['inputs']?['path']"
                                                                }
                                                            }
                                                        },
                                                        "SendToFile:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "SendToFile:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to send a file using the FileSystem connector"
                                                            }
                                                        },
                                                        "SendToFile:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "SendToFile:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('SendToFile:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('SendToFile:_Create_File')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "SendToFile:_Set_CopyMode_variable": {
                                    "runAfter": {},
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "CopyMode",
                                        "value": "@{coalesce(variables('Configuration')?[parameters('scenarioStep')]?['copyMode'], 'Create')}"
                                    }
                                },
                                "SendToFile:_Create_File": {
                                    "inputs": {
                                        "body": "@variables('BodyContent')",
                                        "host": {
                                            "connection": {
                                                "name": "@parameters('$connections')['filesystemsend']['connectionId']"
                                            }
                                        },
                                        "method": "@{if(equals(variables('CopyMode'), 'Create'), 'post', if(equals(variables('CopyMode'), 'Append'), 'patch', if(equals(variables('CopyMode'), 'Update'), 'put', 'undefined')))}",
                                        "path": "/datasets/default/[email protected]{if(contains(createArray('Append', 'Update'), variables('CopyMode')), concat(coalesce(variables('Configuration')?[parameters('scenarioStep')]?['destinationFolder'], '(undefined)'), '\\', variables('SendFileName')), '')}",
                                        "queries": {
                                            "folderPath": "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['destinationFolder'], '(undefined)')",
                                            "name": "@variables('SendFileName')",
                                            "queryParametersSingleEncoded": true
                                        }
                                    },
                                    "runAfter": {
                                        "SendToFile:_Set_CopyMode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "runtimeConfiguration": {
                                        "contentTransfer": {
                                            "transferMode": "Chunked"
                                        }
                                    },
                                    "type": "ApiConnection"
                                },
                                "SendToFile:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "SendToFile:_Create_File": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('SendToFile:_Create_File')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_GetSendFileName": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetSendFileName"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        }
                    },
                    "outputs": {}
                },
                "parameters": {
                    "$connections": {
                        "value": {
                            "filesystemsend": {
                                "connectionId": "[variables('fileSendApiConnectionResourceId')]",
                                "connectionName": "[parameters('fileSystemSendApiConnectionName')]",
                                "id": "[concat(subscription().id, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/filesystem')]"
                            }
                        }
                    },
                    "scenarioStep": {
                        "value": "[parameters('scenarioStep')]"
                    },
                    "apimSubscriptionKey": {
                        "value": "[parameters('apimSubscriptionKey')]"
                    }
                }
            }
        }
    ]
}
tools\templates\endpoints\file\send\filesendadapter.logicapp.prod.parameters.json.liquid
 
tools\templates\endpoints\file\send\filesystemsendadapter.apiconnection.dev.parameters.json.liquid
 
tools\templates\endpoints\file\send\filesystemsendadapter.apiconnection.json.liquid
 
tools\templates\endpoints\file\send\filesystemsendadapter.apiconnection.prod.parameters.json.liquid
 
tools\templates\endpoints\file\send\filesystemsendadapter.apiconnpolicy.dev.parameters.json.liquid
 
tools\templates\endpoints\file\send\filesystemsendadapter.apiconnpolicy.json
{
	"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
	"contentVersion": "1.0.0.0",
	"parameters": {
		"apiConnectionName": {
			"type": "string",
			"metadata": {
				"description": "Resource Name of the API Connection"
			}
		},
		"apiConnectionDisplayName": {
			"type": "string",
			"defaultValue": "[parameters('apiConnectionName')]",
			"metadata": {
				"description": "Display Name of the API Connection"
			}
		},
		"apiConnectionLocation": {
			"type": "string",
			"defaultValue": "[resourceGroup().location]",
			"metadata": {
				"description": "Location that we're deploying this resource to."
			}
		},
		"logicAppName": {
			"type": "String",
			"metadata": {
				"description": "Name of the LogicApp that we're creating a policy for."
			}
		},
		"tags": {
			"type": "object"
		}
	},
	"variables": {},
	"resources": [
		{
			"type": "Microsoft.Web/connections/accessPolicies",
			"apiVersion": "2016-06-01",
			"name": "[concat(parameters('apiConnectionName'),'/', parameters('logicAppName'))]",
			"location": "[parameters('apiConnectionLocation')]",
			"dependsOn": [],
			"properties": {
				"principal": {
					"type": "ActiveDirectory",
					"identity": {
						"tenantId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.tenantId]",
						"objectId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.principalId]"
					}
				}
			}
		}
	],
	"outputs": {}
}
tools\templates\endpoints\file\send\filesystemsendadapter.apiconnpolicy.prod.parameters.json.liquid
 
tools\templates\endpoints\file\send\New-FileSendAdapter-ApiConnection.ps1
<#
.SYNOPSIS
Creates a file send adapters api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileSendAdapter-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth-xxxxx" -templateFile ".\fileconnection.json" -templateParameterFile ".\fileconnection.dev.parameters.json" -deploymentName "filesendconnection"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying a file send adapters api connection`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\send\New-FileSendAdapter-ApiConnPolicy.ps1
<#
.SYNOPSIS
Creates a file send api connection access policy.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileSendAdapter-ApiConnPolicy.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -templateFile ".\filesystemsendadapter.apiconnpolicy.json" -templateParameterFile ".\filesystemsendadapter.apiconnpolicy.dev.parameters.json" -deploymentName "filesystemsendadapter.apicaccesspolicy.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an api connection access policy`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\send\New-FileSendAdapter-LogicApp.ps1
<#
.SYNOPSIS
Creates a file send adapter.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FileSendAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth-xxxxx" -templateFile ".\fileadapter.json" -templateParameterFile ".\fileadapter.dev.parameters.json" -deploymentName "fileadapter"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Getting the subscription from Key Vault for the routing slip router Logic App"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

Write-Host "Deploying a file send adapter`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile "apimSubscriptionKey=$apimSubscriptionKey" --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\file\send\Remove-FileSendAdapter-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the file send adapters api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FileSendAdapter-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth-xxxxx" -resourceName "filereceiveconnector-Aim-FilePassthru-ReceiveLocation-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the file send adapters api connection: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the file send adapters api connection: $resourceName"
}
else {
    Write-Host "The file send adapaters api connectionresource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\file\send\Remove-FileSendAdapter-LogicApp.ps1
<#
.SYNOPSIS
Tears down the file send adapter.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FileSendAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-filepassthru-dev-uksouth-xxxxx" -resourceName "logic-Aim-FilePassthru-ReceiveLocation-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

if ($resourceExists) {
    Write-Host "Removing the file send adapter resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

    Write-Host "Removed the file send adapter resource: $resourceName"
}
else {
    Write-Host "The file send adapter resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\file\send\TearDown-100-FileSendAdapter-ApiConnection.ps1.liquid
 
tools\templates\endpoints\file\send\TearDown-105-FileSendAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\ftp\receive\Deploy-100-FtpReceiveAdapterFtp-ApiConnection.ps1.liquid
 
tools\templates\endpoints\ftp\receive\Deploy-100-FtpReceiveAdapterServiceBus-ApiConnection.ps1.liquid
 
tools\templates\endpoints\ftp\receive\Deploy-105-FtpReceiveAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\ftp\receive\Deploy-110-FtpReceiveAdapterFtp-ApiConnPolicy.ps1.liquid
 
tools\templates\endpoints\ftp\receive\Deploy-110-FtpReceiveAdapterServiceBus-ApiConnPolicy.ps1.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapter.logicapp.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapter.logicapp.json
{
    "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "logicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of this LogicApp."
            }
        },
        "logicAppLocation": {
            "defaultValue": "[resourceGroup().location]",
            "type": "string",
            "metadata": {
                "description": "Location (region) or ISE that this LogicApp is to be deployed to. Defaults to the ResourceGroup location."
            }
        },
        "logicApStartupState": {
            "type": "string",
            "defaultValue": "Enabled",
            "allowedValues": [ "Enabled", "Disabled" ],
            "metadata": {
                "description": "Initial state of the LogicApp after it is deployed."
            }
        },
        "messageBusResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that MessageBus artifacts are deployed to (e.g. APIM or RoutingSlipRouter LogicApp)."
            }
        },
        "systemApplicationResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that SystemApplication artifacts are deployed to (e.g. ServiceBus or MessageConstructor LogicApp)."
            }
        },
        "integrationAccountName": {
            "type": "string",
            "metadata": {
                "description": "Name of the IntegrationAccount connected to this LogicApp."
            }
        },
        "messageConstructorLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to handle FTP Message Construction and Sending."
            }
        },
        "messageSuspendProcessorLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to handle suspending of messages."
            }
        },
        "suspendQueueTopicName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ServiceBus Topic that suspended messages are sent to."
            }
        },
        "apimServiceName": {
            "type": "string",
            "metadata": {
                "description": "Name of the APIM Service used for MessageBus operations."
            }
        },
        "apimSubscriptionKey": {
            "type": "securestring",
            "metadata": {
                "description": "Subscription Key used to access APIM."
            }
        },
        "apimRetryPolicy": {
            "type": "object",
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "metadata": {
                "description": "Retry Policy to use when calling APIM."
            }
        },
        "ftpReceiveApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for FTP Receive operations."
            }
        },
        "ftpReceiveFolder": {
            "type": "string",
            "metadata": {
                "description": "The path where the FTP connector looks for new/updated files."
            }
        },
        "ftpMaxFileCount": {
            "defaultValue": 10,
            "type": "int",
            "metadata": {
                "description": "The max number of files the FTP Connector will retrieve per polling interval."
            }
        },
        "ftpFileMask": {
            "type": "string",
            "metadata": {
                "description": "The mask to use to decide if we're processing a given file e.g. *.* or *.csv"
            }
        },
        "ftpRecurrenceFrequency": {
            "type": "string",
            "allowedValues": [ "Second", "Minute", "Hour", "Day", "Month", "Year" ],
            "metadata": {
                "description": "The frequency with which to check for new files on the FTP server."
            }
        },
        "ftpRecurrenceInterval": {
            "type": "int",
            "metadata": {
                "description": "The interval with which to check for new files on the FTP server."
            }
        },
        "serviceBusTopicPublishApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for ServiceBus SuspendQueue Publish operations."
            }
        },
        "scenario": {
            "type": "string",
            "metadata": {
                "description": "The name of the Scenario that this LogicApp is running under e.g. ApplicationName + ReceivePort/Location Name."
            }
        },
        "scenarioStep": {
            "defaultValue": "ftpReceiveAdapter",
            "type": "string",
            "metadata": {
                "description": "The step within a Scenario that this LogicApp is running under e.g. ftpReceiveAdapter."
            }
        },
        "tags": {
            "type": "object"
        }
    },
    "variables": {
        "apimServiceResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.ApiManagement/service', parameters('apimServiceName'))]",
        "configurationManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimconfigurationmanager')]",
        "messageConstructorLogicAppResourceId": "[resourceId(parameters('systemApplicationResourceGroupName'), 'Microsoft.Logic/workflows', parameters('messageConstructorLogicAppName'))]",
        "messageSuspendProcessorLogicAppResourceId": "[resourceId(parameters('systemApplicationResourceGroupName'), 'Microsoft.Logic/workflows', parameters('messageSuspendProcessorLogicAppName'))]",
        "ftpApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('ftpReceiveApiConnectionName'))]",
        "integrationAccountResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.Logic/integrationAccounts', parameters('integrationAccountName'))]",
        "serviceBusTopicPublishApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('serviceBusTopicPublishApiConnectionName'))]"
    },
    "resources": [
        {
            "type": "Microsoft.Logic/workflows",
            "apiVersion": "2017-07-01",
            "name": "[parameters('logicAppName')]",
            "location": "[parameters('logicAppLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "state": "[parameters('logicApStartupState')]",
                "integrationAccount": {
                    "id": "[variables('integrationAccountResourceId')]"
                },
                "definition": {
                    "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
                    "contentVersion": "1.0.0.0",
                    "parameters": {
                        "$connections": {
                            "defaultValue": {},
                            "type": "Object"
                        },
                        "ftpReceiveFolder": {
                            "type": "String",
                            "description": "The path where the FTP connector looks for new/updated files."
                        },
                        "ftpMaxFileCount": {
                            "type": "Int",
                            "description": "The max number of files the FTP Connector will retrieve per polling interval."
                        },
                        "ftpRecurrenceFrequency": {
                            "type": "string",
                            "allowedValues": [ "Second", "Minute", "Hour", "Day", "Month", "Year" ],
                            "description": "The frequency with which to check for new files on the FTP server."
                        },
                        "ftpRecurrenceInterval": {
                            "type": "int",
                            "description": "The interval with which to check for new files on the FTP server."
                        },
                        "fileNameMask": {
                            "defaultValue": "*.*",
                            "type": "String",
                            "description": "The mask to use to decide if we're processing a given file e.g. *.* or *.csv"
                        },
                        "apimSubscriptionKey": {
                            "type": "SecureString",
                            "description": "Subscription Key used to access APIM."
                        },
                        "scenario": {
                            "type": "String",
                            "description": "The name of the Scenario that this LogicApp is running under e.g. ApplicationName + ReceivePort/Location Name."
                        },
                        "scenarioStep": {
                            "type": "String",
                            "description": "The step within a Scenario that this LogicApp is running under e.g. FTPReceiveAdapter."
                        },
                        "clearCache": {
                            "defaultValue": true,
                            "type": "Bool",
                            "description": "Indicates if we should clear APIM cache before retrieved config items e.g. configurationEntries or routingSlips."
                        },
                        "suspendQueueTopicName": {
                            "type": "String",
                            "description": "Name of the ServiceBus Topic that suspended messages are sent to."
                        }
                    },
                    "triggers": {
                        "When_a_file_is_added_or_modified_(properties_only)": {
                            "recurrence": {
                                "frequency": "@{parameters('ftpRecurrenceFrequency')}",
                                "interval": "@parameters('ftpRecurrenceInterval')"
                            },
                            "splitOn": "@triggerBody()",
                            "type": "ApiConnection",
                            "inputs": {
                                "host": {
                                    "connection": {
                                        "name": "@parameters('$connections')['ftpreceive']['connectionId']"
                                    }
                                },
                                "method": "get",
                                "path": "/datasets/default/triggers/batch/onupdatedfile",
                                "queries": {
                                    "folderId": "@{parameters('ftpReceiveFolder')}",
                                    "maxFileCount": "@parameters('ftpMaxFileCount')"
                                }
                            }
                        }
                    },
                    "actions": {
                        "Initialize_StatusCode_variable": {
                            "runAfter": {},
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "StatusCode",
                                        "type": "integer",
                                        "value": 500
                                    }
                                ]
                            }
                        },
                        "Initialize_FaultMessage_variable": {
                            "runAfter": {
                                "Initialize_StatusCode_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "FaultMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_ErrorMessage_variable": {
                            "runAfter": {
                                "Initialize_FaultMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ErrorMessage",
                                        "type": "string",
                                        "value": "An error occurred in the @{workflow()?['name']} (@{workflow()?['run']?['name']}) LogicApp"
                                    }
                                ]
                            }
                        },
                        "Initialize_ResponseMessage_variable": {
                            "runAfter": {
                                "Initialize_ErrorMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ResponseMessage",
                                        "type": "object",
                                        "value": null
                                    }
                                ]
                            }
                        },
                        "Initialize_Checkpoint_variable": {
                            "runAfter": {
                                "Initialize_ResponseMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Checkpoint",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_Configuration_variable": {
                            "runAfter": {
                                "Initialize_Checkpoint_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Configuration",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Compose_FileNameMask": {
                            "runAfter": {
                                "Initialize_Configuration_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "Compose",
                            "inputs": "@parameters('fileNameMask')"
                        },
                        "Respond:_Were_we_successful": {
                            "actions": {
                                "Terminate_with_ACK": {
                                    "runAfter": {},
                                    "type": "Terminate",
                                    "inputs": {
                                        "runStatus": "Succeeded"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Construct Message": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "else": {
                                "actions": {
                                    "Failure:_Do_we_have_a_NACK": {
                                        "actions": {},
                                        "runAfter": {},
                                        "else": {
                                            "actions": {
                                                "Failure:_Build_NACK_message": {
                                                    "runAfter": {},
                                                    "type": "Compose",
                                                    "inputs": {
                                                        "body": [
                                                            {
                                                                "$content": {
                                                                    "code": "500",
                                                                    "message": "@variables('ErrorMessage')",
                                                                    "lastCheckpoint": "@variables('Checkpoint')",
                                                                    "fault": "@variables('FaultMessage')"
                                                                },
                                                                "$contentType": "application/json",
                                                                "$part": 1,
                                                                "$partType": "http://schemas.microsoft.com/aim#nack"
                                                            }
                                                        ],
                                                        "header": {
                                                            "properties": {
                                                                "createDate": "@utcNow()",
                                                                "envelopeType": "nack",
                                                                "messageId": "@guid()",
                                                                "rootPart": 1,
                                                                "trackingId": "@triggerBody()?['header']?['properties']?['trackingId']"
                                                            },
                                                            "routing": {
                                                                "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                            },
                                                            "routingSlip": {},
                                                            "state": {}
                                                        }
                                                    }
                                                },
                                                "Failure:_Set_ResponseMessage_variable": {
                                                    "runAfter": {
                                                        "Failure:_Build_NACK_message": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "ResponseMessage",
                                                        "value": "@outputs('Failure:_Build_NACK_message')"
                                                    }
                                                }
                                            }
                                        },
                                        "expression": {
                                            "and": [
                                                {
                                                    "equals": [
                                                        "@{coalesce(variables('ResponseMessage')?['header']?['properties']?['envelopeType'], '(unknown)')}",
                                                        "nack"
                                                    ]
                                                }
                                            ]
                                        },
                                        "type": "If"
                                    },
                                    "Failure:_Send_NACK_to_SuspendQueue": {
                                        "runAfter": {
                                            "Failure:_Do_we_have_a_NACK": [
                                                "Succeeded"
                                            ]
                                        },
                                        "type": "Workflow",
                                        "inputs": {
                                            "body": {
                                                "nackMessage": "@variables('ResponseMessage')",
                                                "originalMessage": "@triggerBody()",
                                                "suspendQueueTopicName": "@{parameters('suspendQueueTopicName')}",
                                                "failedMessageRouting": "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['failedMessageRouting'], false)",
                                                "scenario": "@{parameters('scenario')}"
                                            },
                                            "headers": {
                                                "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                            },
                                            "host": {
                                                "triggerName": "manual",
                                                "workflow": {
                                                    "id": "[variables('messageSuspendProcessorLogicAppResourceId')]"
                                                }
                                            }
                                        }
                                    },
                                    "Terminate_with_NACK": {
                                        "runAfter": {
                                            "Failure:_Send_NACK_to_SuspendQueue": [
                                                "Succeeded",
                                                "Failed",
                                                "Skipped",
                                                "TimedOut"
                                            ]
                                        },
                                        "type": "Terminate",
                                        "inputs": {
                                            "runError": {
                                                "code": "@{coalesce(variables('ResponseMessage')?['body']?[0]?['$content']?['code'], '500')}",
                                                "message": "@{coalesce(variables('ResponseMessage')?['body']?[0]?['$content']?['message'], '(unknown error)')}"
                                            },
                                            "runStatus": "Failed"
                                        }
                                    }
                                }
                            },
                            "expression": {
                                "or": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "IgnoreFile"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "ConstructMessageACK"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_Configuration": {
                            "actions": {
                                "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": {
                                    "runAfter": {},
                                    "type": "ApiManagement",
                                    "inputs": {
                                        "api": {
                                            "id": "[variables('configurationManagerApiResourceId')]"
                                        },
                                        "method": "get",
                                        "pathTemplate": {
                                            "parameters": {
                                                "scenario": "@{encodeURIComponent(parameters('scenario'))}",
                                                "step": "@{encodeURIComponent(parameters('scenarioStep'))}"
                                            },
                                            "template": "/aimconfigurationmanager/configuration/{scenario}/{step}"
                                        },
                                        "queries": {
                                            "clearCache": "@parameters('clearCache')"
                                        },
                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                    }
                                },
                                "GetConfiguration:_Check_Status_Code": {
                                    "runAfter": {
                                        "GetConfiguration:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "GetConfiguration:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {
                                                        "GetConfiguration:Success:_Set_Configuration_variable": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "GetConfiguration"
                                                    }
                                                },
                                                "GetConfiguration:Success:_Set_Configuration_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Configuration",
                                                        "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "GetConfiguration:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "GetConfiguration:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "GetConfiguration:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                        }
                                                    },
                                                    "GetConfiguration:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "GetConfiguration:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['statusCode'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['message'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('GetConfiguration:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "GetConfiguration:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Compose_FileNameMask": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            ""
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Validate_Configuration": {
                            "actions": {
                                "ValidateConfiguration:_Have_Valid_Properties": {
                                    "actions": {
                                        "ValidateConfiguration:Success:_Set_Checkpoint_variable": {
                                            "runAfter": {},
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "Checkpoint",
                                                "value": "ValidateConfiguration"
                                            }
                                        }
                                    },
                                    "runAfter": {},
                                    "else": {
                                        "actions": {
                                            "ValidateConfiguration:Failure:_Set_Checkpoint_variable": {
                                                "runAfter": {},
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ErrorMessage",
                                                    "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}): property btsReceivePortName is not set in configuration"
                                                }
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "not": {
                                                    "equals": [
                                                        "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['btsReceivePortName'], '')",
                                                        ""
                                                    ]
                                                }
                                            }
                                        ]
                                    },
                                    "type": "If"
                                }
                            },
                            "runAfter": {
                                "Step:_Get_Configuration": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetConfiguration"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Should_we_process_file": {
                            "actions": {
                                "ShouldWeProcessFile:_Check_FileMask": {
                                    "runAfter": {},
                                    "type": "JavaScriptCode",
                                    "inputs": {
                                        "code": "var escapedFileMask = workflowContext.actions.Compose_FileNameMask.outputs;\r\nvar fileMaskRegex = \"^\" + escapedFileMask.replace(\".\", \"[.]\").replace(\"*\", \".*\").replace(\"?\", \".\") + \"$\";\r\nreturn workflowContext.trigger.outputs.body.Name.match(fileMaskRegex) !== null;"
                                    }
                                },
                                "ShouldWeProcessFile:Failure:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "ShouldWeProcessFile:_Check_FileMask": [
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": 500
                                    }
                                },
                                "ShouldWeProcessFile:Success:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "ShouldWeProcessFile:_Check_FileMask": [
                                            "Succeeded"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": 200
                                    }
                                },
                                "ShouldWeProcessFile:_Check_StatusCode": {
                                    "runAfter": {
                                        "ShouldWeProcessFile:Failure:_Set_StatusCode_variable": [
                                            "Succeeded",
                                            "Skipped"
                                        ],
                                        "ShouldWeProcessFile:Success:_Set_StatusCode_variable": [
                                            "Succeeded",
                                            "Skipped"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "ShouldWeProcessFile:Success:_Does_FileMask_match": {
                                                    "actions": {
                                                        "ShouldWeProcessFile:Process:_Set_Checkpoint_variable": {
                                                            "runAfter": {},
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "Checkpoint",
                                                                "value": "ProcessFile"
                                                            }
                                                        }
                                                    },
                                                    "runAfter": {},
                                                    "else": {
                                                        "actions": {
                                                            "ShouldWeProcessFile:Ignore:_Set_Checkpoint_variable": {
                                                                "runAfter": {},
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "Checkpoint",
                                                                    "value": "IgnoreFile"
                                                                }
                                                            }
                                                        }
                                                    },
                                                    "expression": {
                                                        "and": [
                                                            {
                                                                "equals": [
                                                                    "@outputs('ShouldWeProcessFile:_Check_FileMask')?['body']",
                                                                    true
                                                                ]
                                                            }
                                                        ]
                                                    },
                                                    "type": "If"
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "ShouldWeProcessFile:Failure:_Create_Fault_message": {
                                                "runAfter": {},
                                                "type": "Compose",
                                                "inputs": {
                                                    "fault": {
                                                        "faultActor": "@concat(workflow()?['name'], '.', actions('ShouldWeProcessFile:_Check_FileMask')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                        "faultCategory": "Error",
                                                        "faultCode": "@{coalesce(outputs('ShouldWeProcessFile:_Check_FileMask')?['statusCode'], outputs('ShouldWeProcessFile:_Check_FileMask')?['body']?['statusCode'], actions('ShouldWeProcessFile:_Check_FileMask')?['error']?['code'])}",
                                                        "faultMessage": "@{coalesce(outputs('ShouldWeProcessFile:_Check_FileMask')?['error']?['message'], outputs('ShouldWeProcessFile:_Check_FileMask')?['body']?['message'], actions('ShouldWeProcessFile:_Check_FileMask')?['error']?['message'])}",
                                                        "faultReason": "@{actions('ShouldWeProcessFile:_Check_FileMask')?['status']}"
                                                    }
                                                }
                                            },
                                            "ShouldWeProcessFile:Failure:_Set_ErrorMessage_variable": {
                                                "runAfter": {
                                                    "ShouldWeProcessFile:Failure:_Set_FaultMessage_variable": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ErrorMessage",
                                                    "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to execute the FileMask Javascript"
                                                }
                                            },
                                            "ShouldWeProcessFile:Failure:_Set_FaultMessage_variable": {
                                                "runAfter": {
                                                    "ShouldWeProcessFile:Failure:_Create_Fault_message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "FaultMessage",
                                                    "value": "@outputs('ShouldWeProcessFile:Failure:_Create_Fault_message')"
                                                }
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                }
                            },
                            "runAfter": {
                                "Step:_Validate_Configuration": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "ValidateConfiguration"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Construct Message": {
                            "actions": {
                                "ConstructMessage:_Call_MessageConstructor": {
                                    "runAfter": {
                                        "ConstructMessage:_Get_file_content": [
                                            "Succeeded"
                                        ]
                                    },
                                    "type": "Workflow",
                                    "inputs": {
                                        "body": {
                                            "$content": "@{body('ConstructMessage:_Get_file_content')}",
                                            "$contentTransferEncoding": "none",
                                            "$contentType": "@triggerBody()?['MediaType']",
                                            "properties": {
                                                "receivedFileName": "@{triggerBody()?['Name']}",
                                                "scenario": "@{parameters('scenario')}",
                                                "btsReceivePortName": "@{coalesce(variables('Configuration')?[parameters('scenarioStep')]?['btsReceivePortName'], '(unknownReceivePortName)')}",
                                                "btsReceivePortId": "@{coalesce(variables('Configuration')?[parameters('scenarioStep')]?['btsReceivePortId'], '(unknownReceivePortId)')}"
                                            }
                                        },
                                        "headers": {
                                            "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                            "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                        },
                                        "host": {
                                            "triggerName": "manual",
                                            "workflow": {
                                                "id": "[variables('messageConstructorLogicAppResourceId')]"
                                            }
                                        }
                                    }
                                },
                                "ConstructMessage:_Check_StatusCode": {
                                    "runAfter": {
                                        "ConstructMessage:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "ConstructMessage:Success:_Check_EnvelopeType": {
                                                    "runAfter": {},
                                                    "cases": {
                                                        "ACK": {
                                                            "case": "ack",
                                                            "actions": {
                                                                "ACK:_Set_ResponseMessage_variable": {
                                                                    "runAfter": {},
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "ResponseMessage",
                                                                        "value": "@body('ConstructMessage:_Call_MessageConstructor')"
                                                                    }
                                                                },
                                                                "ACK:_Set_Checkpoint_variable": {
                                                                    "runAfter": {
                                                                        "ACK:_Set_ResponseMessage_variable": [
                                                                            "Succeeded"
                                                                        ]
                                                                    },
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "Checkpoint",
                                                                        "value": "ConstructMessageACK"
                                                                    }
                                                                }
                                                            }
                                                        },
                                                        "NACK": {
                                                            "case": "nack",
                                                            "actions": {
                                                                "NACK:_Set_ResponseMessage_variable": {
                                                                    "runAfter": {},
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "ResponseMessage",
                                                                        "value": "@body('ConstructMessage:_Call_MessageConstructor')"
                                                                    }
                                                                },
                                                                "NACK:_Set_Checkpoint_variable": {
                                                                    "runAfter": {
                                                                        "NACK:_Set_ResponseMessage_variable": [
                                                                            "Succeeded"
                                                                        ]
                                                                    },
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "Checkpoint",
                                                                        "value": "ConstructMessageNACK"
                                                                    }
                                                                }
                                                            }
                                                        }
                                                    },
                                                    "default": {
                                                        "actions": {
                                                            "ConstructMessage:UnknownEnvelope:_Compose_NACK_Message": {
                                                                "runAfter": {},
                                                                "type": "Compose",
                                                                "inputs": {
                                                                    "body": [
                                                                        {
                                                                            "$content": {
                                                                                "code": "500",
                                                                                "message": "@concat('Body returned by action ', actions('ConstructMessage:_Call_MessageConstructor')?['name'], ' is not an ACK or NACK. Envelope type is: ', coalesce(body('ConstructMessage:_Call_MessageConstructor')?['header']?['properties']?['envelopeType'], '(unknown)'))"
                                                                            },
                                                                            "$contentType": "application/json",
                                                                            "$part": 1,
                                                                            "$partType": "http://schemas.microsoft.com/aim#nack"
                                                                        }
                                                                    ],
                                                                    "header": {
                                                                        "properties": {
                                                                            "createDate": "@utcNow()",
                                                                            "envelopeType": "nack",
                                                                            "messageId": "@guid()",
                                                                            "rootPart": 1,
                                                                            "trackingId": ""
                                                                        },
                                                                        "routing": {
                                                                            "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                                        },
                                                                        "routingSlip": {},
                                                                        "state": {}
                                                                    }
                                                                }
                                                            },
                                                            "ConstructMessage:UnknownEnvelope:_Set_ResponseMessage_variable": {
                                                                "runAfter": {
                                                                    "ConstructMessage:UnknownEnvelope:_Compose_NACK_Message": [
                                                                        "Succeeded"
                                                                    ]
                                                                },
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "ResponseMessage",
                                                                    "value": "@outputs('ConstructMessage:UnknownEnvelope:_Compose_NACK_Message')"
                                                                }
                                                            },
                                                            "ConstructMessage:UnknownEnvelope:_Set_Checkpoint_variable": {
                                                                "runAfter": {
                                                                    "ConstructMessage:UnknownEnvelope:_Set_ResponseMessage_variable": [
                                                                        "Succeeded"
                                                                    ]
                                                                },
                                                                "type": "SetVariable",
                                                                "inputs": {
                                                                    "name": "Checkpoint",
                                                                    "value": "ConstructMessageNACK"
                                                                }
                                                            }
                                                        }
                                                    },
                                                    "expression": "@body('ConstructMessage:_Call_MessageConstructor')?['header']?['properties']?['envelopeType']",
                                                    "type": "Switch"
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "ConstructMessage:Failure:_Create_NACK_Message": {
                                                "runAfter": {},
                                                "type": "Compose",
                                                "inputs": {
                                                    "body": [
                                                        {
                                                            "$content": {
                                                                "code": "500",
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('ConstructMessage:_Call_MessageConstructor')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('ConstructMessage:_Call_MessageConstructor')?['statusCode'], outputs('ConstructMessage:_Call_MessageConstructor')?['body']?['statusCode'])}",
                                                                    "faultMessage": "@{coalesce(outputs('ConstructMessage:_Call_MessageConstructor')?['error']?['message'], outputs('ConstructMessage:_Call_MessageConstructor')?['body']?['message'])}",
                                                                    "faultReason": ""
                                                                },
                                                                "message": "@concat('Action ', actions('ConstructMessage:_Call_MessageConstructor')?['name'], ' resulted in an error response.')"
                                                            },
                                                            "$contentType": "application/json",
                                                            "$part": 1,
                                                            "$partType": "http://schemas.microsoft.com/aim#nack"
                                                        }
                                                    ],
                                                    "header": {
                                                        "properties": {
                                                            "createDate": "@utcNow()",
                                                            "envelopeType": "nack",
                                                            "messageId": "@guid()",
                                                            "rootPart": 1,
                                                            "trackingId": ""
                                                        },
                                                        "routing": {
                                                            "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                        },
                                                        "routingSlip": {},
                                                        "state": {}
                                                    }
                                                }
                                            },
                                            "ConstructMessage:Failure:_Set_ResponseMessage_variable": {
                                                "runAfter": {
                                                    "ConstructMessage:Failure:_Create_NACK_Message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ResponseMessage",
                                                    "value": "@outputs('ConstructMessage:Failure:_Create_NACK_Message')"
                                                }
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "ConstructMessage:_Get_file_content": {
                                    "runAfter": {},
                                    "type": "ApiConnection",
                                    "inputs": {
                                        "host": {
                                            "connection": {
                                                "name": "@parameters('$connections')['ftpreceive']['connectionId']"
                                            }
                                        },
                                        "method": "get",
                                        "path": "/datasets/default/files/@{encodeURIComponent(encodeURIComponent(triggerBody()?['Id']))}/content",
                                        "queries": {
                                            "inferContentType": true
                                        }
                                    }
                                },
                                "ConstructMessage:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "ConstructMessage:_Call_MessageConstructor": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('ConstructMessage:_Call_MessageConstructor')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Should_we_process_file": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "ProcessFile"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        }
                    },
                    "outputs": {}
                },
                "parameters": {
                    "$connections": {
                        "value": {
                            "ftpreceive": {
                                "connectionId": "[variables('ftpApiConnectionResourceId')]",
                                "connectionName": "[parameters('ftpReceiveApiConnectionName')]",
                                "id": "[concat(subscription().id, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/ftp')]"
                            }
                        }
                    },
                    "ftpReceiveFolder": {
                        "value": "[parameters('ftpReceiveFolder')]"
                    },
                    "ftpMaxFileCount": {
                        "value": "[parameters('ftpMaxFileCount')]"
                    },
                    "ftpRecurrenceFrequency": {
                        "value": "[parameters('ftpRecurrenceFrequency')]"
                    },
                    "ftpRecurrenceInterval": {
                        "value": "[parameters('ftpRecurrenceInterval')]"
                    },
                    "fileNameMask": {
                        "value": "[parameters('ftpFileMask')]"
                    },
                    "apimSubscriptionKey": {
                        "value": "[parameters('apimSubscriptionKey')]"
                    },
                    "scenario": {
                        "value": "[parameters('scenario')]"
                    },
                    "scenarioStep": {
                        "value": "[parameters('scenarioStep')]"
                    },
                    "suspendQueueTopicName": {
                        "value": "[parameters('suspendQueueTopicName')]"
                    }
                }
            }
        }
    ]
}
tools\templates\endpoints\ftp\receive\ftpreceiveadapter.logicapp.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterftp.apiconnection.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterftp.apiconnection.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterftp.apiconnection.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterftp.apiconnpolicy.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterftp.apiconnpolicy.json
{
	"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
	"contentVersion": "1.0.0.0",
	"parameters": {
		"apiConnectionName": {
			"type": "string",
			"metadata": {
				"description": "Resource Name of the API Connection"
			}
		},
		"apiConnectionDisplayName": {
			"type": "string",
			"defaultValue": "[parameters('apiConnectionName')]",
			"metadata": {
				"description": "Display Name of the API Connection"
			}
		},
		"apiConnectionLocation": {
			"type": "string",
			"defaultValue": "[resourceGroup().location]",
			"metadata": {
				"description": "Location that we're deploying this resource to."
			}
		},
		"logicAppName": {
			"type": "String",
			"metadata": {
				"description": "Name of the LogicApp that we're creating a policy for."
			}
		},
		"tags": {
			"type": "object"
		}
	},
	"variables": {},
	"resources": [
		{
			"type": "Microsoft.Web/connections/accessPolicies",
			"apiVersion": "2016-06-01",
			"name": "[concat(parameters('apiConnectionName'),'/', parameters('logicAppName'))]",
			"location": "[parameters('apiConnectionLocation')]",
			"dependsOn": [],
			"properties": {
				"principal": {
					"type": "ActiveDirectory",
					"identity": {
						"tenantId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.tenantId]",
						"objectId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.principalId]"
					}
				}
			}
		}
	],
	"outputs": {}
}
tools\templates\endpoints\ftp\receive\ftpreceiveadapterftp.apiconnpolicy.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterservicebus.apiconnection.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterservicebus.apiconnection.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterservicebus.apiconnection.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterservicebus.apiconnpolicy.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\ftpreceiveadapterservicebus.apiconnpolicy.json
{
	"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
	"contentVersion": "1.0.0.0",
	"parameters": {
		"apiConnectionName": {
			"type": "string",
			"metadata": {
				"description": "Resource Name of the API Connection"
			}
		},
		"apiConnectionDisplayName": {
			"type": "string",
			"defaultValue": "[parameters('apiConnectionName')]",
			"metadata": {
				"description": "Display Name of the API Connection"
			}
		},
		"apiConnectionLocation": {
			"type": "string",
			"defaultValue": "[resourceGroup().location]",
			"metadata": {
				"description": "Location that we're deploying this resource to."
			}
		},
		"logicAppName": {
			"type": "String",
			"metadata": {
				"description": "Name of the LogicApp that we're creating a policy for."
			}
		},
		"tags": {
			"type": "object"
		}
	},
	"variables": {},
	"resources": [
		{
			"type": "Microsoft.Web/connections/accessPolicies",
			"apiVersion": "2016-06-01",
			"name": "[concat(parameters('apiConnectionName'),'/', parameters('logicAppName'))]",
			"location": "[parameters('apiConnectionLocation')]",
			"dependsOn": [],
			"properties": {
				"principal": {
					"type": "ActiveDirectory",
					"identity": {
						"tenantId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.tenantId]",
						"objectId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.principalId]"
					}
				}
			}
		}
	],
	"outputs": {}
}
tools\templates\endpoints\ftp\receive\ftpreceiveadapterservicebus.apiconnpolicy.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\receive\New-FtpReceiveAdapter-LogicApp.ps1
<#
.SYNOPSIS
Creates an ftp receive adapter for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER keyVaultName
The name of the key vault store.

.PARAMETER keyVaultApimSubscriptionSecretName
The name of secret in key vault which stores the apim subscription.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FtpReceiveAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth" -templateFile ".\ftpreceiveadapter.logicapp.json" -templateParameterFile ".\ftpreceiveadapter.logicapp.dev.parameters.json" -keyVaultName "kv-aimrstore-dev-xxxxx" -keyVaultApimSubscriptionSecretName "aim-apim-subscriptionkey-unlimited" -deploymentName "ftpreceiveadapter.logicapp.xxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Getting the subscription key from Key Vault for APIM"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

Write-Host "Deploying an ftp receive adapter`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --parameters "apimSubscriptionKey=$apimSubscriptionKey" --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\receive\New-FtpReceiveAdapterFtp-ApiConnection.ps1
<#
.SYNOPSIS
Creates an ftp api connection for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FtpReceiveAdapterFtp-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth" -templateFile ".\ftpreceiveadapterftp.apiconnection.json" -templateParameterFile ".\ftpreceiveadapterftp.apiconnection.dev.parameters.json" -deploymentName "ftpreceiveadapterftp.apiconnection.xxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an ftp api connection`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\receive\New-FtpReceiveAdapterFtp-ApiConnPolicy.ps1
<#
.SYNOPSIS
Creates an ftp receive api connection access policy.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FtpReceiveAdapterFtp-ApiConnPolicy.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -templateFile ".\ftpreceiveadapterftp.apiconnpolicy.json" -templateParameterFile ".\ftpreceiveadapterftp.apiconnpolicy.dev.parameters.json" -deploymentName "ftpreceiveadapterftp.apicaccesspolicy.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an api connection access policy`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\receive\New-FtpReceiveAdapterServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Creates a service bus api connection for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FtpReceiveAdapterServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth" -templateFile ".\ftpreceiveadaptersb.apiconnection.json" -templateParameterFile ".\ftpreceiveadaptersb.apiconnection.dev.parameters.json" -deploymentName "ftpreceiveadaptersb.apiconnection.xxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying a service bus api connection`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\receive\New-FtpReceiveAdapterServiceBus-ApiConnPolicy.ps1
<#
.SYNOPSIS
Creates an ftp receive service bus api connection access policy.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FtpReceiveAdapterServiceBus-ApiConnPolicy.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -templateFile ".\ftpreceiveadapterservicebus.apiconnpolicy.json" -templateParameterFile ".\ftpreceiveadapterservicebus.apiconnpolicy.dev.parameters.json" -deploymentName "ftpreceiveadapterservicebus.apicaccesspolicy.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an api connection access policy`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\receive\Remove-FtpReceiveAdapter-LogicApp.ps1
<#
.SYNOPSIS
Tears down the ftp receive adapter.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FtpReceiveAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth-xxxxx" -resourceName "logic-Aim-FtpPassthru-ReceiveLocation-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

if ($resourceExists) {
    Write-Host "Removing the ftp receive adapter resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

    Write-Host "Removed the ftp receive adapter resource: $resourceName"
}
else {
    Write-Host "The ftp receive adapter resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\ftp\receive\Remove-FtpReceiveAdapterFtp-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the ftp api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FtpReceiveAdapterFtp-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth" -resourceName "ftpreceiveconnector-Aim-FtpPassthru-ReceiveLocation-dev"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the ftp api connection resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the ftp api connection resource: $resourceName"
}
else {
    Write-Host "The ftp api connection resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\ftp\receive\Remove-FtpReceiveAdapterServiceBus-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the ftp receive adapters service bus api connection.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
.\Remove-FtpReceiveAdapterServiceBus-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth" -resourceName "topicpublisherconnector-ftpreceiveadapater-dev"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the ftp receive adapters service bus api connection resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the ftp receive adapters service bus api connection resource: $resourceName"
}
else {
    Write-Host "The ftp receive adapters service bus api connection resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\ftp\receive\TearDown-100-FtpReceiveAdapterFtp-ApiConnection.ps1.liquid
 
tools\templates\endpoints\ftp\receive\TearDown-100-FtpReceiveAdapterServiceBus-ApiConnection.ps1.liquid
 
tools\templates\endpoints\ftp\receive\TearDown-105-FtpReceiveAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\ftp\send\Deploy-100-FtpSendAdapter-ApiConnection.ps1.liquid
 
tools\templates\endpoints\ftp\send\Deploy-105-FtpSendAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\ftp\send\Deploy-110-FtpSendAdapter-ApiConnPolicy.ps1.liquid
 
tools\templates\endpoints\ftp\send\ftpsendadapter.apiconnection.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\send\ftpsendadapter.apiconnection.json.liquid
 
tools\templates\endpoints\ftp\send\ftpsendadapter.apiconnection.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\send\ftpsendadapter.apiconnpolicy.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\send\ftpsendadapter.apiconnpolicy.json
{
	"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
	"contentVersion": "1.0.0.0",
	"parameters": {
		"apiConnectionName": {
			"type": "string",
			"metadata": {
				"description": "Resource Name of the API Connection"
			}
		},
		"apiConnectionDisplayName": {
			"type": "string",
			"defaultValue": "[parameters('apiConnectionName')]",
			"metadata": {
				"description": "Display Name of the API Connection"
			}
		},
		"apiConnectionLocation": {
			"type": "string",
			"defaultValue": "[resourceGroup().location]",
			"metadata": {
				"description": "Location that we're deploying this resource to."
			}
		},
		"logicAppName": {
			"type": "String",
			"metadata": {
				"description": "Name of the LogicApp that we're creating a policy for."
			}
		},
		"tags": {
			"type": "object"
		}
	},
	"variables": {},
	"resources": [
		{
			"type": "Microsoft.Web/connections/accessPolicies",
			"apiVersion": "2016-06-01",
			"name": "[concat(parameters('apiConnectionName'),'/', parameters('logicAppName'))]",
			"location": "[parameters('apiConnectionLocation')]",
			"dependsOn": [],
			"properties": {
				"principal": {
					"type": "ActiveDirectory",
					"identity": {
						"tenantId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.tenantId]",
						"objectId": "[reference(resourceId('Microsoft.Web/sites', parameters('logicAppName')),'2021-01-15', 'full').identity.principalId]"
					}
				}
			}
		}
	],
	"outputs": {}
}
tools\templates\endpoints\ftp\send\ftpsendadapter.apiconnpolicy.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\send\ftpsendadapter.logicapp.dev.parameters.json.liquid
 
tools\templates\endpoints\ftp\send\ftpsendadapter.logicapp.json
{
    "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "logicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of this LogicApp."
            }
        },
        "logicAppLocation": {
            "defaultValue": "[resourceGroup().location]",
            "type": "string",
            "metadata": {
                "description": "Location (region) or ISE that this LogicApp is to be deployed to. Defaults to the ResourceGroup location."
            }
        },
        "logicAppStartupState": {
            "type": "string",
            "defaultValue": "Enabled",
            "allowedValues": [ "Enabled", "Disabled" ],
            "metadata": {
                "description": "Initial state of the LogicApp after it is deployed."
            }
        },
        "messageBusResourceGroupName": {
            "type": "String",
            "metadata": {
                "description": "Name of the ResourceGroup that MessageBus artifacts are deployed to (e.g. APIM or RoutingSlipRouter LogicApp)."
            }
        },
        "routingSlipRouterLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to route via the RoutingSlip."
            }
        },
        "routerRetryPolicy": {
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "type": "object",
            "metadata": {
                "description": "Retry Policy to use when calling RoutingSlipRouter."
            }
        },
        "apimServiceName": {
            "type": "string",
            "metadata": {
                "description": "Name of the APIM Service used for MessageBus operations."
            }
        },
        "apimSubscriptionKey": {
            "type": "securestring",
            "metadata": {
                "description": "Subscription Key used to access APIM."
            }
        },
        "apimRetryPolicy": {
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "type": "object",
            "metadata": {
                "description": "Retry Policy to use when calling APIM."
            }
        },
        "ftpSendApiConnectionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the API Connection used for FTP Send operations."
            }
        },
        "ftpSendFolder": {
            "defaultValue": "/",
            "type": "string",
            "metadata": {
                "description": "The path where the FTP connector send files."
            }
        },
        "ftpSendFileName": {
            "defaultValue": "%MessageID%-%SourceFileName%",
            "type": "string",
            "metadata": {
                "description": "The name of the file to send (can include macro values e.g. %MessageID% or %SourceFileName%)."
            }
        },
        "scenarioStep": {
            "defaultValue": "ftpSendAdapter",
            "type": "string",
            "metadata": {
                "description": "The step within a Scenario that this LogicApp is running under e.g. ftpSendAdapter."
            }
        },
        "tags": {
            "type": "object"
        }
    },
    "variables": {
        "apimServiceResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.ApiManagement/service', parameters('apimServiceName'))]",
        "configurationManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimconfigurationmanager')]",
        "messagingManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimmessagingmanager')]",
        "ftpSendApiConnectionResourceId": "[resourceId('Microsoft.Web/connections', parameters('ftpSendApiConnectionName'))]",
        "routingSlipRouterLogicAppResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.Logic/workflows', parameters('routingSlipRouterLogicAppName'))]"
    },
    "resources": [
        {
            "type": "Microsoft.Logic/workflows",
            "apiVersion": "2017-07-01",
            "name": "[parameters('logicAppName')]",
            "location": "[parameters('logicAppLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "state": "[parameters('logicAppStartupState')]",
                "definition": {
                    "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
                    "contentVersion": "1.0.0.0",
                    "parameters": {
                        "$connections": {
                            "defaultValue": {},
                            "type": "Object"
                        },
                        "ftpSendFolder": {
                            "type": "String",
                            "description": "The path where the FTP connector send files."
                        },
                        "ftpSendFileName": {
                            "type": "String",
                            "description": "The name of the file to send (can include macro values e.g. %MessageID% or %SourceFileName%))."
                        },
                        "scenarioStep": {
                            "type": "String",
                            "description": "The step within a Scenario that this LogicApp is running under e.g. ftpSendAdapter."
                        },
                        "apimSubscriptionKey": {
                            "type": "SecureString",
                            "description": "Subscription Key used to access APIM."
                        }
                    },
                    "triggers": {
                        "manual": {
                            "correlation": {
                                "clientTrackingId": "@coalesce(triggerBody()?['header']?['properties']?['trackingId'], guid())"
                            },
                            "type": "Request",
                            "kind": "Http",
                            "inputs": {
                                "schema": {}
                            }
                        }
                    },
                    "actions": {
                        "Initialize_StatusCode_variable": {
                            "runAfter": {},
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "StatusCode",
                                        "type": "integer",
                                        "value": 500
                                    }
                                ]
                            }
                        },
                        "Initialize_FaultMessage_variable": {
                            "runAfter": {
                                "Initialize_StatusCode_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "FaultMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_ErrorMessage_variable": {
                            "runAfter": {
                                "Initialize_FaultMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ErrorMessage",
                                        "type": "string",
                                        "value": "An error occurred in the @{workflow()?['name']} (@{workflow()?['run']?['name']}) LogicApp"
                                    }
                                ]
                            }
                        },
                        "Initialize_Checkpoint_variable": {
                            "runAfter": {
                                "Initialize_ErrorMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Checkpoint",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_Envelope_variable": {
                            "runAfter": {
                                "Initialize_Checkpoint_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Envelope",
                                        "type": "object",
                                        "value": "@triggerBody()"
                                    }
                                ]
                            }
                        },
                        "Initialize_Configuration_variable": {
                            "runAfter": {
                                "Initialize_Envelope_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Configuration",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_BodyContent_variable": {
                            "runAfter": {
                                "Initialize_Configuration_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "BodyContent",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_SendFileName_variable": {
                            "runAfter": {
                                "Initialize_BodyContent_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "SendFileName",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "MessageSender:_Were_we_Successful": {
                            "actions": {
                                "Routing:_Call_RoutingSlipRouter": {
                                    "runAfter": {},
                                    "type": "Workflow",
                                    "inputs": {
                                        "body": "@variables('Envelope')",
                                        "headers": {
                                            "Aim-Clear-Cache": "@coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], false)",
                                            "Aim-Enable-Trace": "@coalesce(triggerOutputs()?['headers']?['Aim-Enable-Trace'], false)",
                                            "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                            "Content-Type": "application/json"
                                        },
                                        "host": {
                                            "triggerName": "manual",
                                            "workflow": {
                                                "id": "[variables('routingSlipRouterLogicAppResourceId')]"
                                            }
                                        },
                                        "retryPolicy": "[parameters('routerRetryPolicy')]"
                                    }
                                },
                                "Routing:_Check_StatusCode": {
                                    "runAfter": {
                                        "Routing:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "Routing:Success:_Send_ACK-Content_response": {
                                                    "runAfter": {},
                                                    "type": "Response",
                                                    "kind": "Http",
                                                    "inputs": {
                                                        "body": "@body('Routing:_Call_RoutingSlipRouter')",
                                                        "headers": {
                                                            "Aim-Clear-Cache": "@coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], false)",
                                                            "Aim-Enable-Trace": "@coalesce(triggerOutputs()?['headers']?['Aim-Enable-Trace'], false)",
                                                            "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                                            "Content-Type": "application/json"
                                                        },
                                                        "statusCode": 200
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "Routing:Error:_Build_NACK_message": {
                                                "runAfter": {
                                                    "Routing:Error:_Do_we_have_a_Fault_Message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "Compose",
                                                "inputs": {
                                                    "body": [
                                                        {
                                                            "$content": {
                                                                "code": "500",
                                                                "message": "@variables('ErrorMessage')",
                                                                "lastCheckpoint": "@variables('Checkpoint')",
                                                                "fault": "@variables('FaultMessage')"
                                                            },
                                                            "$contentType": "application/json",
                                                            "$part": 1,
                                                            "$partType": "http://schemas.microsoft.com/aim#nack"
                                                        }
                                                    ],
                                                    "header": {
                                                        "properties": {
                                                            "createDate": "@utcNow()",
                                                            "envelopeType": "nack",
                                                            "messageId": "@guid()",
                                                            "rootPart": 1,
                                                            "trackingId": "@triggerBody()?['header']?['properties']?['trackingId']"
                                                        },
                                                        "routing": {
                                                            "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                        },
                                                        "routingSlip": {},
                                                        "state": {}
                                                    }
                                                }
                                            },
                                            "Routing:Error:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "Routing:Error:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "Routing:Error:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the RoutingSlipRouter Logic App"
                                                        }
                                                    },
                                                    "Routing:Error:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('Routing:_Call_RoutingSlipRouter')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "Routing:Error:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('Routing:_Call_RoutingSlipRouter')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('Routing:_Call_RoutingSlipRouter')?['statusCode'], outputs('Routing:_Call_RoutingSlipRouter')?['body']?['statusCode'], actions('Routing:_Call_RoutingSlipRouter')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('Routing:_Call_RoutingSlipRouter')?['error']?['message'], outputs('Routing:_Call_RoutingSlipRouter')?['body']?['message'], actions('Routing:_Call_RoutingSlipRouter')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('Routing:_Call_RoutingSlipRouter')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "Routing:Error:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "Routing:Error:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the RoutingSlipRouter Logic App"
                                                            }
                                                        },
                                                        "Routing:Error:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "Routing:Error:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('Routing:Error:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('Routing:_Call_RoutingSlipRouter')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            },
                                            "Routing:Error:_Send_NACK_response": {
                                                "runAfter": {
                                                    "Routing:Error:_Build_NACK_message": [
                                                        "Succeeded"
                                                    ]
                                                },
                                                "type": "Response",
                                                "kind": "Http",
                                                "inputs": {
                                                    "body": "@outputs('Routing:Error:_Build_NACK_message')",
                                                    "headers": {
                                                        "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                        "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')",
                                                        "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                                        "Content-Type": "application/json"
                                                    },
                                                    "statusCode": 200
                                                }
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "Routing:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "Routing:_Call_RoutingSlipRouter": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('Routing:_Call_RoutingSlipRouter')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_SendToFTP": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "else": {
                                "actions": {
                                    "Failure:_Build_NACK_message": {
                                        "runAfter": {},
                                        "type": "Compose",
                                        "inputs": {
                                            "body": [
                                                {
                                                    "$content": {
                                                        "code": "500",
                                                        "message": "@variables('ErrorMessage')",
                                                        "lastCheckpoint": "@variables('Checkpoint')",
                                                        "fault": "@variables('FaultMessage')"
                                                    },
                                                    "$contentType": "application/json",
                                                    "$part": 1,
                                                    "$partType": "http://schemas.microsoft.com/aim#nack"
                                                }
                                            ],
                                            "header": {
                                                "properties": {
                                                    "createDate": "@utcNow()",
                                                    "envelopeType": "nack",
                                                    "messageId": "@guid()",
                                                    "rootPart": 1,
                                                    "trackingId": "@triggerBody()?['header']?['properties']?['trackingId']"
                                                },
                                                "routing": {
                                                    "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                },
                                                "routingSlip": {},
                                                "state": {}
                                            }
                                        }
                                    },
                                    "Failure:_Send_NACK_response": {
                                        "runAfter": {
                                            "Failure:_Build_NACK_message": [
                                                "Succeeded"
                                            ]
                                        },
                                        "type": "Response",
                                        "kind": "Http",
                                        "inputs": {
                                            "body": "@outputs('Failure:_Build_NACK_message')",
                                            "headers": {
                                                "Aim-Clear-Cache": "@coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], false)",
                                                "Aim-Enable-Trace": "@coalesce(triggerOutputs()?['headers']?['Aim-Enable-Trace'], false)",
                                                "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                                "Content-Type": "application/json"
                                            },
                                            "statusCode": 200
                                        }
                                    }
                                }
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "SendToFTP"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_Configuration": {
                            "actions": {
                                "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": {
                                    "runAfter": {},
                                    "type": "ApiManagement",
                                    "inputs": {
                                        "api": {
                                            "id": "[variables('configurationManagerApiResourceId')]"
                                        },
                                        "method": "get",
                                        "pathTemplate": {
                                            "parameters": {
                                                "scenario": "@{encodeURIComponent(triggerBody()?['header']?['properties']?['scenario'])}",
                                                "step": "@{encodeURIComponent(parameters('scenarioStep'))}"
                                            },
                                            "template": "/aimconfigurationmanager/configuration/{scenario}/{step}"
                                        },
                                        "queries": {
                                            "clearCache": "@{coalesce(triggerOutputs()?['headers']?['Aim-Clear-Cache'], 'false')}"
                                        },
                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                    }
                                },
                                "GetConfiguration:_Check_Status_Code": {
                                    "runAfter": {
                                        "GetConfiguration:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "GetConfiguration:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {
                                                        "GetConfiguration:Success:_Set_Configuration_variable": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "GetConfiguration"
                                                    }
                                                },
                                                "GetConfiguration:Success:_Set_Configuration_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Configuration",
                                                        "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "GetConfiguration:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "GetConfiguration:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "GetConfiguration:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                        }
                                                    },
                                                    "GetConfiguration:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "GetConfiguration:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['statusCode'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['message'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('GetConfiguration:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "GetConfiguration:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Initialize_SendFileName_variable": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            ""
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Check_BodyContent": {
                            "actions": {
                                "CheckBodyContent:_Body_Content_is_missing": {
                                    "actions": {
                                        "CheckBodyContent:Missing:_Set_Checkpoint_variable": {
                                            "runAfter": {},
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "Checkpoint",
                                                "value": "NoBodyContent"
                                            }
                                        }
                                    },
                                    "runAfter": {
                                        "CheckBodyContent:_Select_Root_Part": [
                                            "Succeeded"
                                        ]
                                    },
                                    "else": {
                                        "actions": {
                                            "CheckBodyContent:Success:_Set_Checkpoint_variable": {
                                                "runAfter": {},
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "Checkpoint",
                                                    "value": "CheckBodyContent"
                                                }
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "equals": [
                                                    "@coalesce(body('CheckBodyContent:_Select_Root_Part')?[0]?['$content'], '')",
                                                    ""
                                                ]
                                            }
                                        ]
                                    },
                                    "type": "If"
                                },
                                "CheckBodyContent:_Select_Root_Part": {
                                    "runAfter": {},
                                    "type": "Query",
                                    "inputs": {
                                        "from": "@variables('Envelope')?['body']",
                                        "where": "@equals(item()?['$part'], variables('Envelope')?['header']?['properties']?['rootPart'])"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Get_Configuration": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetConfiguration"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_BodyContent": {
                            "actions": {
                                "GetBodyContent:_Call_APIM_MessageManager.GetBodyContent": {
                                    "runAfter": {},
                                    "type": "ApiManagement",
                                    "inputs": {
                                        "api": {
                                            "id": "[variables('messagingManagerApiResourceId')]"
                                        },
                                        "body": "@variables('Envelope')",
                                        "headers": {
                                            "Aim-Tracking-Id": "@{triggerBody()?['header']?['properties']?['trackingId']}",
                                            "Content-Type": "application/json"
                                        },
                                        "method": "post",
                                        "pathTemplate": {
                                            "parameters": {},
                                            "template": "/aimmessagingmanager/getbodycontent"
                                        },
                                        "queries": {
                                            "clearCache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                            "enableTrace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                        },
                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                    }
                                },
                                "GetBodyContent:_Check_Status_Code": {
                                    "runAfter": {
                                        "GetBodyContent:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "GetBodyContent:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {
                                                        "GetBodyContent:Success:_Set_BodyContent_variable": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "GetBodyContent"
                                                    }
                                                },
                                                "GetBodyContent:Success:_Set_BodyContent_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "BodyContent",
                                                        "value": "@{base64ToString(body('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['$content'])}"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "GetBodyContent:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "GetBodyContent:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "GetBodyContent:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the MessageManager GetBodyContent operation"
                                                        }
                                                    },
                                                    "GetBodyContent:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "GetBodyContent:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['statusCode'], outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['body']?['statusCode'], actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['error']?['message'], outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['body']?['message'], actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "GetBodyContent:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "GetBodyContent:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the MessageManager GetBodyContent operation"
                                                            }
                                                        },
                                                        "GetBodyContent:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "GetBodyContent:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('GetBodyContent:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "GetBodyContent:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "GetBodyContent:_Call_APIM_MessageManager.GetBodyContent": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('GetBodyContent:_Call_APIM_MessageManager.GetBodyContent')['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Check_BodyContent": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "CheckBodyContent"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_GetSendFileName": {
                            "actions": {
                                "GetSendFileName:_Set_SendFileName_variable": {
                                    "description": "A full list of supported FileName macros can be found here: https://social.technet.microsoft.com/wiki/contents/articles/8823.biztalk-server-list-of-macros.aspx. At this time we are not supporting the Party macros.",
                                    "type": "SetVariable",
                                    "runAfter": {},
                                    "inputs": {
                                        "name": "SendFileName",
                                        "value": "@{replace(replace(replace(replace(replace(replace(replace(parameters('ftpSendFileName'), '%MessageID%', coalesce(triggerBody()?['header']?['properties']?['messageId'], guid())), '%SourceFileName%', coalesce(triggerBody()?['header']?['properties']?['receivedFileName'], 'myfile.txt')), '%datetime%', utcNow('yyyy-MM-ddThhmmss')), '%datetime_bts2000%', utcNow('yyyyMMddhhmmsss')), '%datetime.tz%', utcNow('yyyy-MM-ddThhmmssK')), '%time%', utcNow('hhmmss')), '%time.tz%', utcNow('hhmmssK'))}"
                                    }
                                },
                                "SendToFTP:_Set_Checkpoint_variable": {
                                    "runAfter": {
                                        "GetSendFileName:_Set_SendFileName_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "Checkpoint",
                                        "value": "GetSendFileName"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_Get_BodyContent": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "or": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetBodyContent"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "NoBodyContent"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_SendToFTP": {
                            "actions": {
                                "SendToFTP:_Check_Status_Code": {
                                    "runAfter": {
                                        "SendToFTP:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "SendToFTP:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "SendToFTP"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "SendToFTP:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "SendToFTP:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "SendToFTP:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to send a file using the FTP connector"
                                                        }
                                                    },
                                                    "SendToFTP:Fault:_Create_Fault_Message": {
                                                        "runAfter": {},
                                                        "type": "Compose",
                                                        "inputs": {
                                                            "fault": {
                                                                "faultActor": "@concat(workflow()?['name'], '.', actions('SendToFTP:_Create_File')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                "faultCategory": "Error",
                                                                "faultCode": "@{coalesce(outputs('SendToFTP:_Create_File')?['statusCode'], outputs('SendToFTP:_Create_File')?['body']?['statusCode'], actions('SendToFTP:_Create_File')?['error']?['code'])}",
                                                                "faultMessage": "@{coalesce(outputs('SendToFTP:_Create_File')?['error']?['message'], outputs('SendToFTP:_Create_File')?['body']?['message'], actions('SendToFTP:_Create_File')?['error']?['message'])}",
                                                                "faultReason": "@{actions('SendToFTP:_Create_File')?['status']}"
                                                            }
                                                        }
                                                    },
                                                    "SendToFTP:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {
                                                            "SendToFTP:Fault:_Create_Fault_Message": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('SendToFTP:Fault:_Create_Fault_Message')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "SendToFTP:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('SendToFTP:_Create_File')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('SendToFTP:_Create_File')?['statusCode'], outputs('SendToFTP:_Create_File')?['body']?['statusCode'])}",
                                                                    "faultMessage": "@{coalesce(outputs('SendToFTP:_Create_File')?['error']?['message'], outputs('SendToFTP:_Create_File')?['body']?['message'])}",
                                                                    "faultReason": "@actions('SendToFTP:_Create_File')?['inputs']?['path']"
                                                                }
                                                            }
                                                        },
                                                        "SendToFTP:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "SendToFTP:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to send a file using the FTP connector"
                                                            }
                                                        },
                                                        "SendToFTP:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "SendToFTP:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('SendToFTP:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('SendToFTP:_Create_File')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "SendToFTP:_Create_File": {
                                    "inputs": {
                                        "body": "@variables('BodyContent')",
                                        "headers": {
                                            "ReadFileMetadataFromServer": true
                                        },
                                        "host": {
                                            "connection": {
                                                "name": "@parameters('$connections')['ftpsend']['connectionId']"
                                            }
                                        },
                                        "method": "post",
                                        "path": "/datasets/default/files",
                                        "queries": {
                                            "folderPath": "@parameters('ftpSendFolder')",
                                            "name": "@variables('SendFileName')",
                                            "queryParametersSingleEncoded": true
                                        }
                                    },
                                    "runAfter": {},
                                    "runtimeConfiguration": {
                                        "contentTransfer": {
                                            "transferMode": "Chunked"
                                        }
                                    },
                                    "type": "ApiConnection"
                                },
                                "SendToFTP:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "SendToFTP:_Create_File": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('SendToFTP:_Create_File')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Step:_GetSendFileName": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "GetSendFileName"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        }
                    },
                    "outputs": {}
                },
                "parameters": {
                    "$connections": {
                        "value": {
                            "ftpsend": {
                                "connectionId": "[variables('ftpSendApiConnectionResourceId')]",
                                "connectionName": "[parameters('ftpSendApiConnectionName')]",
                                "id": "[concat(subscription().id, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/ftp')]"
                            }
                        }
                    },
                    "ftpSendFolder": {
                        "value": "[parameters('ftpSendFolder')]"
                    },
                    "ftpSendFileName": {
                        "value": "[parameters('ftpSendFileName')]"
                    },
                    "scenarioStep": {
                        "value": "[parameters('scenarioStep')]"
                    },
                    "apimSubscriptionKey": {
                        "value": "[parameters('apimSubscriptionKey')]"
                    }
                }
            }
        }
    ]
}
tools\templates\endpoints\ftp\send\ftpsendadapter.logicapp.prod.parameters.json.liquid
 
tools\templates\endpoints\ftp\send\New-FtpSendAdapter-ApiConnection.ps1
<#
.SYNOPSIS
Creates an ftp connector for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
./New-FtpSendAdapter-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth-xxxxx" -templateFile ".\ftpconnection.json" -templateParameterFile ".\ftpconnection.dev.parameters.json" -deploymentName "ftpsendconnection"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an ftp connector`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\send\New-FtpSendAdapter-ApiConnPolicy.ps1
<#
.SYNOPSIS
Creates an ftp send api connection access policy.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
.\New-FtpSendAdapter-ApiConnPolicy.ps1 -resourceGroupName "rg-aimapp-application-dev-uksouth-xxxxx" -templateFile ".\ftpsendadapter.apiconnpolicy.json" -templateParameterFile ".\ftpsendadapter.apiconnpolicy.dev.parameters.json" -deploymentName "ftpsendadapter.apicaccesspolicy.xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Deploying an api connection access policy`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\send\New-FtpSendAdapter-LogicApp.ps1
<#
.SYNOPSIS
Creates an ftp adapter for an application.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroupName
Name of the resource group where the resources will be created.

.PARAMETER templateFile
Path to the ARM template that needs to be deployed.

.PARAMETER templateParameterFile
Path to the ARM template parameter file that contains the parameter values related to the template file.

.PARAMETER deploymentName
The name used to identify this instance of the deployment.

.EXAMPLE
./New-FtpSendAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth-xxxxx" -templateFile ".\ftpadapter.json" -templateParameterFile ".\ftpadapter.dev.parameters.json" -deploymentName "ftpadapter"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]    
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]    
    [string] $templateFile,
    [parameter(Mandatory = $true)]
    [string] $templateParameterFile,
    [parameter(Mandatory = $true)]
    [string] $keyVaultName,
    [parameter(Mandatory = $true)]
    [string] $keyVaultApimSubscriptionSecretName,
    [parameter(Mandatory = $true)]
    [string] $deploymentName
)

Write-Host "Getting the subscription from Key Vault for the routing slip router Logic App"

$apimSubscriptionKey = az keyvault secret show --name $keyVaultApimSubscriptionSecretName --vault-name $keyVaultName --query value
if (!$apimSubscriptionKey) {
    throw "Unable to get a secret from the vault $keyVaultName with the name $keyVaultApimSubscriptionSecretName"
}

Write-Host "Deploying an ftp adapter`r`n Template File: $templateFile`r`n Parameter File: $templateParameterFile`r`n Deployment Name: $deploymentName`r`n"

az deployment group create --resource-group $resourceGroupName --template-file $templateFile --parameters $templateParameterFile "apimSubscriptionKey=$apimSubscriptionKey" --name $deploymentName

Write-Host "Deployment complete"
tools\templates\endpoints\ftp\send\Remove-FtpSendAdapter-ApiConnection.ps1
<#
.SYNOPSIS
Tears down the ftp connector.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
./Remove-FtpSendAdapter-ApiConnection.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth-xxxxx" -resourceName "ftpreceiveconnector-Aim-FtpPassthru-ReceiveLocation-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

if ($resourceExists) {
    Write-Host "Removing the ftp connector resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "connections" --namespace "Microsoft.Web"

    Write-Host "Removed the ftp connector resource: $resourceName"
}
else {
    Write-Host "The ftp connector resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\ftp\send\Remove-FtpSendAdapter-LogicApp.ps1
<#
.SYNOPSIS
Tears down the ftp adapter.

.DESCRIPTION
Prior to running this script ensure you are authenticated against Azure and have the desired subscription set.

.PARAMETER resourceGroup
The name of the resource group containing the resources to remove.

.PARAMETER resourceName
The name of the resource to remove.

.EXAMPLE
./Remove-FtpSendAdapter-LogicApp.ps1 -resourceGroupName "rg-aimapp-aim-ftppassthru-dev-uksouth-xxxxx" -resourceName "logic-Aim-FtpPassthru-ReceiveLocation-dev-xxxxx"
#>

[CmdletBinding()]
Param(
    [parameter(Mandatory = $true)]
    [string] $resourceGroupName,
    [parameter(Mandatory = $true)]
    [string] $resourceName
)

$resourceExists = az resource show --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

if ($resourceExists) {
    Write-Host "Removing the ftp adapter resource: $resourceName"

    az resource delete --name $resourceName --resource-group $resourceGroupName --resource-type "workflows" --namespace "Microsoft.Logic"

    Write-Host "Removed the ftp adapter resource: $resourceName"
}
else {
    Write-Host "The ftp adapter resource $resourceName does not exist in resource group $resourceGroupName"
}
tools\templates\endpoints\ftp\send\TearDown-100-FtpSendAdapter-ApiConnection.ps1.liquid
 
tools\templates\endpoints\ftp\send\TearDown-105-FtpSendAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\http\receive\Deploy-105-HttpReceiveAdapter-LogicApp.ps1.liquid
 
tools\templates\endpoints\http\receive\httpreceiveadapter.logicapp.dev.parameters.json.liquid
 
tools\templates\endpoints\http\receive\httpreceiveadapter.logicapp.json
{
    "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "logicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of this LogicApp."
            }
        },
        "logicAppLocation": {
            "defaultValue": "[resourceGroup().location]",
            "type": "string",
            "metadata": {
                "description": "Location (region) or ISE that this LogicApp is to be deployed to. Defaults to the ResourceGroup location."
            }
        },
        "logicApStartupState": {
            "type": "string",
            "defaultValue": "Enabled",
            "allowedValues": [ "Enabled", "Disabled" ],
            "metadata": {
                "description": "Initial state of the LogicApp after it is deployed."
            }
        },
        "messageBusResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that MessageBus artifacts are deployed to (e.g. APIM or RoutingSlipRouter LogicApp)."
            }
        },
        "systemApplicationResourceGroupName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ResourceGroup that SystemApplication artifacts are deployed to (e.g. ServiceBus or MessageConstructor LogicApp)."
            }
        },
        "integrationAccountName": {
            "type": "string",
            "metadata": {
                "description": "Name of the IntegrationAccount connected to this LogicApp."
            }
        },
        "messageConstructorLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to handle File Message Construction and Sending."
            }
        },
        "messageResponseHandlerLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to handle retrieving the response in a two-way messaging scenario."
            }
        },
        "messageSuspendProcessorLogicAppName": {
            "type": "string",
            "metadata": {
                "description": "Name of the LogicApp to call to handle suspending of messages."
            }
        },
        "suspendQueueTopicName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ServiceBus Topic that suspended messages are sent to."
            }
        },
        "responseTopicName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ServiceBus Topic where response messages are found for two-way operations."
            }
        },
        "responseSubscriptionName": {
            "type": "string",
            "metadata": {
                "description": "Name of the ServiceBus Subscription used to get response messages for two-way operations."
            }
        },
        "apimServiceName": {
            "type": "string",
            "metadata": {
                "description": "Name of the APIM Service used for MessageBus operations."
            }
        },
        "apimSubscriptionKey": {
            "type": "securestring",
            "metadata": {
                "description": "Subscription Key used to access APIM."
            }
        },
        "apimRetryPolicy": {
            "type": "object",
            "defaultValue": {
                "count": 3,
                "interval": "PT5S",
                "type": "fixed"
            },
            "metadata": {
                "description": "Retry Policy to use when calling APIM."
            }
        },

        "scenario": {
            "type": "string",
            "metadata": {
                "description": "The name of the Scenario that this LogicApp is running under e.g. ApplicationName + ReceivePort/Location Name."
            }
        },
        "scenarioStep": {
            "defaultValue": "httpReceiveAdapter",
            "type": "string",
            "metadata": {
                "description": "The step within a Scenario that this LogicApp is running under e.g. httpReceiveAdapter."
            }
        },
        "tags": {
            "type": "object"
        }
    },
    "variables": {
        "apimServiceResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.ApiManagement/service', parameters('apimServiceName'))]",
        "configurationManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimconfigurationmanager')]",
        "messagingManagerApiResourceId": "[concat(variables('apimServiceResourceId'), '/apis/aimmessagingmanager')]",
        "messageConstructorLogicAppResourceId": "[resourceId(parameters('systemApplicationResourceGroupName'), 'Microsoft.Logic/workflows', parameters('messageConstructorLogicAppName'))]",
        "messageResponseHandlerLogicAppResourceId": "[resourceId(parameters('systemApplicationResourceGroupName'), 'Microsoft.Logic/workflows', parameters('messageResponseHandlerLogicAppName'))]",
        "messageSuspendProcessorLogicAppResourceId": "[resourceId(parameters('systemApplicationResourceGroupName'), 'Microsoft.Logic/workflows', parameters('messageSuspendProcessorLogicAppName'))]",
        "integrationAccountResourceId": "[resourceId(parameters('messageBusResourceGroupName'), 'Microsoft.Logic/integrationAccounts', parameters('integrationAccountName'))]"
    },
    "resources": [
        {
            "type": "Microsoft.Logic/workflows",
            "apiVersion": "2017-07-01",
            "name": "[parameters('logicAppName')]",
            "location": "[parameters('logicAppLocation')]",
            "tags": "[parameters('tags')]",
            "properties": {
                "state": "[parameters('logicApStartupState')]",
                "integrationAccount": {
                    "id": "[variables('integrationAccountResourceId')]"
                },
                "definition": {
                    "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
                    "contentVersion": "1.0.0.0",
                    "parameters": {
                        "apimSubscriptionKey": {
                            "type": "SecureString",
                            "description": "Subscription Key used to access APIM."
                        },
                        "scenario": {
                            "type": "String",
                            "description": "The name of the Scenario that this LogicApp is running under e.g. ApplicationName + ReceivePort/Location Name."
                        },
                        "scenarioStep": {
                            "type": "String",
                            "description": "The step within a Scenario that this LogicApp is running under e.g. httpReceiveAdapter."
                        },
                        "clearCache": {
                            "defaultValue": true,
                            "type": "Bool",
                            "description": "Indicates if we should clear APIM cache before retrieved config items e.g. configurationEntries or routingSlips."
                        },
                        "suspendQueueTopicName": {
                            "type": "String",
                            "description": "Name of the ServiceBus Topic that suspended messages are sent to."
                        },
                        "responseTopicName": {
                            "type": "String",
                            "description": "Name of the ServiceBus Topic where response messages are found for two-way operations."
                        },
                        "responseSubscriptionName": {
                            "type": "String",
                            "description": "Name of the ServiceBus Subscription used to get response messages for two-way operations."
                        }
                    },
                    "triggers": {
                        "manual": {
                            "type": "Request",
                            "kind": "Http",
                            "inputs": {
                                "schema": {}
                            }
                        }
                    },
                    "actions": {
                        "Initialize_StatusCode_variable": {
                            "runAfter": {},
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "StatusCode",
                                        "type": "integer",
                                        "value": 500
                                    }
                                ]
                            }
                        },
                        "Initialize_FaultMessage_variable": {
                            "runAfter": {
                                "Initialize_StatusCode_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "FaultMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_ErrorMessage_variable": {
                            "runAfter": {
                                "Initialize_FaultMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ErrorMessage",
                                        "type": "string",
                                        "value": "An error occurred in the @{workflow()?['name']} (@{workflow()?['run']?['name']}) LogicApp"
                                    }
                                ]
                            }
                        },
                        "Initialize_ResponseMessage_variable": {
                            "runAfter": {
                                "Initialize_ErrorMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "ResponseMessage",
                                        "type": "object",
                                        "value": null
                                    }
                                ]
                            }
                        },
                        "Initialize_Checkpoint_variable": {
                            "runAfter": {
                                "Initialize_ResponseMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Checkpoint",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Initialize_Configuration_variable": {
                            "runAfter": {
                                "Initialize_Checkpoint_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "Configuration",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_TwoWayResponseMessage_variable": {
                            "runAfter": {
                                "Initialize_Configuration_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "TwoWayResponseMessage",
                                        "type": "object"
                                    }
                                ]
                            }
                        },
                        "Initialize_TwoWayResponseContent_variable": {
                            "runAfter": {
                                "Initialize_TwoWayResponseMessage_variable": [
                                    "Succeeded"
                                ]
                            },
                            "type": "InitializeVariable",
                            "inputs": {
                                "variables": [
                                    {
                                        "name": "TwoWayResponseContent",
                                        "type": "string"
                                    }
                                ]
                            }
                        },
                        "Respond:_Were_we_successful": {
                            "actions": {
                                "Respond:_Is_this_a_TwoWay_adapter": {
                                    "actions": {
                                        "Respond:TwoWay:_Call_Response_Handler": {
                                            "runAfter": {},
                                            "type": "Workflow",
                                            "inputs": {
                                                "body": {
                                                    "responseTopicName": "@{parameters('responseTopicName')}",
                                                    "responseSubscriptionName": "@{parameters('responseSubscriptionName')}",
                                                    "correlationId": "@variables('ResponseMessage')?['header']?['properties']?['correlationId']",
                                                    "responseTimeoutInMinutes": "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['responseTimeoutInMinutes'], 3)"
                                                },
                                                "headers": {
                                                    "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                    "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                                },
                                                "host": {
                                                    "triggerName": "manual",
                                                    "workflow": {
                                                        "id": "[variables('messageResponseHandlerLogicAppResourceId')]"
                                                    }
                                                }
                                            }
                                        },
                                        "Respond:TwoWay:_Check_StatusCode": {
                                            "runAfter": {
                                                "Respond:TwoWay:_Set_StatusCode_variable": [
                                                    "Succeeded"
                                                ]
                                            },
                                            "cases": {
                                                "Success": {
                                                    "case": 200,
                                                    "actions": {
                                                        "Respond:TwoWay:Success:_Set_TwoWayResponseMessage_variable": {
                                                            "runAfter": {},
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "TwoWayResponseMessage",
                                                                "value": "@body('Respond:TwoWay:_Call_Response_Handler')"
                                                            }
                                                        },
                                                        "Respond:TwoWay:Success:_Check_TwoWayResponse_ContentType": {
                                                            "runAfter": {
                                                                "Respond:TwoWay:Success:_Set_TwoWayResponseMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "If",
                                                            "actions": {
                                                                "Respond:TwoWay:Success:_Get_Response_BodyContent": {
                                                                    "runAfter": {},
                                                                    "type": "ApiManagement",
                                                                    "inputs": {
                                                                        "api": {
                                                                            "id": "[variables('messagingManagerApiResourceId')]"
                                                                        },
                                                                        "body": "@if(equals(variables('TwoWayResponseMessage')?['$content-encoding'], 'Base64'), json(decodeBase64(variables('TwoWayResponseMessage')?['$content'])), variables('TwoWayResponseMessage')?['$content'])",
                                                                        "headers": {
                                                                            "Aim-Tracking-Id": "@{variables('ResponseMessage')?['header']?['properties']?['trackingId']}",
                                                                            "Content-Type": "application/json"
                                                                        },
                                                                        "method": "post",
                                                                        "pathTemplate": {
                                                                            "parameters": {},
                                                                            "template": "/aimmessagingmanager/getbodycontent"
                                                                        },
                                                                        "queries": {
                                                                            "clearCache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                                            "enableTrace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                                                        },
                                                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                                                    }
                                                                },
                                                                "Respond:TwoWay:Success:GetBodyContent:_Check_Status_Code": {
                                                                    "runAfter": {
                                                                        "Respond:TwoWay:Success:GetBodyContent:_Set_StatusCode_variable": [
                                                                            "Succeeded"
                                                                        ]
                                                                    },
                                                                    "cases": {
                                                                        "Success": {
                                                                            "case": 200,
                                                                            "actions": {
                                                                                "Respond:TwoWay:Success:GetBodyContent:_Set_TwoWayResponseContent_variable": {
                                                                                    "runAfter": {},
                                                                                    "type": "SetVariable",
                                                                                    "inputs": {
                                                                                        "name": "TwoWayResponseContent",
                                                                                        "value": "@decodeBase64(body('Respond:TwoWay:Success:_Get_Response_BodyContent')?['$content'])"
                                                                                    }
                                                                                },
                                                                                "Respond:TwoWay:Success:GetBodyContent:Success:_Send_Response": {
                                                                                    "inputs": {
                                                                                        "body": "@variables('TwoWayResponseContent')",
                                                                                        "statusCode": 200,
                                                                                        "headers": {
                                                                                            "Content-Type": "@body('Respond:TwoWay:Success:_Get_Response_BodyContent')?['$contentType']"
                                                                                        }
                                                                                    },
                                                                                    "kind": "Http",
                                                                                    "runAfter": {
                                                                                        "Respond:TwoWay:Success:GetBodyContent:_Set_TwoWayResponseContent_variable": [
                                                                                            "Succeeded"
                                                                                        ]
                                                                                    },
                                                                                    "type": "Response"
                                                                                }
                                                                            }
                                                                        }
                                                                    },
                                                                    "default": {
                                                                        "actions": {
                                                                            "Respond:TwoWay:Success:GetBodyContent:Failure:_Do_we_have_a_Fault_Message": {
                                                                                "actions": {
                                                                                    "Respond:TwoWay:Success:GetBodyContent:Fault:_Set_ErrorMessage_variable": {
                                                                                        "runAfter": {
                                                                                            "Respond:TwoWay:Success:GetBodyContent:Fault:_Set_FaultMessage_variable": [
                                                                                                "Succeeded"
                                                                                            ]
                                                                                        },
                                                                                        "type": "SetVariable",
                                                                                        "inputs": {
                                                                                            "name": "ErrorMessage",
                                                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the MessageManager GetBodyContent operation"
                                                                                        }
                                                                                    },
                                                                                    "Respond:TwoWay:Success:GetBodyContent:Fault:_Set_FaultMessage_variable": {
                                                                                        "runAfter": {},
                                                                                        "type": "SetVariable",
                                                                                        "inputs": {
                                                                                            "name": "FaultMessage",
                                                                                            "value": "@body('Respond:TwoWay:Success:_Get_Response_BodyContent')"
                                                                                        }
                                                                                    }
                                                                                },
                                                                                "runAfter": {},
                                                                                "else": {
                                                                                    "actions": {
                                                                                        "Respond:TwoWay:Success:GetBodyContent:NoFault:_Create_Fault_Message": {
                                                                                            "runAfter": {},
                                                                                            "type": "Compose",
                                                                                            "inputs": {
                                                                                                "fault": {
                                                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('Respond:TwoWay:Success:_Get_Response_BodyContent')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                                                    "faultCategory": "Error",
                                                                                                    "faultCode": "@{coalesce(outputs('Respond:TwoWay:Success:_Get_Response_BodyContent')?['statusCode'], outputs('Respond:TwoWay:Success:_Get_Response_BodyContent')?['body']?['statusCode'], actions('Respond:TwoWay:Success:_Get_Response_BodyContent')?['error']?['code'])}",
                                                                                                    "faultMessage": "@{coalesce(outputs('Respond:TwoWay:Success:_Get_Response_BodyContent')?['error']?['message'], outputs('Respond:TwoWay:Success:_Get_Response_BodyContent')?['body']?['message'], actions('Respond:TwoWay:Success:_Get_Response_BodyContent')?['error']?['message'])}",
                                                                                                    "faultReason": "@{actions('Respond:TwoWay:Success:_Get_Response_BodyContent')?['status']}"
                                                                                                }
                                                                                            }
                                                                                        },
                                                                                        "Respond:TwoWay:Success:GetBodyContent:NoFault:_Set_ErrorMessage_variable": {
                                                                                            "runAfter": {
                                                                                                "Respond:TwoWay:Success:GetBodyContent:NoFault:_Set_FaultMessage_variable": [
                                                                                                    "Succeeded"
                                                                                                ]
                                                                                            },
                                                                                            "type": "SetVariable",
                                                                                            "inputs": {
                                                                                                "name": "ErrorMessage",
                                                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the MessageManager GetBodyContent operation"
                                                                                            }
                                                                                        },
                                                                                        "Respond:TwoWay:Success:GetBodyContent:NoFault:_Set_FaultMessage_variable": {
                                                                                            "runAfter": {
                                                                                                "Respond:TwoWay:Success:GetBodyContent:NoFault:_Create_Fault_Message": [
                                                                                                    "Succeeded"
                                                                                                ]
                                                                                            },
                                                                                            "type": "SetVariable",
                                                                                            "inputs": {
                                                                                                "name": "FaultMessage",
                                                                                                "value": "@outputs('Respond:TwoWay:Success:GetBodyContent:NoFault:_Create_Fault_Message')"
                                                                                            }
                                                                                        }
                                                                                    }
                                                                                },
                                                                                "expression": {
                                                                                    "and": [
                                                                                        {
                                                                                            "not": {
                                                                                                "equals": [
                                                                                                    "@body('Respond:TwoWay:Success:_Get_Response_BodyContent')?['fault']",
                                                                                                    null
                                                                                                ]
                                                                                            }
                                                                                        }
                                                                                    ]
                                                                                },
                                                                                "type": "If"
                                                                            },
                                                                            "Respond:TwoWay:Success:GetBodyContent:Failure:_Build_NACK_message": {
                                                                                "runAfter": {
                                                                                    "Respond:TwoWay:Success:GetBodyContent:Failure:_Do_we_have_a_Fault_Message": [
                                                                                        "Succeeded"
                                                                                    ]
                                                                                },
                                                                                "type": "Compose",
                                                                                "inputs": {
                                                                                    "body": [
                                                                                        {
                                                                                            "$content": {
                                                                                                "code": "500",
                                                                                                "message": "@variables('ErrorMessage')",
                                                                                                "lastCheckpoint": "@variables('Checkpoint')",
                                                                                                "fault": "@variables('FaultMessage')"
                                                                                            },
                                                                                            "$contentType": "application/json",
                                                                                            "$part": 1,
                                                                                            "$partType": "http://schemas.microsoft.com/aim#nack"
                                                                                        }
                                                                                    ],
                                                                                    "header": {
                                                                                        "properties": {
                                                                                            "createDate": "@utcNow()",
                                                                                            "envelopeType": "nack",
                                                                                            "messageId": "@guid()",
                                                                                            "rootPart": 1,
                                                                                            "trackingId": "@body('Respond:TwoWay:_Call_Response_Handler')?['header']?['properties']?['trackingId']"
                                                                                        },
                                                                                        "routing": {
                                                                                            "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                                                        },
                                                                                        "routingSlip": {},
                                                                                        "state": {}
                                                                                    }
                                                                                }
                                                                            },
                                                                            "Respond:TwoWay:Success:GetBodyContent:Failure:_Send_to_SuspendQueue": {
                                                                                "runAfter": {
                                                                                    "Respond:TwoWay:Success:GetBodyContent:Failure:_Build_NACK_message": [
                                                                                        "Succeeded",
                                                                                        "Failed",
                                                                                        "TimedOut"
                                                                                    ]
                                                                                },
                                                                                "type": "Workflow",
                                                                                "inputs": {
                                                                                    "body": {
                                                                                        "nackMessage": "@outputs('Respond:TwoWay:Success:GetBodyContent:Failure:_Build_NACK_message')",
                                                                                        "originalMessage": "@body('Respond:TwoWay:_Call_Response_Handler')",
                                                                                        "suspendQueueTopicName": "@{parameters('suspendQueueTopicName')}",
                                                                                        "failedMessageRouting": "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['failedMessageRouting'], false)",
                                                                                        "scenario": "@{parameters('scenario')}"
                                                                                    },
                                                                                    "headers": {
                                                                                        "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                                                        "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                                                                    },
                                                                                    "host": {
                                                                                        "triggerName": "manual",
                                                                                        "workflow": {
                                                                                            "id": "[variables('messageSuspendProcessorLogicAppResourceId')]"
                                                                                        }
                                                                                    }
                                                                                }
                                                                            },
                                                                            "Respond:TwoWay:Success:GetBodyContent:Failure:_Send_Response": {
                                                                                "inputs": {
                                                                                    "body": "@variables('FaultMessage')",
                                                                                    "statusCode": 500,
                                                                                    "headers": {
                                                                                        "Content-Type": "application/json"
                                                                                    }
                                                                                },
                                                                                "kind": "Http",
                                                                                "runAfter": {
                                                                                    "Respond:TwoWay:Success:GetBodyContent:Failure:_Send_to_SuspendQueue": [
                                                                                        "Succeeded",
                                                                                        "Failed",
                                                                                        "TimedOut"
                                                                                    ]
                                                                                },
                                                                                "type": "Response"
                                                                            }
                                                                        }
                                                                    },
                                                                    "expression": "@variables('StatusCode')",
                                                                    "type": "Switch"
                                                                },
                                                                "Respond:TwoWay:Success:GetBodyContent:_Set_StatusCode_variable": {
                                                                    "runAfter": {
                                                                        "Respond:TwoWay:Success:_Get_Response_BodyContent": [
                                                                            "Succeeded",
                                                                            "Failed",
                                                                            "Skipped",
                                                                            "TimedOut"
                                                                        ]
                                                                    },
                                                                    "type": "SetVariable",
                                                                    "inputs": {
                                                                        "name": "StatusCode",
                                                                        "value": "@coalesce(outputs('Respond:TwoWay:Success:_Get_Response_BodyContent')['statusCode'], 500)"
                                                                    }
                                                                }
                                                            },
                                                            "else": {
                                                                "actions": {
                                                                    "Respond:TwoWay:Success:UnknownContentType:_Send_Response": {
                                                                        "inputs": {
                                                                            "body": "@if(equals(variables('TwoWayResponseMessage')?['$content-encoding'], 'Base64'), json(decodeBase64(variables('TwoWayResponseMessage')?['$content'])), variables('TwoWayResponseMessage')?['$content'])",
                                                                            "statusCode": 200,
                                                                            "headers": {
                                                                                "Content-Type": "@variables('TwoWayResponseMessage')?['$content-type']"
                                                                            }
                                                                        },
                                                                        "kind": "Http",
                                                                        "runAfter": {},
                                                                        "type": "Response"
                                                                    }
                                                                }
                                                            },
                                                            "expression": {
                                                                "or": [
                                                                    {
                                                                        "equals": [
                                                                            "@variables('TwoWayResponseMessage')?['$content-type']",
                                                                            "text/json"
                                                                        ]
                                                                    },
                                                                    {
                                                                        "equals": [
                                                                            "@variables('TwoWayResponseMessage')?['$content-type']",
                                                                            "application/json"
                                                                        ]
                                                                    }
                                                                ]
                                                            }
                                                        }
                                                    }   
                                                }
                                            },
                                            "default": {
                                                "actions": {
                                                    "Respond:TwoWay:Failure:_Create_Fault": {
                                                        "runAfter": {},
                                                        "type": "Compose",
                                                        "inputs": {
                                                            "fault": {
                                                                "faultActor": "@concat(workflow()?['name'], '.', actions('Respond:TwoWay:_Call_Response_Handler')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                "faultCategory": "Error",
                                                                "faultCode": "@{outputs('Respond:TwoWay:_Call_Response_Handler')?['statusCode']}",
                                                                "faultMessage": "An error occurred whilst trying to get the response message for a two-way scenario.",
                                                                "faultReason": "@{coalesce(body('Respond:TwoWay:_Call_Response_Handler')?['fault']?['faultMessage'], body('Respond:TwoWay:_Call_Response_Handler')?['error']?['message'])}"
                                                            }
                                                        }
                                                    },
                                                    "Respond:TwoWay:Failure:_Set_FaultMessage_variable": {
                                                        "runAfter": {
                                                            "Respond:TwoWay:Failure:_Create_Fault": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@outputs('Respond:TwoWay:Failure:_Create_Fault')"
                                                        }
                                                    },
                                                    "Respond:TwoWay:Failure:_Create_NACK_Message": {
                                                        "runAfter": {
                                                            "Respond:TwoWay:Failure:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "Compose",
                                                        "inputs": {
                                                            "body": [
                                                                {
                                                                    "$content": {
                                                                        "code": "500",
                                                                        "fault": "@variables('FaultMessage')",
                                                                        "message": "Action @{actions('Respond:TwoWay:_Call_Response_Handler')?['name']} resulted in an error response."
                                                                    },
                                                                    "$contentType": "application/json",
                                                                    "$part": 1,
                                                                    "$partType": "http://schemas.microsoft.com/aim#nack"
                                                                }
                                                            ],
                                                            "header": {
                                                                "properties": {
                                                                    "createDate": "@utcNow()",
                                                                    "envelopeType": "nack",
                                                                    "messageId": "@guid()",
                                                                    "rootPart": 1,
                                                                    "trackingId": "@body('Respond:TwoWay:_Call_Response_Handler')?['header']?['properties']?['trackingId']"
                                                                },
                                                                "routing": {
                                                                    "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                                },
                                                                "routingSlip": {},
                                                                "state": {}
                                                            }
                                                        }
                                                    },
                                                    "Respond:TwoWay:Failure:_Send_to_SuspendQueue": {
                                                        "runAfter": {
                                                            "Respond:TwoWay:Failure:_Create_NACK_Message": [
                                                                "Succeeded",
                                                                "Failed",
                                                                "TimedOut"
                                                            ]
                                                        },
                                                        "type": "Workflow",
                                                        "inputs": {
                                                            "body": {
                                                                "nackMessage": "@outputs('Respond:TwoWay:Failure:_Create_NACK_Message')",
                                                                "originalMessage": "@variables('ResponseMessage')",
                                                                "suspendQueueTopicName": "@{parameters('suspendQueueTopicName')}",
                                                                "failedMessageRouting": "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['failedMessageRouting'], false)",
                                                                "scenario": "@{parameters('scenario')}"
                                                            },
                                                            "headers": {
                                                                "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                                "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                                            },
                                                            "host": {
                                                                "triggerName": "manual",
                                                                "workflow": {
                                                                    "id": "[variables('messageSuspendProcessorLogicAppResourceId')]"
                                                                }
                                                            }
                                                        }
                                                    },
                                                    "Respond:TwoWay:Failure:_Send_Fault_Response": {
                                                        "inputs": {
                                                            "body": "@variables('FaultMessage')",
                                                            "statusCode": "@coalesce(outputs('Respond:TwoWay:_Call_Response_Handler')?['statusCode'], 500)",
                                                            "headers": {
                                                                "Content-Type": "application/json"
                                                            }
                                                        },
                                                        "kind": "Http",
                                                        "runAfter": {
                                                            "Respond:TwoWay:Failure:_Send_to_SuspendQueue": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "Response"
                                                    }
                                                }
                                            },
                                            "expression": "@variables('StatusCode')",
                                            "type": "Switch"
                                        },
                                        "Respond:TwoWay:_Set_StatusCode_variable": {
                                            "runAfter": {
                                                "Respond:TwoWay:_Call_Response_Handler": [
                                                    "Succeeded",
                                                    "Failed",
                                                    "Skipped",
                                                    "TimedOut"
                                                ]
                                            },
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "StatusCode",
                                                "value": "@coalesce(outputs('Respond:TwoWay:_Call_Response_Handler')?['statusCode'], 500)"
                                            }
                                        }
                                    },
                                    "runAfter": {},
                                    "else": {
                                        "actions": {
                                            "Respond:OneWay:_Send_Accepted_Response": {
                                                "inputs": {
                                                    "statusCode": 202,
                                                    "headers": {
                                                        "Content-Type": "application/json"
                                                    }
                                                },
                                                "kind": "Http",
                                                "runAfter": {},
                                                "type": "Response"
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "equals": [
                                                    "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['isTwoWay'], false)",
                                                    true
                                                ]
                                            }
                                        ]
                                    },
                                    "type": "if"
                                }
                            },
                            "runAfter": {
                                "Step:_Construct Message": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "else": {
                                "actions": {
                                    "Failure:_Do_we_have_a_NACK": {
                                        "actions": {},
                                        "runAfter": {},
                                        "else": {
                                            "actions": {
                                                "Failure:_Build_NACK_message": {
                                                    "runAfter": {},
                                                    "type": "Compose",
                                                    "inputs": {
                                                        "body": [
                                                            {
                                                                "$content": {
                                                                    "code": "500",
                                                                    "message": "@variables('ErrorMessage')",
                                                                    "lastCheckpoint": "@variables('Checkpoint')",
                                                                    "fault": "@variables('FaultMessage')"
                                                                },
                                                                "$contentType": "application/json",
                                                                "$part": 1,
                                                                "$partType": "http://schemas.microsoft.com/aim#nack"
                                                            }
                                                        ],
                                                        "header": {
                                                            "properties": {
                                                                "createDate": "@utcNow()",
                                                                "envelopeType": "nack",
                                                                "messageId": "@guid()",
                                                                "rootPart": 1,
                                                                "trackingId": "@triggerBody()?['header']?['properties']?['trackingId']"
                                                            },
                                                            "routing": {
                                                                "MessageType": "http://schemas.microsoft.com/aim#nack"
                                                            },
                                                            "routingSlip": {},
                                                            "state": {}
                                                        }
                                                    }
                                                },
                                                "Failure:_Set_ResponseMessage_variable": {
                                                    "runAfter": {
                                                        "Failure:_Build_NACK_message": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "ResponseMessage",
                                                        "value": "@outputs('Failure:_Build_NACK_message')"
                                                    }
                                                }
                                            }
                                        },
                                        "expression": {
                                            "and": [
                                                {
                                                    "equals": [
                                                        "@{coalesce(variables('ResponseMessage')?['header']?['properties']?['envelopeType'], '(unknown)')}",
                                                        "nack"
                                                    ]
                                                }
                                            ]
                                        },
                                        "type": "If"
                                    },
                                    "Failure:_Send_NACK_to_SuspendQueue": {
                                        "runAfter": {
                                            "Failure:_Do_we_have_a_NACK": [
                                                "Succeeded"
                                            ]
                                        },
                                        "type": "Workflow",
                                        "inputs": {
                                            "body": {
                                                "nackMessage": "@variables('ResponseMessage')",
                                                "originalMessage": "@triggerBody()",
                                                "suspendQueueTopicName": "@{parameters('suspendQueueTopicName')}",
                                                "failedMessageRouting": "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['failedMessageRouting'], false)",
                                                "scenario": "@{parameters('scenario')}"
                                            },
                                            "headers": {
                                                "Aim-Clear-Cache": "@coalesce(variables('Configuration')?['globalConfig']?['clearCache'], 'false')",
                                                "Aim-Enable-Trace": "@coalesce(variables('Configuration')?['globalConfig']?['enableTrace'], 'false')"
                                            },
                                            "host": {
                                                "triggerName": "manual",
                                                "workflow": {
                                                    "id": "[variables('messageSuspendProcessorLogicAppResourceId')]"
                                                }
                                            }
                                        }
                                    },
                                    "Failure:_Send_Fault_Response": {
                                        "inputs": {
                                            "body": {
                                                "fault": {
                                                    "faultActor": "@{workflow()['name']} (@{workflow()?['run']?['name']})",
                                                    "faultCategory": "Error",
                                                    "faultCode": "500",
                                                    "faultMessage": "@variables('ErrorMessage')",
                                                    "faultReason": ""
                                                }
                                            },
                                            "headers": {
                                                "Content-Type": "application/json"
                                            },
                                            "statusCode": 500
                                        },
                                        "kind": "Http",
                                        "runAfter": {
                                            "Failure:_Send_NACK_to_SuspendQueue": [
                                                "Succeeded",
                                                "Failed",
                                                "Skipped",
                                                "TimedOut"
                                            ]
                                        },
                                        "type": "Response"
                                    }
                                }
                            },
                            "expression": {
                                "or": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "IgnoreFile"
                                        ]
                                    },
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            "ConstructMessageACK"
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Get_Configuration": {
                            "actions": {
                                "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": {
                                    "runAfter": {},
                                    "type": "ApiManagement",
                                    "inputs": {
                                        "api": {
                                            "id": "[variables('configurationManagerApiResourceId')]"
                                        },
                                        "method": "get",
                                        "pathTemplate": {
                                            "parameters": {
                                                "scenario": "@{encodeURIComponent(parameters('scenario'))}",
                                                "step": "@{encodeURIComponent(parameters('scenarioStep'))}"
                                            },
                                            "template": "/aimconfigurationmanager/configuration/{scenario}/{step}"
                                        },
                                        "queries": {
                                            "clearCache": "@parameters('clearCache')"
                                        },
                                        "retryPolicy": "[parameters('apimRetryPolicy')]",
                                        "subscriptionKey": "@{parameters('apimSubscriptionKey')}"
                                    }
                                },
                                "GetConfiguration:_Check_Status_Code": {
                                    "runAfter": {
                                        "GetConfiguration:_Set_StatusCode_variable": [
                                            "Succeeded"
                                        ]
                                    },
                                    "cases": {
                                        "Success": {
                                            "case": 200,
                                            "actions": {
                                                "GetConfiguration:Success:_Set_Checkpoint_variable": {
                                                    "runAfter": {
                                                        "GetConfiguration:Success:_Set_Configuration_variable": [
                                                            "Succeeded"
                                                        ]
                                                    },
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Checkpoint",
                                                        "value": "GetConfiguration"
                                                    }
                                                },
                                                "GetConfiguration:Success:_Set_Configuration_variable": {
                                                    "runAfter": {},
                                                    "type": "SetVariable",
                                                    "inputs": {
                                                        "name": "Configuration",
                                                        "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                    }
                                                }
                                            }
                                        }
                                    },
                                    "default": {
                                        "actions": {
                                            "GetConfiguration:Failure:_Do_we_have_a_Fault_Message": {
                                                "actions": {
                                                    "GetConfiguration:Fault:_Set_ErrorMessage_variable": {
                                                        "runAfter": {
                                                            "GetConfiguration:Fault:_Set_FaultMessage_variable": [
                                                                "Succeeded"
                                                            ]
                                                        },
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "ErrorMessage",
                                                            "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                        }
                                                    },
                                                    "GetConfiguration:Fault:_Set_FaultMessage_variable": {
                                                        "runAfter": {},
                                                        "type": "SetVariable",
                                                        "inputs": {
                                                            "name": "FaultMessage",
                                                            "value": "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')"
                                                        }
                                                    }
                                                },
                                                "runAfter": {},
                                                "else": {
                                                    "actions": {
                                                        "GetConfiguration:NoFault:_Create_Fault_Message": {
                                                            "runAfter": {},
                                                            "type": "Compose",
                                                            "inputs": {
                                                                "fault": {
                                                                    "faultActor": "@concat(workflow()?['name'], '.', actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['name'], ' (', workflow()?['run']?['name'], ')')",
                                                                    "faultCategory": "Error",
                                                                    "faultCode": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['statusCode'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['code'])}",
                                                                    "faultMessage": "@{coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'], outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['body']?['message'], actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['error']?['message'])}",
                                                                    "faultReason": "@{actions('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['status']}"
                                                                }
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_ErrorMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Set_FaultMessage_variable": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "ErrorMessage",
                                                                "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}) trying to call the ConfigurationManager GetConfigurationForStep operation"
                                                            }
                                                        },
                                                        "GetConfiguration:NoFault:_Set_FaultMessage_variable": {
                                                            "runAfter": {
                                                                "GetConfiguration:NoFault:_Create_Fault_Message": [
                                                                    "Succeeded"
                                                                ]
                                                            },
                                                            "type": "SetVariable",
                                                            "inputs": {
                                                                "name": "FaultMessage",
                                                                "value": "@outputs('GetConfiguration:NoFault:_Create_Fault_Message')"
                                                            }
                                                        }
                                                    }
                                                },
                                                "expression": {
                                                    "and": [
                                                        {
                                                            "not": {
                                                                "equals": [
                                                                    "@body('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['fault']",
                                                                    null
                                                                ]
                                                            }
                                                        }
                                                    ]
                                                },
                                                "type": "If"
                                            }
                                        }
                                    },
                                    "expression": "@variables('StatusCode')",
                                    "type": "Switch"
                                },
                                "GetConfiguration:_Set_StatusCode_variable": {
                                    "runAfter": {
                                        "GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep": [
                                            "Succeeded",
                                            "Failed",
                                            "Skipped",
                                            "TimedOut"
                                        ]
                                    },
                                    "type": "SetVariable",
                                    "inputs": {
                                        "name": "StatusCode",
                                        "value": "@coalesce(outputs('GetConfiguration:_Call_APIM_ConfigurationManager.GetConfigurationForStep')?['statusCode'], 500)"
                                    }
                                }
                            },
                            "runAfter": {
                                "Initialize_TwoWayResponseContent_variable": [
                                    "Succeeded",
                                    "Failed",
                                    "Skipped",
                                    "TimedOut"
                                ]
                            },
                            "expression": {
                                "and": [
                                    {
                                        "equals": [
                                            "@variables('Checkpoint')",
                                            ""
                                        ]
                                    }
                                ]
                            },
                            "type": "If"
                        },
                        "Step:_Validate_Configuration": {
                            "actions": {
                                "ValidateConfiguration:_Have_Valid_Properties": {
                                    "actions": {
                                        "ValidateConfiguration:Success:_Set_Checkpoint_variable": {
                                            "runAfter": {},
                                            "type": "SetVariable",
                                            "inputs": {
                                                "name": "Checkpoint",
                                                "value": "ValidateConfiguration"
                                            }
                                        }
                                    },
                                    "runAfter": {},
                                    "else": {
                                        "actions": {
                                            "ValidateConfiguration:Failure:_Set_Checkpoint_variable": {
                                                "runAfter": {},
                                                "type": "SetVariable",
                                                "inputs": {
                                                    "name": "ErrorMessage",
                                                    "value": "An error occurred in @{workflow()?['name']} (@{workflow()?['run']?['name']}): property btsReceivePortName is not set in configuration"
                                                }
                                            }
                                        }
                                    },
                                    "expression": {
                                        "and": [
                                            {
                                                "not": {
                                                    "equals": [
                                                        "@coalesce(variables('Configuration')?[parameters('scenarioStep')]?['btsReceivePortName'], '')",
                                                        ""
                                                    ]