Skip to content
Open
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
5 changes: 5 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,11 @@ test-framework:
@echo "Running framework tests only..."
@TF_ACC=1 GOLANG_PROTOBUF_REGISTRATION_CONFLICT=ignore go test -v -tags=planonly ./tests/framework/...

# AKS bootstrap_vm_params unit tests (requires GOLANG_PROTOBUF_REGISTRATION_CONFLICT=ignore)
test-aks-bootstrap-vm:
@echo "Running AKS bootstrap_vm_params unit tests..."
GOLANG_PROTOBUF_REGISTRATION_CONFLICT=ignore go test -v ./rafay/ -run 'TestExpandAKSBootstrapVmParams|TestExpandAKSBootstrapVmImage|TestExpandAKSClusterConfigSpecWithBootstrapVmParams|TestFlattenAKSBootstrapVmParams|TestFlattenAKSBootstrapVmImage|TestFlattenAKSClusterConfigSpecWithBootstrapVmParams'

test-integration:
@echo "Running integration tests only..."
@TF_ACC=1 GOLANG_PROTOBUF_REGISTRATION_CONFLICT=ignore go test -v -tags=planonly ./tests/integration/plan_only/...
Expand Down
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ module github.com/RafaySystems/terraform-provider-rafay
go 1.24.13

require (
github.com/RafaySystems/edge-common v1.24.1-0.20260217060826-5d14ce3468bb
github.com/RafaySystems/edge-common v1.24.1-0.20260224030813-316a61fe7ada
github.com/RafaySystems/rafay-common v1.29.1-rc2.0.20260223061243-4275b1866249
github.com/RafaySystems/rctl v1.29.1-0.20260223064400-85e7030db490
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc
Expand Down
4 changes: 2 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,8 @@ github.com/ProtonMail/go-crypto v1.1.0-alpha.2 h1:bkyFVUP+ROOARdgCiJzNQo2V2kiB97
github.com/ProtonMail/go-crypto v1.1.0-alpha.2/go.mod h1:rA3QumHc/FZ8pAHreoekgiAbzpNsfQAosU5td4SnOrE=
github.com/RafaySystems/eaas-playground/proto v0.0.0-20251008151511-bf1cf36fe5bd h1:50smMqzYlYN0e7bgVLGBIX7Y1V9fUE+yUhkCoQIVgD4=
github.com/RafaySystems/eaas-playground/proto v0.0.0-20251008151511-bf1cf36fe5bd/go.mod h1:lAle7/tiVlakfiXdJKnsf6qNdLkoWS712T4pAXytSOQ=
github.com/RafaySystems/edge-common v1.24.1-0.20260217060826-5d14ce3468bb h1:8anR/rG1Esy9NNBJiaN7M0skF/6XbPNXEoCFJxfuZ88=
github.com/RafaySystems/edge-common v1.24.1-0.20260217060826-5d14ce3468bb/go.mod h1:tbd1Z34RfnJ3umcDjf478+dh7hJ66ict3wra7YbQmiA=
github.com/RafaySystems/edge-common v1.24.1-0.20260224030813-316a61fe7ada h1:3SbAmUwwp9XWJtNYWh7RgNgqcwmjnGyHF7L+8duZWtc=
github.com/RafaySystems/edge-common v1.24.1-0.20260224030813-316a61fe7ada/go.mod h1:tbd1Z34RfnJ3umcDjf478+dh7hJ66ict3wra7YbQmiA=
github.com/RafaySystems/paas-common v0.0.0-20250519095800-e92646adcd6e h1:SrznY+xkaQ4BkX0HXGa0upur7RAtR6UsTsdMNEgBreY=
github.com/RafaySystems/paas-common v0.0.0-20250519095800-e92646adcd6e/go.mod h1:vDR0S28Q+hwE/5wO0L/Ohn9CZwaI/o2QuPupJ2iLI7k=
github.com/RafaySystems/rafay-common v1.29.1-rc2.0.20260223061243-4275b1866249 h1:9rTe9UFUo38dssUqezoKrnHSYhPXdpOzKolewJMzckg=
Expand Down
18 changes: 18 additions & 0 deletions rafay/aks_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -85,9 +85,27 @@ type AKSClusterConfigSpec struct {
NodePools []*AKSNodePool `yaml:"nodePools,omitempty"`
MaintenanceConfigs []*AKSMaintenanceConfig `yaml:"maintenanceConfigurations,omitempty"`
WorkloadIdentities []*AzureWorkloadIdentity `yaml:"workloadIdentities,omitempty"`
BootstrapVmParams *AKSBootstrapVmParams `yaml:"bootstrapVmParams,omitempty"`
//Internal *AKSRafayInternal `yaml:"internal,omitempty"`
}

// AKSBootstrapVmParams holds optional bootstrap VM size and image for AKS cluster provisioning.
// When omitted, defaults are used: VM size Standard_B1ms, Canonical Ubuntu Server Jammy 22.04 LTS.
type AKSBootstrapVmParams struct {
VMSize string `yaml:"vmSize,omitempty"` // e.g. "Standard_B1ms"
Image *AKSBootstrapVmImageRef `yaml:"image,omitempty"`
}

// AKSBootstrapVmImageRef is the image reference for the bootstrap VM (Azure compute.StorageProfile.ImageReference).
// Use ID for non-marketplace (Compute Gallery, custom image); or Publisher/Offer/Sku/Version for marketplace.
type AKSBootstrapVmImageRef struct {
ID string `yaml:"id,omitempty"`
Publisher string `yaml:"publisher,omitempty"`
Offer string `yaml:"offer,omitempty"`
Sku string `yaml:"sku,omitempty"`
Version string `yaml:"version,omitempty"`
}

type AzureWorkloadIdentity struct {
CreateIdentity bool `yaml:"createIdentity,omitempty"`
Metadata *AzureWorkloadIdentityMetadata `yaml:"metadata,omitempty"`
Expand Down
168 changes: 168 additions & 0 deletions rafay/resource_aks_cluster.go
Original file line number Diff line number Diff line change
Expand Up @@ -324,10 +324,68 @@ func clusterAKSClusterConfigSpec() map[string]*schema.Schema {
Schema: clusterAKSMaintenanceConfig(),
},
},
"bootstrap_vm_params": {
Type: schema.TypeList,
Optional: true,
MaxItems: 1,
Description: "Optional bootstrap VM size and image for AKS cluster provisioning. When omitted, defaults are used: VM size Standard_B1ms, Canonical Ubuntu Server Jammy 22.04 LTS.",
Elem: &schema.Resource{
Schema: clusterAKSBootstrapVmParams(),
},
},
}
return s
}

func clusterAKSBootstrapVmParams() map[string]*schema.Schema {
return map[string]*schema.Schema{
"vm_size": {
Type: schema.TypeString,
Optional: true,
Description: "Azure VM size for the bootstrap VM (e.g. Standard_B1ms).",
},
"image": {
Type: schema.TypeList,
Optional: true,
MaxItems: 1,
Description: "Image reference for the bootstrap VM. Use id for non-marketplace (Compute Gallery, custom image), or publisher/offer/sku/version for marketplace.",
Elem: &schema.Resource{
Schema: clusterAKSBootstrapVmImage(),
},
},
}
}

func clusterAKSBootstrapVmImage() map[string]*schema.Schema {
return map[string]*schema.Schema{
"id": {
Type: schema.TypeString,
Optional: true,
Description: "Full Azure resource ID for non-marketplace image (Compute Gallery, custom image). Takes precedence when set.",
},
"publisher": {
Type: schema.TypeString,
Optional: true,
Description: "Marketplace image publisher (e.g. Canonical).",
},
"offer": {
Type: schema.TypeString,
Optional: true,
Description: "Marketplace image offer (e.g. 0001-com-ubuntu-server-jammy).",
},
"sku": {
Type: schema.TypeString,
Optional: true,
Description: "Marketplace image SKU (e.g. 22_04-lts).",
},
"version": {
Type: schema.TypeString,
Optional: true,
Description: "Marketplace image version (e.g. latest).",
},
}
}

func clusterAKSManagedCluster() map[string]*schema.Schema {
s := map[string]*schema.Schema{
"apiversion": {
Expand Down Expand Up @@ -2494,6 +2552,55 @@ func expandAKSClusterConfigSpec(p []interface{}, rawConfig cty.Value) *AKSCluste
obj.MaintenanceConfigs = expandAKSMaintenanceConfigs(v)
}

if v, ok := in["bootstrap_vm_params"].([]interface{}); ok && len(v) > 0 {
obj.BootstrapVmParams = expandAKSBootstrapVmParams(v)
}

return obj
}

func expandAKSBootstrapVmParams(p []interface{}) *AKSBootstrapVmParams {
if len(p) == 0 || p[0] == nil {
return nil
}
in := p[0].(map[string]interface{})
obj := &AKSBootstrapVmParams{}
if v, ok := in["vm_size"].(string); ok && len(v) > 0 {
obj.VMSize = v
}
if v, ok := in["image"].([]interface{}); ok && len(v) > 0 {
obj.Image = expandAKSBootstrapVmImage(v)
}
if obj.VMSize == "" && obj.Image == nil {
return nil
}
return obj
}

func expandAKSBootstrapVmImage(p []interface{}) *AKSBootstrapVmImageRef {
if len(p) == 0 || p[0] == nil {
return nil
}
in := p[0].(map[string]interface{})
obj := &AKSBootstrapVmImageRef{}
if v, ok := in["id"].(string); ok && len(v) > 0 {
obj.ID = v
}
if v, ok := in["publisher"].(string); ok && len(v) > 0 {
obj.Publisher = v
}
if v, ok := in["offer"].(string); ok && len(v) > 0 {
obj.Offer = v
}
if v, ok := in["sku"].(string); ok && len(v) > 0 {
obj.Sku = v
}
if v, ok := in["version"].(string); ok && len(v) > 0 {
obj.Version = v
}
if obj.ID == "" && obj.Publisher == "" && obj.Offer == "" && obj.Sku == "" && obj.Version == "" {
return nil
}
return obj
}

Expand Down Expand Up @@ -4509,10 +4616,65 @@ func flattenAKSClusterConfigSpec(in *AKSClusterConfigSpec, p []interface{}, rawS
obj["maintenance_configurations"] = flattenAKSMaintenanceConfigs(in.MaintenanceConfigs, v)
}

if in.BootstrapVmParams != nil {
v, ok := obj["bootstrap_vm_params"].([]interface{})
if !ok {
v = []interface{}{}
}
obj["bootstrap_vm_params"] = flattenAKSBootstrapVmParams(in.BootstrapVmParams, v)
}

return []interface{}{obj}

}

func flattenAKSBootstrapVmParams(in *AKSBootstrapVmParams, p []interface{}) []interface{} {
if in == nil {
return nil
}
obj := map[string]interface{}{}
if len(p) != 0 && p[0] != nil {
obj = p[0].(map[string]interface{})
}
if len(in.VMSize) > 0 {
obj["vm_size"] = in.VMSize
}
if in.Image != nil {
v, ok := obj["image"].([]interface{})
if !ok {
v = []interface{}{}
}
obj["image"] = flattenAKSBootstrapVmImage(in.Image, v)
}
return []interface{}{obj}
}

func flattenAKSBootstrapVmImage(in *AKSBootstrapVmImageRef, p []interface{}) []interface{} {
if in == nil {
return nil
}
obj := map[string]interface{}{}
if len(p) != 0 && p[0] != nil {
obj = p[0].(map[string]interface{})
}
if len(in.ID) > 0 {
obj["id"] = in.ID
}
if len(in.Publisher) > 0 {
obj["publisher"] = in.Publisher
}
if len(in.Offer) > 0 {
obj["offer"] = in.Offer
}
if len(in.Sku) > 0 {
obj["sku"] = in.Sku
}
if len(in.Version) > 0 {
obj["version"] = in.Version
}
return []interface{}{obj}
}

func flattenAKSManagedCluster(in *AKSManagedCluster, p []interface{}) []interface{} {
if in == nil {
return nil
Expand Down Expand Up @@ -6920,6 +7082,12 @@ func resourceAKSClusterRead(ctx context.Context, d *schema.ResourceData, m inter
clusterSpec.Spec.AKSClusterConfig.Spec.WorkloadIdentities = nil
}

// BootstrapVmParams is create-only; not supported for Day 2 operations. Do not expose in state on read.
if clusterSpec.Spec.AKSClusterConfig.Spec.BootstrapVmParams != nil {
log.Println("Removing deployed bootstrap_vm_params from deployed cluster spec (create-only, no Day 2)")
clusterSpec.Spec.AKSClusterConfig.Spec.BootstrapVmParams = nil
}

// ============== Unfurl End =================

err = flattenAKSCluster(d, clusterSpec)
Expand Down
Loading