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
42 changes: 42 additions & 0 deletions cmd/openshift-install/features.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
package main

import (
"encoding/json"
"fmt"
"strings"

"github.com/sirupsen/logrus"
"github.com/spf13/cobra"
)

var (
outputJSON = false
hiddenFeatures = []string{
"terraform-spot-masters",
}
)

func newListFeaturesCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "list-hidden-features",
Short: "List supported hidden features",
Long: "",
Hidden: true,
Args: cobra.ExactArgs(0),
Run: func(_ *cobra.Command, _ []string) {
var out string
if outputJSON {
outb, err := json.Marshal(hiddenFeatures)
if err != nil {
logrus.Fatalf("failed to marshal output: %s", err.Error())
}
out = string(outb)
} else {
out = strings.Join(hiddenFeatures, "\n")
}
fmt.Println(out)
},
}
cmd.PersistentFlags().BoolVar(&outputJSON, "json", false, "print output in json format")
return cmd
}
1 change: 1 addition & 0 deletions cmd/openshift-install/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@ func installerMain() {
newCompletionCmd(),
newExplainCmd(),
newAgentCmd(ctx),
newListFeaturesCmd(),
} {
rootCmd.AddCommand(subCmd)
}
Expand Down
10 changes: 10 additions & 0 deletions data/data/aws/bootstrap/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,16 @@ resource "aws_instance" "bootstrap" {
vpc_security_group_ids = [var.master_sg_id, aws_security_group.bootstrap.id]
associate_public_ip_address = local.public_endpoints && var.aws_public_ipv4_pool == ""

dynamic "instance_market_options" {
for_each = var.aws_master_use_spot_instance ? [1] : []
content {
market_type = "spot"
spot_options {
spot_instance_type = "one-time"
}
}
}

lifecycle {
# Ignore changes in the AMI which force recreation of the resource. This
# avoids accidental deletion of nodes whenever a new OS release comes out.
Expand Down
1 change: 1 addition & 0 deletions data/data/aws/cluster/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@ module "masters" {
user_data_ign = var.ignition_master
publish_strategy = var.aws_publish_strategy
iam_role_name = var.aws_master_iam_role_name
use_spot_instance = var.aws_master_use_spot_instance
}

module "iam" {
Expand Down
10 changes: 10 additions & 0 deletions data/data/aws/cluster/master/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,16 @@ resource "aws_instance" "master" {
device_index = 0
}

dynamic "instance_market_options" {
for_each = var.use_spot_instance ? [1] : []
content {
market_type = "spot"
spot_options {
spot_instance_type = "one-time"
}
}
}

lifecycle {
# Ignore changes in the AMI which force recreation of the resource. This
# avoids accidental deletion of nodes whenever a new CoreOS Release comes
Expand Down
5 changes: 5 additions & 0 deletions data/data/aws/cluster/master/variables.tf
Original file line number Diff line number Diff line change
Expand Up @@ -101,3 +101,8 @@ variable "iam_role_name" {
type = string
description = "The name of the existing role to use for the instance profile"
}

variable "use_spot_instance" {
type = bool
description = "Whether to use Spot instances for masters"
}
6 changes: 6 additions & 0 deletions data/data/aws/variables-aws.tf
Original file line number Diff line number Diff line change
Expand Up @@ -239,3 +239,9 @@ EOF

default = ""
}

variable "aws_master_use_spot_instance" {
type = bool
description = "(optional) Whether to use instances from the Spot market for masters"
default = false
}
8 changes: 8 additions & 0 deletions pkg/tfvars/aws/aws.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (
"strings"

"github.com/pkg/errors"
"github.com/sirupsen/logrus"

machinev1beta1 "github.com/openshift/api/machine/v1beta1"
"github.com/openshift/installer/pkg/asset/ignition/bootstrap"
Expand Down Expand Up @@ -50,6 +51,7 @@ type Config struct {
PreserveBootstrapIgnition bool `json:"aws_preserve_bootstrap_ignition"`
MasterSecurityGroups []string `json:"aws_master_security_groups,omitempty"`
PublicIpv4Pool string `json:"aws_public_ipv4_pool"`
MasterUseSpotInstance bool `json:"aws_master_use_spot_instance,omitempty"`
}

// TFVarsSources contains the parameters to be converted into Terraform variables
Expand Down Expand Up @@ -187,6 +189,11 @@ func TFVars(sources TFVarsSources) ([]byte, error) {
return nil, errors.New("EBS IOPS must be configured for the io1 root volume")
}

useSpotInstances := masterConfig.SpotMarketOptions != nil
if useSpotInstances {
logrus.Warn("Found Spot instance configuration. Please be warned, this is not advised.")
}

cfg := &Config{
CustomEndpoints: endpoints,
Region: masterConfig.Placement.Region,
Expand All @@ -211,6 +218,7 @@ func TFVars(sources TFVarsSources) ([]byte, error) {
PreserveBootstrapIgnition: sources.PreserveBootstrapIgnition,
MasterSecurityGroups: sources.MasterSecurityGroups,
PublicIpv4Pool: sources.PublicIpv4Pool,
MasterUseSpotInstance: useSpotInstances,
}

stubIgn, err := bootstrap.GenerateIgnitionShimWithCertBundleAndProxy(sources.IgnitionPresignedURL, sources.AdditionalTrustBundle, sources.Proxy)
Expand Down