diff --git a/pkg/model/awsmodel/autoscalinggroup.go b/pkg/model/awsmodel/autoscalinggroup.go index f1533e9c8d..86ccb7ebe9 100644 --- a/pkg/model/awsmodel/autoscalinggroup.go +++ b/pkg/model/awsmodel/autoscalinggroup.go @@ -100,7 +100,9 @@ func (b *AutoscalingGroupModelBuilder) Build(c *fi.CloudupModelBuilderContext) e if warmPool.IsEnabled() { warmPoolTask.MinSize = warmPool.MinSize warmPoolTask.MaxSize = warmPool.MaxSize - + tsk.WarmPool = warmPoolTask + } else { + tsk.WarmPool = nil } c.AddTask(warmPoolTask) diff --git a/tests/integration/update_cluster/minimal-warmpool/kubernetes.tf b/tests/integration/update_cluster/minimal-warmpool/kubernetes.tf index 82215b52c2..ebc2f94348 100644 --- a/tests/integration/update_cluster/minimal-warmpool/kubernetes.tf +++ b/tests/integration/update_cluster/minimal-warmpool/kubernetes.tf @@ -198,6 +198,10 @@ resource "aws_autoscaling_group" "nodes-minimal-warmpool-example-com" { value = "owned" } vpc_zone_identifier = [aws_subnet.us-test-1a-minimal-warmpool-example-com.id] + warm_pool { + max_group_prepared_capacity = 1 + min_size = 0 + } } resource "aws_autoscaling_lifecycle_hook" "kops-warmpool-nodes" { diff --git a/upup/pkg/fi/cloudup/awstasks/autoscalinggroup.go b/upup/pkg/fi/cloudup/awstasks/autoscalinggroup.go index e1f947a56b..29a4dc8a85 100644 --- a/upup/pkg/fi/cloudup/awstasks/autoscalinggroup.go +++ b/upup/pkg/fi/cloudup/awstasks/autoscalinggroup.go @@ -98,6 +98,8 @@ type AutoscalingGroup struct { TargetGroups []*TargetGroup // CapacityRebalance makes ASG proactively replace spot instances when ASG receives a rebalance recommendation CapacityRebalance *bool + // WarmPool is the WarmPool config for the ASG + WarmPool *WarmPool } var _ fi.CompareWithID = &AutoscalingGroup{} @@ -929,6 +931,11 @@ type terraformMixedInstancesPolicy struct { InstanceDistribution []*terraformAutoscalingInstanceDistribution `cty:"instances_distribution"` } +type terraformWarmPool struct { + MinSize *int64 `cty:"min_size"` + MaxSize *int64 `cty:"max_group_prepared_capacity"` +} + type terraformAutoscalingGroup struct { Name *string `cty:"name"` LaunchConfigurationName *terraformWriter.Literal `cty:"launch_configuration"` @@ -946,6 +953,7 @@ type terraformAutoscalingGroup struct { TargetGroupARNs []*terraformWriter.Literal `cty:"target_group_arns"` MaxInstanceLifetime *int64 `cty:"max_instance_lifetime"` CapacityRebalance *bool `cty:"capacity_rebalance"` + WarmPool *terraformWarmPool `cty:"warm_pool"` } // RenderTerraform is responsible for rendering the terraform codebase @@ -1069,6 +1077,13 @@ func (_ *AutoscalingGroup) RenderTerraform(t *terraform.TerraformTarget, a, e, c } tf.SuspendedProcesses = processes + if e.WarmPool != nil && *e.WarmPool.Enabled { + tf.WarmPool = &terraformWarmPool{ + MinSize: &e.WarmPool.MinSize, + MaxSize: e.WarmPool.MaxSize, + } + } + return t.RenderResource("aws_autoscaling_group", *e.Name, tf) } diff --git a/upup/pkg/fi/cloudup/awstasks/autoscalinggroup_test.go b/upup/pkg/fi/cloudup/awstasks/autoscalinggroup_test.go index f341470b11..417fee4982 100644 --- a/upup/pkg/fi/cloudup/awstasks/autoscalinggroup_test.go +++ b/upup/pkg/fi/cloudup/awstasks/autoscalinggroup_test.go @@ -331,6 +331,89 @@ terraform { } `, }, + { + Resource: &AutoscalingGroup{ + Name: fi.PtrTo("test1"), + LaunchTemplate: &LaunchTemplate{Name: fi.PtrTo("test_lt")}, + MaxSize: fi.PtrTo(int64(10)), + Metrics: []string{"test"}, + MinSize: fi.PtrTo(int64(5)), + MixedInstanceOverrides: []string{"t2.medium", "t2.large"}, + MixedOnDemandBase: fi.PtrTo(int64(4)), + MixedOnDemandAboveBase: fi.PtrTo(int64(30)), + MixedSpotAllocationStrategy: fi.PtrTo("capacity-optimized"), + WarmPool: &WarmPool{ + Enabled: fi.PtrTo(true), + MinSize: 3, + MaxSize: fi.PtrTo(int64(5)), + }, + Subnets: []*Subnet{ + { + Name: fi.PtrTo("test-sg"), + ID: fi.PtrTo("sg-1111"), + }, + }, + Tags: map[string]string{ + "test": "tag", + "cluster": "test", + }, + }, + Expected: `provider "aws" { + region = "eu-west-2" +} + +resource "aws_autoscaling_group" "test1" { + enabled_metrics = ["test"] + max_size = 10 + min_size = 5 + mixed_instances_policy { + instances_distribution { + on_demand_base_capacity = 4 + on_demand_percentage_above_base_capacity = 30 + spot_allocation_strategy = "capacity-optimized" + } + launch_template { + launch_template_specification { + launch_template_id = aws_launch_template.test_lt.id + version = aws_launch_template.test_lt.latest_version + } + override { + instance_type = "t2.medium" + } + override { + instance_type = "t2.large" + } + } + } + name = "test1" + tag { + key = "cluster" + propagate_at_launch = true + value = "test" + } + tag { + key = "test" + propagate_at_launch = true + value = "tag" + } + vpc_zone_identifier = [aws_subnet.test-sg.id] + warm_pool { + max_group_prepared_capacity = 5 + min_size = 3 + } +} + +terraform { + required_version = ">= 0.15.0" + required_providers { + aws = { + "source" = "hashicorp/aws" + "version" = ">= 4.0.0" + } + } +} +`, + }, } doRenderTests(t, "RenderTerraform", cases) diff --git a/upup/pkg/fi/cloudup/awstasks/warmpool.go b/upup/pkg/fi/cloudup/awstasks/warmpool.go index 4de8864c93..18f84a3c68 100644 --- a/upup/pkg/fi/cloudup/awstasks/warmpool.go +++ b/upup/pkg/fi/cloudup/awstasks/warmpool.go @@ -20,7 +20,6 @@ import ( "fmt" "github.com/aws/aws-sdk-go/service/autoscaling" - "k8s.io/klog/v2" "k8s.io/kops/upup/pkg/fi" "k8s.io/kops/upup/pkg/fi/cloudup/awsup" "k8s.io/kops/upup/pkg/fi/cloudup/terraform" @@ -118,9 +117,7 @@ func (*WarmPool) RenderAWS(t *awsup.AWSAPITarget, a, e, changes *WarmPool) error return nil } +// For the terraform target, warmpool config is rendered inside the AutoscalingGroup resource func (_ *WarmPool) RenderTerraform(t *terraform.TerraformTarget, a, e, changes *WarmPool) error { - if changes != nil { - klog.Warning("ASG warm pool is not supported by the terraform target") - } return nil }