From 94c1f72ffb12081899d5c03cff3f9eca31a8dc38 Mon Sep 17 00:00:00 2001 From: jiawei Date: Thu, 28 Sep 2023 02:55:15 +0000 Subject: [PATCH 01/10] temp env apex --- .../container_app_environment_resource.go | 25 +++--- ...container_app_environment_resource_test.go | 66 ++++++++++++++++ .../containerapps/helpers/container_apps.go | 79 +++++++++++++++++++ 3 files changed, 161 insertions(+), 9 deletions(-) diff --git a/internal/services/containerapps/container_app_environment_resource.go b/internal/services/containerapps/container_app_environment_resource.go index d5c10f926977..a3456f16d6a6 100644 --- a/internal/services/containerapps/container_app_environment_resource.go +++ b/internal/services/containerapps/container_app_environment_resource.go @@ -6,6 +6,7 @@ package containerapps import ( "context" "fmt" + "github.com/hashicorp/terraform-provider-azurerm/internal/services/containerapps/helpers" "time" "github.com/hashicorp/go-azure-helpers/lang/pointer" @@ -25,15 +26,16 @@ import ( type ContainerAppEnvironmentResource struct{} type ContainerAppEnvironmentModel struct { - Name string `tfschema:"name"` - ResourceGroup string `tfschema:"resource_group_name"` - Location string `tfschema:"location"` - DaprApplicationInsightsConnectionString string `tfschema:"dapr_application_insights_connection_string"` - LogAnalyticsWorkspaceId string `tfschema:"log_analytics_workspace_id"` - InfrastructureSubnetId string `tfschema:"infrastructure_subnet_id"` - InternalLoadBalancerEnabled bool `tfschema:"internal_load_balancer_enabled"` - ZoneRedundant bool `tfschema:"zone_redundancy_enabled"` - Tags map[string]interface{} `tfschema:"tags"` + Name string `tfschema:"name"` + ResourceGroup string `tfschema:"resource_group_name"` + Location string `tfschema:"location"` + DaprApplicationInsightsConnectionString string `tfschema:"dapr_application_insights_connection_string"` + LogAnalyticsWorkspaceId string `tfschema:"log_analytics_workspace_id"` + InfrastructureSubnetId string `tfschema:"infrastructure_subnet_id"` + InternalLoadBalancerEnabled bool `tfschema:"internal_load_balancer_enabled"` + ZoneRedundant bool `tfschema:"zone_redundancy_enabled"` + Tags map[string]interface{} `tfschema:"tags"` + WorkloadProfiles []helpers.WorkloadProfileModel `tfschema:"workload_profile"` DefaultDomain string `tfschema:"default_domain"` DockerBridgeCidr string `tfschema:"docker_bridge_cidr"` @@ -104,6 +106,8 @@ func (r ContainerAppEnvironmentResource) Arguments() map[string]*pluginsdk.Schem Description: "Should the Container Environment operate in Internal Load Balancing Mode? Defaults to `false`. **Note:** can only be set to `true` if `infrastructure_subnet_id` is specified.", }, + "workload_profile": helpers.WorkloadProfileSchema(), + "zone_redundancy_enabled": { Type: pluginsdk.TypeBool, Optional: true, @@ -231,6 +235,8 @@ func (r ContainerAppEnvironmentResource) Create() sdk.ResourceFunc { managedEnvironment.Properties.VnetConfiguration.Internal = pointer.To(containerAppEnvironment.InternalLoadBalancerEnabled) } + managedEnvironment.Properties.WorkloadProfiles = helpers.ExpandWorkloadProfiles(containerAppEnvironment.WorkloadProfiles) + if err := client.CreateOrUpdateThenPoll(ctx, id, managedEnvironment); err != nil { return fmt.Errorf("creating %s: %+v", id, err) } @@ -279,6 +285,7 @@ func (r ContainerAppEnvironmentResource) Read() sdk.ResourceFunc { state.ZoneRedundant = pointer.From(props.ZoneRedundant) state.StaticIP = pointer.From(props.StaticIP) state.DefaultDomain = pointer.From(props.DefaultDomain) + state.WorkloadProfiles = helpers.FlattenWorkloadProfiles(props.WorkloadProfiles) } } diff --git a/internal/services/containerapps/container_app_environment_resource_test.go b/internal/services/containerapps/container_app_environment_resource_test.go index ecc8b8917fc0..5c593aaa3eb7 100644 --- a/internal/services/containerapps/container_app_environment_resource_test.go +++ b/internal/services/containerapps/container_app_environment_resource_test.go @@ -64,6 +64,21 @@ func TestAccContainerAppEnvironment_complete(t *testing.T) { }) } +func TestAccContainerAppEnvironment_withWorkloadProfile(t *testing.T) { + data := acceptance.BuildTestData(t, "azurerm_container_app_environment", "test") + r := ContainerAppEnvironmentResource{} + + data.ResourceTest(t, r, []acceptance.TestStep{ + { + Config: r.completeWithWorkloadProfile(data), + Check: acceptance.ComposeTestCheckFunc( + check.That(data.ResourceName).ExistsInAzure(r), + ), + }, + data.ImportStep("log_analytics_workspace_id"), + }) +} + func TestAccContainerAppEnvironment_completeUpdate(t *testing.T) { data := acceptance.BuildTestData(t, "azurerm_container_app_environment", "test") r := ContainerAppEnvironmentResource{} @@ -189,6 +204,57 @@ resource "azurerm_container_app_environment" "test" { `, r.templateVNet(data), data.RandomInteger) } +func (r ContainerAppEnvironmentResource) completeWithWorkloadProfile(data acceptance.TestData) string { + return fmt.Sprintf(` +%[1]s + +resource "azurerm_virtual_network" "test" { + name = "acctestvirtnet%[2]d" + address_space = ["10.0.0.0/16"] + location = azurerm_resource_group.test.location + resource_group_name = azurerm_resource_group.test.name +} + +resource "azurerm_subnet" "control" { + name = "control-plane" + resource_group_name = azurerm_resource_group.test.name + virtual_network_name = azurerm_virtual_network.test.name + address_prefixes = ["10.0.0.0/23"] + delegation { + name = "acctestdelegation%[2]d" + service_delegation { + actions = ["Microsoft.Network/virtualNetworks/subnets/join/action"] + name = "Microsoft.App/environments" + } + } +} + +resource "azurerm_container_app_environment" "test" { + name = "acctest-CAEnv%[2]d" + resource_group_name = azurerm_resource_group.test.name + location = azurerm_resource_group.test.location + log_analytics_workspace_id = azurerm_log_analytics_workspace.test.id + + infrastructure_subnet_id = azurerm_subnet.control.id + + internal_load_balancer_enabled = true + + workload_profile { + maximum_count = 2 + minimum_count = 0 + name = "My-GP--01" + workload_profile_type = "D4" + } + + tags = { + Foo = "Bar" + secret = "sauce" + } +} +`, r.template(data), data.RandomInteger) + +} + func (r ContainerAppEnvironmentResource) completeUpdate(data acceptance.TestData) string { return fmt.Sprintf(` provider "azurerm" { diff --git a/internal/services/containerapps/helpers/container_apps.go b/internal/services/containerapps/helpers/container_apps.go index 61ee769355a1..3f5a94d5b9ba 100644 --- a/internal/services/containerapps/helpers/container_apps.go +++ b/internal/services/containerapps/helpers/container_apps.go @@ -3014,3 +3014,82 @@ func (c *ContainerTemplate) flattenContainerAppScaleRules(input *[]containerapps c.TCPScaleRules = tcpScaleRules } } + +type WorkloadProfileModel struct { + MaximumCount int `tfschema:"maximum_count"` + MinimumCount int `tfschema:"minimum_count"` + Name string `tfschema:"name"` + WorkloadProfileType string `tfschema:"workload_profile_type"` +} + +func WorkloadProfileSchema() *pluginsdk.Schema { + return &pluginsdk.Schema{ + Type: pluginsdk.TypeList, + Optional: true, + Elem: &pluginsdk.Resource{ + Schema: map[string]*pluginsdk.Schema{ + "maximum_count": { + Type: pluginsdk.TypeInt, + Required: true, + ValidateFunc: validation.IntAtLeast(1), + }, + + "minimum_count": { + Type: pluginsdk.TypeInt, + Required: true, + ValidateFunc: validation.IntAtLeast(0), + }, + + "name": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringIsNotEmpty, + }, + + "workload_profile_type": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringIsNotEmpty, + }, + }, + }, + } +} + +func ExpandWorkloadProfiles(input []WorkloadProfileModel) *[]managedenvironments.WorkloadProfile { + if len(input) == 0 { + return nil + } + + result := make([]managedenvironments.WorkloadProfile, 0) + + for _, v := range input { + result = append(result, managedenvironments.WorkloadProfile{ + Name: v.Name, + MaximumCount: pointer.To(int64(v.MaximumCount)), + MinimumCount: pointer.To(int64(v.MinimumCount)), + WorkloadProfileType: v.WorkloadProfileType, + }) + } + + return &result +} + +func FlattenWorkloadProfiles(input *[]managedenvironments.WorkloadProfile) []WorkloadProfileModel { + if input == nil || len(*input) == 0 { + return []WorkloadProfileModel{} + } + + result := make([]WorkloadProfileModel, 0) + + for _, v := range *input { + result = append(result, WorkloadProfileModel{ + Name: v.Name, + MaximumCount: int(pointer.From(v.MaximumCount)), + MinimumCount: int(pointer.From(v.MinimumCount)), + WorkloadProfileType: v.WorkloadProfileType, + }) + } + + return result +} From 1d852b18555831b144b686919453afa0b2a7d770 Mon Sep 17 00:00:00 2001 From: Jiawei Tao Date: Sun, 8 Oct 2023 15:05:39 +0800 Subject: [PATCH 02/10] containerapps: Add support for workload_profile --- ...container_app_environment_resource_test.go | 25 +++++++--- .../containerapps/helpers/container_apps.go | 48 ++++++++++--------- 2 files changed, 44 insertions(+), 29 deletions(-) diff --git a/internal/services/containerapps/container_app_environment_resource_test.go b/internal/services/containerapps/container_app_environment_resource_test.go index 5c593aaa3eb7..2c8e2e0fb19a 100644 --- a/internal/services/containerapps/container_app_environment_resource_test.go +++ b/internal/services/containerapps/container_app_environment_resource_test.go @@ -206,6 +206,14 @@ resource "azurerm_container_app_environment" "test" { func (r ContainerAppEnvironmentResource) completeWithWorkloadProfile(data acceptance.TestData) string { return fmt.Sprintf(` +provider "azurerm" { + features { + resource_group { + prevent_deletion_if_contains_resources = false + } + } +} + %[1]s resource "azurerm_virtual_network" "test" { @@ -233,19 +241,22 @@ resource "azurerm_container_app_environment" "test" { name = "acctest-CAEnv%[2]d" resource_group_name = azurerm_resource_group.test.name location = azurerm_resource_group.test.location - log_analytics_workspace_id = azurerm_log_analytics_workspace.test.id - infrastructure_subnet_id = azurerm_subnet.control.id - internal_load_balancer_enabled = true + workload_profile { + maximum_count = 2 + minimum_count = 0 + name = "My-GP-01" + workload_profile_type = "D4" + } workload_profile { - maximum_count = 2 - minimum_count = 0 - name = "My-GP--01" - workload_profile_type = "D4" + name = "Consumption" + workload_profile_type = "Consumption" } + zone_redundancy_enabled = true + tags = { Foo = "Bar" secret = "sauce" diff --git a/internal/services/containerapps/helpers/container_apps.go b/internal/services/containerapps/helpers/container_apps.go index 3f5a94d5b9ba..072cd7b27675 100644 --- a/internal/services/containerapps/helpers/container_apps.go +++ b/internal/services/containerapps/helpers/container_apps.go @@ -17,6 +17,8 @@ import ( "github.com/hashicorp/terraform-provider-azurerm/internal/tf/validation" ) +const consumption = "Consumption" + type Registry struct { PasswordSecretRef string `tfschema:"password_secret_name"` Server string `tfschema:"server"` @@ -3016,30 +3018,18 @@ func (c *ContainerTemplate) flattenContainerAppScaleRules(input *[]containerapps } type WorkloadProfileModel struct { - MaximumCount int `tfschema:"maximum_count"` - MinimumCount int `tfschema:"minimum_count"` + MaximumCount int64 `tfschema:"maximum_count"` + MinimumCount int64 `tfschema:"minimum_count"` Name string `tfschema:"name"` WorkloadProfileType string `tfschema:"workload_profile_type"` } func WorkloadProfileSchema() *pluginsdk.Schema { return &pluginsdk.Schema{ - Type: pluginsdk.TypeList, + Type: pluginsdk.TypeSet, Optional: true, Elem: &pluginsdk.Resource{ Schema: map[string]*pluginsdk.Schema{ - "maximum_count": { - Type: pluginsdk.TypeInt, - Required: true, - ValidateFunc: validation.IntAtLeast(1), - }, - - "minimum_count": { - Type: pluginsdk.TypeInt, - Required: true, - ValidateFunc: validation.IntAtLeast(0), - }, - "name": { Type: pluginsdk.TypeString, Required: true, @@ -3051,6 +3041,16 @@ func WorkloadProfileSchema() *pluginsdk.Schema { Required: true, ValidateFunc: validation.StringIsNotEmpty, }, + + "maximum_count": { + Type: pluginsdk.TypeInt, + Optional: true, + }, + + "minimum_count": { + Type: pluginsdk.TypeInt, + Optional: true, + }, }, }, } @@ -3064,12 +3064,17 @@ func ExpandWorkloadProfiles(input []WorkloadProfileModel) *[]managedenvironments result := make([]managedenvironments.WorkloadProfile, 0) for _, v := range input { - result = append(result, managedenvironments.WorkloadProfile{ + r := managedenvironments.WorkloadProfile{ Name: v.Name, - MaximumCount: pointer.To(int64(v.MaximumCount)), - MinimumCount: pointer.To(int64(v.MinimumCount)), WorkloadProfileType: v.WorkloadProfileType, - }) + } + + if v.Name != consumption { + r.MaximumCount = pointer.To(v.MaximumCount) + r.MinimumCount = pointer.To(v.MinimumCount) + } + + result = append(result, r) } return &result @@ -3079,14 +3084,13 @@ func FlattenWorkloadProfiles(input *[]managedenvironments.WorkloadProfile) []Wor if input == nil || len(*input) == 0 { return []WorkloadProfileModel{} } - result := make([]WorkloadProfileModel, 0) for _, v := range *input { result = append(result, WorkloadProfileModel{ Name: v.Name, - MaximumCount: int(pointer.From(v.MaximumCount)), - MinimumCount: int(pointer.From(v.MinimumCount)), + MaximumCount: pointer.From(v.MaximumCount), + MinimumCount: pointer.From(v.MinimumCount), WorkloadProfileType: v.WorkloadProfileType, }) } From 55d92a988a29756b9c3d207e9a0542b5eb11cc8a Mon Sep 17 00:00:00 2001 From: Jiawei Tao Date: Sun, 8 Oct 2023 15:22:28 +0800 Subject: [PATCH 03/10] fix go fmt --- .../containerapps/container_app_environment_resource.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/internal/services/containerapps/container_app_environment_resource.go b/internal/services/containerapps/container_app_environment_resource.go index a3456f16d6a6..a8edc920dace 100644 --- a/internal/services/containerapps/container_app_environment_resource.go +++ b/internal/services/containerapps/container_app_environment_resource.go @@ -6,7 +6,6 @@ package containerapps import ( "context" "fmt" - "github.com/hashicorp/terraform-provider-azurerm/internal/services/containerapps/helpers" "time" "github.com/hashicorp/go-azure-helpers/lang/pointer" @@ -18,6 +17,7 @@ import ( "github.com/hashicorp/go-azure-sdk/resource-manager/containerapps/2023-05-01/managedenvironments" "github.com/hashicorp/go-azure-sdk/resource-manager/operationalinsights/2020-08-01/workspaces" "github.com/hashicorp/terraform-provider-azurerm/internal/sdk" + "github.com/hashicorp/terraform-provider-azurerm/internal/services/containerapps/helpers" "github.com/hashicorp/terraform-provider-azurerm/internal/services/containerapps/validate" "github.com/hashicorp/terraform-provider-azurerm/internal/tf/pluginsdk" "github.com/hashicorp/terraform-provider-azurerm/internal/tf/validation" From 225d57c769ca8358a5fd2b84bb692b21d9734eed Mon Sep 17 00:00:00 2001 From: Jiawei Tao Date: Sun, 8 Oct 2023 16:31:16 +0800 Subject: [PATCH 04/10] Add doc --- .../docs/r/container_app_environment.html.markdown | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/website/docs/r/container_app_environment.html.markdown b/website/docs/r/container_app_environment.html.markdown index 6c229d4cb4f8..4be129ea6a9e 100644 --- a/website/docs/r/container_app_environment.html.markdown +++ b/website/docs/r/container_app_environment.html.markdown @@ -62,8 +62,22 @@ The following arguments are supported: * `log_analytics_workspace_id` - (Optional) The ID for the Log Analytics Workspace to link this Container Apps Managed Environment to. Changing this forces a new resource to be created. +* `workload_profile` - (Optional) The profile of the workload to scope the container app execution. A `workload_profile` block as defined below. + * `tags` - (Optional) A mapping of tags to assign to the resource. +--- + +A `workload_profile` block supports the following: + +* `name` - (Required) The name of the workload profile. + +* `workload_profile_type` - (Required) Workload profile type for the workloads to run on. + +* `maximum_count` - (Optional) The maximum number of containers that can be deployed in the Container App Environment. + +* `minimum_count` - (Optional) The minimum number of containers that can be deployed in the Container App Environment. + ## Attributes Reference In addition to the Arguments listed above - the following Attributes are exported: From 549f695219aac23007a158effc3f5991aed4a981 Mon Sep 17 00:00:00 2001 From: Jiawei Tao Date: Sun, 8 Oct 2023 16:56:42 +0800 Subject: [PATCH 05/10] fix tflint --- ...container_app_environment_resource_test.go | 30 +++++++++---------- .../local_rulestack_data_source_test.go | 2 +- 2 files changed, 16 insertions(+), 16 deletions(-) diff --git a/internal/services/containerapps/container_app_environment_resource_test.go b/internal/services/containerapps/container_app_environment_resource_test.go index 2c8e2e0fb19a..2739d2aa9a26 100644 --- a/internal/services/containerapps/container_app_environment_resource_test.go +++ b/internal/services/containerapps/container_app_environment_resource_test.go @@ -208,9 +208,9 @@ func (r ContainerAppEnvironmentResource) completeWithWorkloadProfile(data accept return fmt.Sprintf(` provider "azurerm" { features { - resource_group { - prevent_deletion_if_contains_resources = false - } + resource_group { + prevent_deletion_if_contains_resources = false + } } } @@ -229,29 +229,29 @@ resource "azurerm_subnet" "control" { virtual_network_name = azurerm_virtual_network.test.name address_prefixes = ["10.0.0.0/23"] delegation { - name = "acctestdelegation%[2]d" - service_delegation { - actions = ["Microsoft.Network/virtualNetworks/subnets/join/action"] - name = "Microsoft.App/environments" - } + name = "acctestdelegation%[2]d" + service_delegation { + actions = ["Microsoft.Network/virtualNetworks/subnets/join/action"] + name = "Microsoft.App/environments" + } } } resource "azurerm_container_app_environment" "test" { - name = "acctest-CAEnv%[2]d" - resource_group_name = azurerm_resource_group.test.name - location = azurerm_resource_group.test.location + name = "acctest-CAEnv%[2]d" + resource_group_name = azurerm_resource_group.test.name + location = azurerm_resource_group.test.location infrastructure_subnet_id = azurerm_subnet.control.id workload_profile { - maximum_count = 2 - minimum_count = 0 - name = "My-GP-01" + maximum_count = 2 + minimum_count = 0 + name = "My-GP-01" workload_profile_type = "D4" } workload_profile { - name = "Consumption" + name = "Consumption" workload_profile_type = "Consumption" } diff --git a/internal/services/paloalto/local_rulestack_data_source_test.go b/internal/services/paloalto/local_rulestack_data_source_test.go index aa7cb48cd9fd..a56016e691c9 100644 --- a/internal/services/paloalto/local_rulestack_data_source_test.go +++ b/internal/services/paloalto/local_rulestack_data_source_test.go @@ -29,7 +29,7 @@ func (d LocalRulestackDataSource) basic(data acceptance.TestData) string { return fmt.Sprintf(` %s -data "azurerm_palo_alto_local_rulestack" "test"{ +data "azurerm_palo_alto_local_rulestack" "test" { name = azurerm_palo_alto_local_rulestack.test.name resource_group_name = azurerm_palo_alto_local_rulestack.test.resource_group_name } From 77c826052d8afa8046400607d7ca919e1f689c33 Mon Sep 17 00:00:00 2001 From: jiawei Date: Tue, 17 Oct 2023 08:43:29 +0000 Subject: [PATCH 06/10] Fix test --- .../container_app_environment_resource_test.go | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/internal/services/containerapps/container_app_environment_resource_test.go b/internal/services/containerapps/container_app_environment_resource_test.go index 2739d2aa9a26..275085b45076 100644 --- a/internal/services/containerapps/container_app_environment_resource_test.go +++ b/internal/services/containerapps/container_app_environment_resource_test.go @@ -207,11 +207,7 @@ resource "azurerm_container_app_environment" "test" { func (r ContainerAppEnvironmentResource) completeWithWorkloadProfile(data acceptance.TestData) string { return fmt.Sprintf(` provider "azurerm" { - features { - resource_group { - prevent_deletion_if_contains_resources = false - } - } + features {} } %[1]s From 16b6acf4779533c4a7210346ad7a60fcd3d87598 Mon Sep 17 00:00:00 2001 From: jiawei Date: Wed, 18 Oct 2023 05:58:27 +0000 Subject: [PATCH 07/10] rename workload profile attributes --- website/docs/r/container_app_environment.html.markdown | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/website/docs/r/container_app_environment.html.markdown b/website/docs/r/container_app_environment.html.markdown index 4be129ea6a9e..20ed29e8eba5 100644 --- a/website/docs/r/container_app_environment.html.markdown +++ b/website/docs/r/container_app_environment.html.markdown @@ -74,9 +74,9 @@ A `workload_profile` block supports the following: * `workload_profile_type` - (Required) Workload profile type for the workloads to run on. -* `maximum_count` - (Optional) The maximum number of containers that can be deployed in the Container App Environment. +* `maximum_container_count` - (Optional) The maximum number of containers that can be deployed in the Container App Environment. -* `minimum_count` - (Optional) The minimum number of containers that can be deployed in the Container App Environment. +* `minimum_container_count` - (Optional) The minimum number of containers that can be deployed in the Container App Environment. ## Attributes Reference From aab804ec166a694c449bcf9a42fcc2268d85c37f Mon Sep 17 00:00:00 2001 From: jiawei Date: Mon, 13 Nov 2023 08:09:46 +0000 Subject: [PATCH 08/10] Modify workload_profile structure --- ...container_app_environment_resource_test.go | 5 - .../helpers/container_app_environment.go | 111 ++++++++++++++++++ .../containerapps/helpers/container_apps.go | 83 ------------- 3 files changed, 111 insertions(+), 88 deletions(-) create mode 100644 internal/services/containerapps/helpers/container_app_environment.go diff --git a/internal/services/containerapps/container_app_environment_resource_test.go b/internal/services/containerapps/container_app_environment_resource_test.go index 275085b45076..2a282c81f59f 100644 --- a/internal/services/containerapps/container_app_environment_resource_test.go +++ b/internal/services/containerapps/container_app_environment_resource_test.go @@ -246,11 +246,6 @@ resource "azurerm_container_app_environment" "test" { workload_profile_type = "D4" } - workload_profile { - name = "Consumption" - workload_profile_type = "Consumption" - } - zone_redundancy_enabled = true tags = { diff --git a/internal/services/containerapps/helpers/container_app_environment.go b/internal/services/containerapps/helpers/container_app_environment.go new file mode 100644 index 000000000000..bdc35d0c2daf --- /dev/null +++ b/internal/services/containerapps/helpers/container_app_environment.go @@ -0,0 +1,111 @@ +// Copyright (c) HashiCorp, Inc. +// SPDX-License-Identifier: MPL-2.0 + +package helpers + +import ( + "github.com/hashicorp/go-azure-helpers/lang/pointer" + "github.com/hashicorp/go-azure-sdk/resource-manager/containerapps/2023-05-01/managedenvironments" + "github.com/hashicorp/terraform-provider-azurerm/internal/tf/pluginsdk" + "github.com/hashicorp/terraform-provider-azurerm/internal/tf/validation" +) + +const consumption = "Consumption" + +type WorkloadProfileModel struct { + MaximumCount int `tfschema:"maximum_count"` + MinimumCount int `tfschema:"minimum_count"` + Name string `tfschema:"name"` + WorkloadProfileType string `tfschema:"workload_profile_type"` +} + +func WorkloadProfileSchema() *pluginsdk.Schema { + return &pluginsdk.Schema{ + Type: pluginsdk.TypeSet, + Optional: true, + Elem: &pluginsdk.Resource{ + Schema: map[string]*pluginsdk.Schema{ + "name": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringIsNotEmpty, + }, + + "workload_profile_type": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringInSlice([]string{ + "D4", + "D8", + "D16", + "D32", + "E4", + "E8", + "E16", + "E32", + }, false), + }, + + "maximum_count": { + Type: pluginsdk.TypeInt, + Optional: true, + }, + + "minimum_count": { + Type: pluginsdk.TypeInt, + Optional: true, + }, + }, + }, + } +} + +func ExpandWorkloadProfiles(input []WorkloadProfileModel) *[]managedenvironments.WorkloadProfile { + if len(input) == 0 { + return nil + } + + result := make([]managedenvironments.WorkloadProfile, 0) + + for _, v := range input { + r := managedenvironments.WorkloadProfile{ + Name: v.Name, + WorkloadProfileType: v.WorkloadProfileType, + } + + if v.Name != consumption { + r.MaximumCount = pointer.To(int64(v.MaximumCount)) + r.MinimumCount = pointer.To(int64(v.MinimumCount)) + } + + result = append(result, r) + } + + result = append(result, managedenvironments.WorkloadProfile{ + Name: consumption, + WorkloadProfileType: consumption, + }) + + return &result +} + +func FlattenWorkloadProfiles(input *[]managedenvironments.WorkloadProfile) []WorkloadProfileModel { + if input == nil || len(*input) == 0 { + return []WorkloadProfileModel{} + } + result := make([]WorkloadProfileModel, 0) + + for _, v := range *input { + if v.Name == consumption { + continue + } + result = append(result, WorkloadProfileModel{ + Name: v.Name, + MaximumCount: int(pointer.From(v.MaximumCount)), + MinimumCount: int(pointer.From(v.MinimumCount)), + WorkloadProfileType: v.WorkloadProfileType, + }) + } + + return result +} diff --git a/internal/services/containerapps/helpers/container_apps.go b/internal/services/containerapps/helpers/container_apps.go index 072cd7b27675..61ee769355a1 100644 --- a/internal/services/containerapps/helpers/container_apps.go +++ b/internal/services/containerapps/helpers/container_apps.go @@ -17,8 +17,6 @@ import ( "github.com/hashicorp/terraform-provider-azurerm/internal/tf/validation" ) -const consumption = "Consumption" - type Registry struct { PasswordSecretRef string `tfschema:"password_secret_name"` Server string `tfschema:"server"` @@ -3016,84 +3014,3 @@ func (c *ContainerTemplate) flattenContainerAppScaleRules(input *[]containerapps c.TCPScaleRules = tcpScaleRules } } - -type WorkloadProfileModel struct { - MaximumCount int64 `tfschema:"maximum_count"` - MinimumCount int64 `tfschema:"minimum_count"` - Name string `tfschema:"name"` - WorkloadProfileType string `tfschema:"workload_profile_type"` -} - -func WorkloadProfileSchema() *pluginsdk.Schema { - return &pluginsdk.Schema{ - Type: pluginsdk.TypeSet, - Optional: true, - Elem: &pluginsdk.Resource{ - Schema: map[string]*pluginsdk.Schema{ - "name": { - Type: pluginsdk.TypeString, - Required: true, - ValidateFunc: validation.StringIsNotEmpty, - }, - - "workload_profile_type": { - Type: pluginsdk.TypeString, - Required: true, - ValidateFunc: validation.StringIsNotEmpty, - }, - - "maximum_count": { - Type: pluginsdk.TypeInt, - Optional: true, - }, - - "minimum_count": { - Type: pluginsdk.TypeInt, - Optional: true, - }, - }, - }, - } -} - -func ExpandWorkloadProfiles(input []WorkloadProfileModel) *[]managedenvironments.WorkloadProfile { - if len(input) == 0 { - return nil - } - - result := make([]managedenvironments.WorkloadProfile, 0) - - for _, v := range input { - r := managedenvironments.WorkloadProfile{ - Name: v.Name, - WorkloadProfileType: v.WorkloadProfileType, - } - - if v.Name != consumption { - r.MaximumCount = pointer.To(v.MaximumCount) - r.MinimumCount = pointer.To(v.MinimumCount) - } - - result = append(result, r) - } - - return &result -} - -func FlattenWorkloadProfiles(input *[]managedenvironments.WorkloadProfile) []WorkloadProfileModel { - if input == nil || len(*input) == 0 { - return []WorkloadProfileModel{} - } - result := make([]WorkloadProfileModel, 0) - - for _, v := range *input { - result = append(result, WorkloadProfileModel{ - Name: v.Name, - MaximumCount: pointer.From(v.MaximumCount), - MinimumCount: pointer.From(v.MinimumCount), - WorkloadProfileType: v.WorkloadProfileType, - }) - } - - return result -} From 2408bb4aa4e115f26253caf16aa4722797e675f5 Mon Sep 17 00:00:00 2001 From: Jiawei Tao Date: Tue, 14 Nov 2023 10:14:08 +0800 Subject: [PATCH 09/10] Fix docs of workload profile attributes --- .../containerapps/helpers/container_app_environment.go | 4 ++-- website/docs/r/container_app_environment.html.markdown | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/internal/services/containerapps/helpers/container_app_environment.go b/internal/services/containerapps/helpers/container_app_environment.go index bdc35d0c2daf..3e11e778122d 100644 --- a/internal/services/containerapps/helpers/container_app_environment.go +++ b/internal/services/containerapps/helpers/container_app_environment.go @@ -48,12 +48,12 @@ func WorkloadProfileSchema() *pluginsdk.Schema { "maximum_count": { Type: pluginsdk.TypeInt, - Optional: true, + Required: true, }, "minimum_count": { Type: pluginsdk.TypeInt, - Optional: true, + Required: true, }, }, }, diff --git a/website/docs/r/container_app_environment.html.markdown b/website/docs/r/container_app_environment.html.markdown index 20ed29e8eba5..4d41eb2f225e 100644 --- a/website/docs/r/container_app_environment.html.markdown +++ b/website/docs/r/container_app_environment.html.markdown @@ -74,9 +74,9 @@ A `workload_profile` block supports the following: * `workload_profile_type` - (Required) Workload profile type for the workloads to run on. -* `maximum_container_count` - (Optional) The maximum number of containers that can be deployed in the Container App Environment. +* `maximum_container_count` - (Optional) The maximum number of instances of workload profile that can be deployed in the Container App Environment. -* `minimum_container_count` - (Optional) The minimum number of containers that can be deployed in the Container App Environment. +* `minimum_container_count` - (Optional) The minimum number of instances of workload profile that can be deployed in the Container App Environment. ## Attributes Reference From 73097951c2f87593264f5aafd895ce41ad49beeb Mon Sep 17 00:00:00 2001 From: Jiawei Tao Date: Mon, 20 Nov 2023 15:40:01 +0800 Subject: [PATCH 10/10] Update tests --- ...container_app_environment_resource_test.go | 29 +++++++++++++++++++ .../helpers/container_app_environment.go | 4 ++- .../r/container_app_environment.html.markdown | 2 +- 3 files changed, 33 insertions(+), 2 deletions(-) diff --git a/internal/services/containerapps/container_app_environment_resource_test.go b/internal/services/containerapps/container_app_environment_resource_test.go index 2a282c81f59f..e304eeaf018d 100644 --- a/internal/services/containerapps/container_app_environment_resource_test.go +++ b/internal/services/containerapps/container_app_environment_resource_test.go @@ -79,6 +79,35 @@ func TestAccContainerAppEnvironment_withWorkloadProfile(t *testing.T) { }) } +func TestAccContainerAppEnvironment_updateWorkloadProfile(t *testing.T) { + data := acceptance.BuildTestData(t, "azurerm_container_app_environment", "test") + r := ContainerAppEnvironmentResource{} + + data.ResourceTest(t, r, []acceptance.TestStep{ + { + Config: r.complete(data), + Check: acceptance.ComposeTestCheckFunc( + check.That(data.ResourceName).ExistsInAzure(r), + ), + }, + data.ImportStep("log_analytics_workspace_id"), + { + Config: r.completeWithWorkloadProfile(data), + Check: acceptance.ComposeTestCheckFunc( + check.That(data.ResourceName).ExistsInAzure(r), + ), + }, + data.ImportStep("log_analytics_workspace_id"), + { + Config: r.completeUpdate(data), + Check: acceptance.ComposeTestCheckFunc( + check.That(data.ResourceName).ExistsInAzure(r), + ), + }, + data.ImportStep("log_analytics_workspace_id"), + }) +} + func TestAccContainerAppEnvironment_completeUpdate(t *testing.T) { data := acceptance.BuildTestData(t, "azurerm_container_app_environment", "test") r := ContainerAppEnvironmentResource{} diff --git a/internal/services/containerapps/helpers/container_app_environment.go b/internal/services/containerapps/helpers/container_app_environment.go index 3e11e778122d..736798edb5ae 100644 --- a/internal/services/containerapps/helpers/container_app_environment.go +++ b/internal/services/containerapps/helpers/container_app_environment.go @@ -4,6 +4,8 @@ package helpers import ( + "strings" + "github.com/hashicorp/go-azure-helpers/lang/pointer" "github.com/hashicorp/go-azure-sdk/resource-manager/containerapps/2023-05-01/managedenvironments" "github.com/hashicorp/terraform-provider-azurerm/internal/tf/pluginsdk" @@ -96,7 +98,7 @@ func FlattenWorkloadProfiles(input *[]managedenvironments.WorkloadProfile) []Wor result := make([]WorkloadProfileModel, 0) for _, v := range *input { - if v.Name == consumption { + if strings.EqualFold(v.WorkloadProfileType, consumption) { continue } result = append(result, WorkloadProfileModel{ diff --git a/website/docs/r/container_app_environment.html.markdown b/website/docs/r/container_app_environment.html.markdown index 4d41eb2f225e..d0fac14c3d86 100644 --- a/website/docs/r/container_app_environment.html.markdown +++ b/website/docs/r/container_app_environment.html.markdown @@ -72,7 +72,7 @@ A `workload_profile` block supports the following: * `name` - (Required) The name of the workload profile. -* `workload_profile_type` - (Required) Workload profile type for the workloads to run on. +* `workload_profile_type` - (Required) Workload profile type for the workloads to run on. Possible values include `D4`, `D8`, `D16`, `D32`, `E4`, `E8`, `E16` and `E32`. * `maximum_container_count` - (Optional) The maximum number of instances of workload profile that can be deployed in the Container App Environment.