'How do I create multiple topics/queues in multiple servicebuses with bicep?
I don't quite understand the relationship between parent and child components when working with bicep and more specifically arrays. The error I get is this: Deployment template validation failed: 'The resource 'Microsoft.Resources/deployments/p6vklkczz4qlm' at line '54' and column '9' is defined multiple times in a template.
The error is quite clear I just don't understand the solution I guess.
main.bicep
param servicebuses array = [
'servicebus_dev'
'servicebus_acc'
'servicebus_prod'
]
resource servicebusNamespace 'Microsoft.ServiceBus/namespaces@2021-11-01' = [for servicebus in servicebuses: {
location: location
name: servicebus
sku:{
name: 'Standard'
}
}]
module topicModule 'topicsModule.bicep' = [for servicebus in servicebuses:{
name: uniqueString('topic')
params:{
parentResource: servicebus
}
}]
topicsModule.bicep
param topics array = [
'topic1'
'topic2'
'topic3'
]
param parentResource string
resource topicResource 'Microsoft.ServiceBus/namespaces/topics@2021-11-01' = [for topic in topics : {
name: topic
}]
Solution 1:[1]
Creating the topics in a module makes it a bit cumbersome. You have to fetch the namespace using the existing keyword and then you can add a parent relationship to your topic to create it within the given namespace.
resource servicebusNamespace 'Microsoft.ServiceBus/namespaces@2021-11-01' existing = {
name: parentResource
}
resource topicResource 'Microsoft.ServiceBus/namespaces/topics@2021-11-01' = [for topic in topics : {
parent: servicebusNamespace
name: topic
}]
Then you have to make your topicModules name dependent on the selected servicebus and also add a dependsOn for the servicebus namespace so that bicep will know to deploy the namespace first.
module topicModule 'topicsModule.bicep' = [for servicebus in servicebuses:{
name: uniqueString(servicebus)
dependsOn:[
servicebusNamespace
]
params:{
parentResource: servicebus
}
}]
I guess you replaced your real service bus namespace names with dummy values but just in case, make sure to use a name thats more likely to be globally unique and don't use the _ character, it is not allowed in the name of a service bus namespace.
Solution 2:[2]
Additionally to the accepted answer.
A topic is a sub resource of service namespace so the resource name looks like that:servicebus-namespace-name/topic-name
topicsModule.bicep file:
param servicebusName string
param topics array = [
'topic1'
'topic2'
'topic3'
]
resource topicResource 'Microsoft.ServiceBus/namespaces/topics@2021-11-01' = [for topic in topics: {
name: '${servicebusName}/${topic}'
}]
In the main file, you can just invoke the module like that:
module topicModule 'topicsModule.bicep' = [for (servicebus, i) in servicebuses: {
name: uniqueString(servicebus)
params: {
servicebusName: servicebusNamespace[i].name
}
}]
Here you don't need to specify the dependsOn
as it is automatically generated by bicep at compile time.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | JustAGuy |
Solution 2 | Thomas |