Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions cli/azd/internal/cmd/add/add_configure.go
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,13 @@ func Configure(
project.ResourceTypeDbMySql,
project.ResourceTypeDbMongo:
return fillDatabaseName(ctx, r, console, p)
case project.ResourceTypeDbCosmos:
r, err := fillDatabaseName(ctx, r, console, p)
if err != nil {
return nil, err
}
r.Props = project.CosmosDBProps{}
return r, nil
case project.ResourceTypeMessagingEventHubs:
return fillEventHubs(ctx, r, console, p)
case project.ResourceTypeMessagingServiceBus:
Expand Down
5 changes: 5 additions & 0 deletions cli/azd/internal/cmd/add/add_preview.go
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,11 @@ func Metadata(r *project.ResourceConfig) resourceMeta {
res.UseEnvVars = []string{
"AZURE_OPENAI_ENDPOINT",
}
case project.ResourceTypeDbCosmos:
res.AzureResourceType = "Microsoft.DocumentDB/databaseAccounts"
res.UseEnvVars = []string{
"AZURE_COSMOS_ENDPOINT",
}
case project.ResourceTypeMessagingEventHubs:
res.AzureResourceType = "Microsoft.EventHub/namespaces"
res.UseEnvVars = []string{
Expand Down
21 changes: 21 additions & 0 deletions cli/azd/internal/scaffold/scaffold_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,9 @@ func TestExecInfra(t *testing.T) {
DbCosmosMongo: &DatabaseCosmosMongo{
DatabaseName: "appdb",
},
DbCosmos: &DatabaseCosmos{
DatabaseName: "cosmos",
},
DbRedis: &DatabaseRedis{},
ServiceBus: &ServiceBus{},
EventHubs: &EventHubs{},
Expand All @@ -134,6 +137,9 @@ func TestExecInfra(t *testing.T) {
DbPostgres: &DatabaseReference{
DatabaseName: "appdb",
},
DbCosmos: &DatabaseReference{
DatabaseName: "cosmos",
},
DbMySql: &DatabaseReference{
DatabaseName: "mysqldb",
},
Expand Down Expand Up @@ -222,6 +228,21 @@ func TestExecInfra(t *testing.T) {
},
},
},
{
"API with Cosmos",
InfraSpec{
DbCosmos: &DatabaseCosmos{},
Services: []ServiceSpec{
{
Name: "api",
Port: 3100,
DbCosmos: &DatabaseReference{
DatabaseName: "cosmos",
},
},
},
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
Expand Down
12 changes: 12 additions & 0 deletions cli/azd/internal/scaffold/spec.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ type InfraSpec struct {
DbPostgres *DatabasePostgres
DbMySql *DatabaseMysql
DbCosmosMongo *DatabaseCosmosMongo
DbCosmos *DatabaseCosmos
DbRedis *DatabaseRedis

// Key vault
Expand Down Expand Up @@ -54,6 +55,16 @@ type DatabaseCosmosMongo struct {
DatabaseName string
}

type DatabaseCosmos struct {
DatabaseName string
Containers []CosmosSqlDatabaseContainer
}

type CosmosSqlDatabaseContainer struct {
ContainerName string
PartitionKeyPaths []string
}

type DatabaseRedis struct {
}

Expand Down Expand Up @@ -124,6 +135,7 @@ type ServiceSpec struct {
DbPostgres *DatabaseReference
DbMySql *DatabaseReference
DbCosmosMongo *DatabaseReference
DbCosmos *DatabaseReference
DbRedis *DatabaseReference

StorageAccount *StorageReference
Expand Down
21 changes: 21 additions & 0 deletions cli/azd/pkg/project/resources.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ func AllResourceTypes() []ResourceType {
ResourceTypeDbPostgres,
ResourceTypeDbMySql,
ResourceTypeDbMongo,
ResourceTypeDbCosmos,
ResourceTypeHostContainerApp,
ResourceTypeOpenAiModel,
ResourceTypeMessagingEventHubs,
Expand All @@ -31,6 +32,7 @@ const (
ResourceTypeDbPostgres ResourceType = "db.postgres"
ResourceTypeDbMySql ResourceType = "db.mysql"
ResourceTypeDbMongo ResourceType = "db.mongo"
ResourceTypeDbCosmos ResourceType = "db.cosmos"
ResourceTypeHostContainerApp ResourceType = "host.containerapp"
ResourceTypeOpenAiModel ResourceType = "ai.openai.model"
ResourceTypeMessagingEventHubs ResourceType = "messaging.eventhubs"
Expand All @@ -50,6 +52,8 @@ func (r ResourceType) String() string {
return "MySQL"
case ResourceTypeDbMongo:
return "MongoDB"
case ResourceTypeDbCosmos:
return "CosmosDB"
case ResourceTypeHostContainerApp:
return "Container App"
case ResourceTypeOpenAiModel:
Expand Down Expand Up @@ -107,6 +111,8 @@ func (r *ResourceConfig) MarshalYAML() (interface{}, error) {
errMarshal = marshalRawProps(raw.Props.(AIModelProps))
case ResourceTypeHostContainerApp:
errMarshal = marshalRawProps(raw.Props.(ContainerAppProps))
case ResourceTypeDbCosmos:
errMarshal = marshalRawProps(raw.Props.(CosmosDBProps))
case ResourceTypeMessagingEventHubs:
errMarshal = marshalRawProps(raw.Props.(EventHubsProps))
case ResourceTypeMessagingServiceBus:
Expand Down Expand Up @@ -158,6 +164,12 @@ func (r *ResourceConfig) UnmarshalYAML(value *yaml.Node) error {
return err
}
raw.Props = cap
case ResourceTypeDbCosmos:
cdp := CosmosDBProps{}
if err := unmarshalProps(&cdp); err != nil {
return err
}
raw.Props = cdp
case ResourceTypeMessagingEventHubs:
ehp := EventHubsProps{}
if err := unmarshalProps(&ehp); err != nil {
Expand Down Expand Up @@ -210,6 +222,15 @@ type AIModelPropsModel struct {
Version string `yaml:"version,omitempty"`
}

type CosmosDBProps struct {
Containers []CosmosDBContainerProps `yaml:"containers,omitempty"`
}

type CosmosDBContainerProps struct {
Name string `yaml:"name,omitempty"`
PartitionKeys []string `yaml:"partitionKeys,omitempty"`
}

type ServiceBusProps struct {
Queues []string `yaml:"queues,omitempty"`
Topics []string `yaml:"topics,omitempty"`
Expand Down
15 changes: 15 additions & 0 deletions cli/azd/pkg/project/scaffold_gen.go
Original file line number Diff line number Diff line change
Expand Up @@ -157,6 +157,19 @@ func infraSpec(projectConfig *ProjectConfig) (*scaffold.InfraSpec, error) {
infraSpec.DbCosmosMongo = &scaffold.DatabaseCosmosMongo{
DatabaseName: res.Name,
}
case ResourceTypeDbCosmos:
props := res.Props.(CosmosDBProps)
containers := make([]scaffold.CosmosSqlDatabaseContainer, 0)
for _, c := range props.Containers {
containers = append(containers, scaffold.CosmosSqlDatabaseContainer{
ContainerName: c.Name,
PartitionKeyPaths: c.PartitionKeys,
})
}
infraSpec.DbCosmos = &scaffold.DatabaseCosmos{
DatabaseName: res.Name,
Containers: containers,
}
case ResourceTypeDbPostgres:
infraSpec.DbPostgres = &scaffold.DatabasePostgres{
DatabaseName: res.Name,
Expand Down Expand Up @@ -329,6 +342,8 @@ func mapHostUses(
switch useRes.Type {
case ResourceTypeDbMongo:
svcSpec.DbCosmosMongo = &scaffold.DatabaseReference{DatabaseName: useRes.Name}
case ResourceTypeDbCosmos:
svcSpec.DbCosmos = &scaffold.DatabaseReference{DatabaseName: useRes.Name}
case ResourceTypeDbPostgres:
svcSpec.DbPostgres = &scaffold.DatabaseReference{DatabaseName: useRes.Name}
case ResourceTypeDbMySql:
Expand Down
1 change: 1 addition & 0 deletions cli/azd/resources/scaffold/base/abbreviations.json
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
"devicesProvisioningServices": "provs-",
"devicesProvisioningServicesCertificates": "pcert-",
"documentDBDatabaseAccounts": "cosmos-",
"documentDBMongoDatabaseAccounts": "cosmon-",
"eventGridDomains": "evgd-",
"eventGridDomainsTopics": "evgt-",
"eventGridEventSubscriptions": "evgs-",
Expand Down
3 changes: 3 additions & 0 deletions cli/azd/resources/scaffold/templates/main.bicept
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,9 @@ output AZURE_RESOURCE_REDIS_ID string = resources.outputs.AZURE_RESOURCE_REDIS_I
{{- if .DbPostgres}}
output AZURE_RESOURCE_{{alphaSnakeUpper .DbPostgres.DatabaseName}}_ID string = resources.outputs.AZURE_RESOURCE_{{alphaSnakeUpper .DbPostgres.DatabaseName}}_ID
{{- end}}
{{- if .DbCosmos }}
output AZURE_RESOURCE_{{alphaSnakeUpper .DbCosmos.DatabaseName}}_ID string = resources.outputs.AZURE_RESOURCE_{{alphaSnakeUpper .DbCosmos.DatabaseName}}_ID
{{- end}}
{{- if .DbMySql}}
output AZURE_RESOURCE_{{alphaSnakeUpper .DbMySql.DatabaseName}}_ID string = resources.outputs.AZURE_RESOURCE_{{alphaSnakeUpper .DbMySql.DatabaseName}}_ID
{{- end}}
Expand Down
69 changes: 65 additions & 4 deletions cli/azd/resources/scaffold/templates/resources.bicept
Original file line number Diff line number Diff line change
Expand Up @@ -69,10 +69,10 @@ module containerAppsEnvironment 'br/public:avm/res/app/managed-environment:0.4.5
{{- end}}

{{- if .DbCosmosMongo}}
module cosmos 'br/public:avm/res/document-db/database-account:0.8.1' = {
name: 'cosmos'
module cosmosMongo 'br/public:avm/res/document-db/database-account:0.8.1' = {
name: 'cosmosMongo'
params: {
name: '${abbrs.documentDBDatabaseAccounts}${resourceToken}'
name: '${abbrs.documentDBMongoDatabaseAccounts}${resourceToken}'
location: location
tags: tags
locations: [
Expand Down Expand Up @@ -103,6 +103,58 @@ module cosmos 'br/public:avm/res/document-db/database-account:0.8.1' = {
}
{{- end}}

{{- if .DbCosmos }}
module cosmos 'br/public:avm/res/document-db/database-account:0.8.1' = {
name: 'cosmos'
params: {
name: '${abbrs.documentDBDatabaseAccounts}${resourceToken}'
Comment thread
weikanglim marked this conversation as resolved.
tags: tags
location: location
locations: [
{
failoverPriority: 0
isZoneRedundant: false
locationName: location
}
]
networkRestrictions: {
ipRules: []
virtualNetworkRules: []
publicNetworkAccess: 'Enabled'
}
sqlDatabases: [
{
name: '{{ .DbCosmos.DatabaseName }}'
containers: [
{{- range .DbCosmos.Containers}}
{
name: '{{ .ContainerName }}'
paths: [
{{- range $path := .PartitionKeyPaths}}
'{{ $path }}'
{{- end}}
]
}
{{- end}}
]
Comment thread
weikanglim marked this conversation as resolved.
}
]
sqlRoleAssignmentsPrincipalIds: [
Comment thread
weikanglim marked this conversation as resolved.
{{- range .Services}}
{{bicepName .Name}}Identity.outputs.principalId
{{- end}}
Comment thread
weikanglim marked this conversation as resolved.
principalId
]
sqlRoleDefinitions: [
{
name: 'service-access-cosmos-sql-role'
}
]
capabilitiesToAdd: [ 'EnableServerless' ]
}
}
{{- end}}

{{- if .DbPostgres}}
var postgresDatabaseName = '{{ .DbPostgres.DatabaseName }}'
var postgresDatabaseUser = 'psqladmin'
Expand Down Expand Up @@ -385,7 +437,7 @@ module {{bicepName .Name}} 'br/public:avm/res/app/container-app:0.8.0' = {
{
name: 'mongodb-url'
identity:{{bicepName .Name}}Identity.outputs.resourceId
keyVaultUrl: cosmos.outputs.exportedSecrets['mongodb-url'].secretUri
keyVaultUrl: cosmosMongo.outputs.exportedSecrets['mongodb-url'].secretUri
}
{{- end}}
{{- if .DbPostgres}}
Expand Down Expand Up @@ -449,6 +501,12 @@ module {{bicepName .Name}} 'br/public:avm/res/app/container-app:0.8.0' = {
secretRef: 'mongodb-url'
}
{{- end}}
{{- if .DbCosmos}}
{
name: 'AZURE_COSMOS_ENDPOINT'
value: cosmos.outputs.endpoint
}
{{- end}}
{{- if .DbPostgres}}
{
name: 'POSTGRES_HOST'
Expand Down Expand Up @@ -718,6 +776,9 @@ output AZURE_RESOURCE_{{alphaSnakeUpper .DbPostgres.DatabaseName}}_ID string = '
{{- if .DbMySql}}
output AZURE_RESOURCE_{{alphaSnakeUpper .DbMySql.DatabaseName}}_ID string = '${mysqlServer.outputs.resourceId}/databases/{{.DbMySql.DatabaseName}}'
{{- end}}
{{- if .DbCosmos }}
output AZURE_RESOURCE_{{alphaSnakeUpper .DbCosmos.DatabaseName}}_ID string = '${cosmos.outputs.resourceId}/sqlDatabases/{{.DbCosmos.DatabaseName}}'
{{- end}}
{{- if .StorageAccount }}
output AZURE_RESOURCE_STORAGE_ID string = storageAccount.outputs.resourceId
{{- end}}
Expand Down
38 changes: 38 additions & 0 deletions schemas/alpha/azure.yaml.json
Original file line number Diff line number Diff line change
Expand Up @@ -370,6 +370,7 @@
"db.mysql",
"db.redis",
"db.mongo",
"db.cosmos",
"ai.openai.model",
"host.containerapp",
"messaging.eventhubs",
Expand All @@ -394,6 +395,7 @@
{ "if": { "properties": { "type": { "const": "db.mysql" }}}, "then": { "$ref": "#/definitions/resource"} },
{ "if": { "properties": { "type": { "const": "db.redis" }}}, "then": { "$ref": "#/definitions/resource"} },
{ "if": { "properties": { "type": { "const": "db.mongo" }}}, "then": { "$ref": "#/definitions/resource"} },
{ "if": { "properties": { "type": { "const": "db.cosmos" }}}, "then": { "$ref": "#/definitions/cosmosDbResource"} },
{ "if": { "properties": { "type": { "const": "messaging.eventhubs" }}}, "then": { "$ref": "#/definitions/eventHubsResource" } },
{ "if": { "properties": { "type": { "const": "messaging.servicebus" }}}, "then": { "$ref": "#/definitions/serviceBusResource" } },
{ "if": { "properties": { "type": { "const": "storage" }}}, "then": { "$ref": "#/definitions/storageAccountResource"} },
Expand Down Expand Up @@ -1238,6 +1240,7 @@
"db.redis",
"db.mysql",
"db.mongo",
"db.cosmos",
"host.containerapp",
"ai.openai.model",
"keyvault"
Expand Down Expand Up @@ -1328,6 +1331,41 @@
}
}
},
"cosmosDbResource": {
"type": "object",
"description": "A deployed, ready-to-use Azure Cosmos DB for NoSQL database.",
"additionalProperties": false,
"properties": {
"type": true,
"uses": true,
"containers": {
"type": "array",
"title": "Containers",
"description": "Containers to be created to store data. Each container stores a collection of items.",
"items": {
"type": "object",
"additionalProperties": false,
"properties": {
"name": {
"type": "string",
"title": "Container name.",
"description": "Required. The name of the container."
},
"partitionKeys": {
"type": "array",
"title": "Partition keys.",
"description": "Required. The partition key(s) used to distribute data across partitions. The ordering of keys matters. By default, a single partition key '/id' is naturally a great choice for most applications.",
"minLength": 1,
"maxLength": 3,
"items": {
"type": "string"
}
}
}
}
}
}
},
"eventHubsResource": {
"type": "object",
"description": "An Azure Event Hubs namespace.",
Expand Down