diff --git a/README.md b/README.md index 67a7438819..58d1194268 100644 --- a/README.md +++ b/README.md @@ -124,6 +124,7 @@ Join our discord community via [this invite link](https://discord.gg/bxgXW8jJGh) | [create\_service\_linked\_role\_spot](#input\_create\_service\_linked\_role\_spot) | (optional) create the service linked role for spot instances that is required by the scale-up lambda. | `bool` | `false` | no | | [delay\_webhook\_event](#input\_delay\_webhook\_event) | The number of seconds the event accepted by the webhook is invisible on the queue before the scale up lambda will receive the event. | `number` | `30` | no | | [disable\_runner\_autoupdate](#input\_disable\_runner\_autoupdate) | Disable the auto update of the github runner agent. Be aware there is a grace period of 30 days, see also the [GitHub article](https://github.blog/changelog/2022-02-01-github-actions-self-hosted-runners-can-now-disable-automatic-updates/) | `bool` | `false` | no | +| [dynamic\_ec2](#input\_dynamic\_ec2) | Configuration for dynamic EC2 instance types feature. |
object({
    enable_types              = bool
    workflow_label_type_prefix = string
  }) | {
  "enable_types": false,
  "workflow_label_type_prefix": "ghr-ec2-"
} | no |
 |  [enable\_ami\_housekeeper](#input\_enable\_ami\_housekeeper) | Option to disable the lambda to clean up old AMIs. | `bool` | `false` | no |
 |  [enable\_cloudwatch\_agent](#input\_enable\_cloudwatch\_agent) | Enables the cloudwatch agent on the ec2 runner instances. The runner uses a default config that can be overridden via `cloudwatch_config`. | `bool` | `true` | no |
 |  [enable\_ephemeral\_runners](#input\_enable\_ephemeral\_runners) | Enable ephemeral runners, runners will only be used once. | `bool` | `false` | no |
diff --git a/examples/default/.terraform.lock.hcl b/examples/default/.terraform.lock.hcl
index 045fb7350a..dbf28844da 100644
--- a/examples/default/.terraform.lock.hcl
+++ b/examples/default/.terraform.lock.hcl
@@ -2,25 +2,25 @@
 # Manual edits may be lost in future updates.
 
 provider "registry.terraform.io/hashicorp/aws" {
-  version     = "5.82.1"
-  constraints = ">= 5.0.0, ~> 5.0, ~> 5.27"
+  version     = "5.94.1"
+  constraints = ">= 5.0.0, ~> 5.0, ~> 5.27, ~> 5.77"
   hashes = [
-    "h1:QTOtDMehUfiD3wDbbDuXYuTqGgLDkKK9Agkd5NCUEic=",
-    "zh:0fde8533282973f1f5d33b2c4f82d962a2c78860d39b42ac20a9ce399f06f62c",
-    "zh:1fd1a252bffe91668f35be8eac4e0a980f022120254eae1674c3c05049aff88a",
-    "zh:31bbd380cd7d74bf9a8c961fc64da4222bed40ffbdb27b011e637fa8b2d33641",
-    "zh:333ee400cf6f62fa199dc1270bf8efac6ffe56659f86918070b8351b8636e03b",
-    "zh:42ea9fee0a152d344d548eab43583299a13bcd73fae9e53e7e1a708720ac1315",
-    "zh:4b78f25a8cda3316eb56aa01909a403ec2f325a2eb0512c9a73966068c26cf29",
-    "zh:5e9cf9a275eda8f7940a41e32abe0b92ba76b5744def4af5124b343b5f33eb94",
-    "zh:6a46c8630c16b9e1338c2daed6006118db951420108b58b8b886403c69317439",
-    "zh:6efe11cf1a01f98a8d8043cdcd8c0ee5fe93a0e582c2b69ebb73ea073f5068c3",
-    "zh:88ab5c768c7d8133dab94eff48071e764424ad2b7cfeee5abe6d5bb16e4b85c6",
+    "h1:dYdnGlaCJONFyGk/t3Y4iJzQ8EiJr2DaDdZ/2JV5PZU=",
+    "zh:14fb41e50219660d5f02b977e6f786d8ce78766cce8c2f6b8131411b087ae945",
+    "zh:3bc5d12acd5e1a5f1cf78a7f05d0d63f988b57485e7d20c47e80a0b723a99d26",
+    "zh:4835e49377f80a37c6191a092f636e227a9f086e3cc3f0c9e1b554da8793cfe8",
+    "zh:605971275adae25096dca30a94e29931039133c667c1d9b38778a09594312964",
+    "zh:8ae46b4a9a67815facf59da0c56d74ef71bcc77ae79e8bfbac504fa43f267f8e",
+    "zh:913f3f371c3e6d1f040d6284406204b049977c13cb75aae71edb0ef8361da7dd",
+    "zh:91f85ae8c73932547ad7139ce0b047a6a7c7be2fd944e51db13231cc80ce6d8e",
+    "zh:96352ae4323ce137903b9fe879941f894a3ce9ef30df1018a0f29f285a448793",
     "zh:9b12af85486a96aedd8d7984b0ff811a4b42e3d88dad1a3fb4c0b580d04fa425",
-    "zh:a614beb312574342b27dbc34d65b450997f63fa3e948d0d30f441e4f69337380",
-    "zh:c1f486e27130610a9b64cacb0bd928009c433d62b3be515488185e6467b4aa1f",
-    "zh:dccd166e89e1a02e7ce658df3c42d040edec4b09c6f7906aa5743938518148b1",
-    "zh:e75a3ae0fb42b7ea5a0bb5dffd8f8468004c9700fcc934eb04c264fda2ba9984",
+    "zh:9b51922c9201b1dc3d05b39f9972715db5f67297deee088793d02dea1832564b",
+    "zh:a689e82112aa71e15647b06502d5b585980cd9002c3cc8458f092e8c8a667696",
+    "zh:c3723fa3e6aff3c1cc0088bdcb1edee168fe60020f2f77161d135bf473f45ab2",
+    "zh:d6a2052b864dd394b01ad1bae32d0a7d257940ee47908d02df7fa7873981d619",
+    "zh:dda4c9c0406cc54ad8ee4f19173a32de7c6e73abb5a948ea0f342d567df26a1d",
+    "zh:f42e0fe592b97cbdf70612f0fbe2bab851835e2d1aaf8cbb87c3ab0f2c96bb27",
   ]
 }
 
@@ -65,21 +65,21 @@ provider "registry.terraform.io/hashicorp/null" {
 }
 
 provider "registry.terraform.io/hashicorp/random" {
-  version     = "3.6.3"
+  version     = "3.7.1"
   constraints = "~> 3.0"
   hashes = [
-    "h1:zG9uFP8l9u+yGZZvi5Te7PV62j50azpgwPunq2vTm1E=",
-    "zh:04ceb65210251339f07cd4611885d242cd4d0c7306e86dda9785396807c00451",
-    "zh:448f56199f3e99ff75d5c0afacae867ee795e4dfda6cb5f8e3b2a72ec3583dd8",
-    "zh:4b4c11ccfba7319e901df2dac836b1ae8f12185e37249e8d870ee10bb87a13fe",
-    "zh:4fa45c44c0de582c2edb8a2e054f55124520c16a39b2dfc0355929063b6395b1",
-    "zh:588508280501a06259e023b0695f6a18149a3816d259655c424d068982cbdd36",
-    "zh:737c4d99a87d2a4d1ac0a54a73d2cb62974ccb2edbd234f333abd079a32ebc9e",
+    "h1:t152MY0tQH4a8fLzTtEWx70ITd3azVOrFDn/pQblbto=",
+    "zh:3193b89b43bf5805493e290374cdda5132578de6535f8009547c8b5d7a351585",
+    "zh:3218320de4be943e5812ed3de995946056db86eb8d03aa3f074e0c7316599bef",
+    "zh:419861805a37fa443e7d63b69fb3279926ccf98a79d256c422d5d82f0f387d1d",
+    "zh:4df9bd9d839b8fc11a3b8098a604b9b46e2235eb65ef15f4432bde0e175f9ca6",
+    "zh:5814be3f9c9cc39d2955d6f083bae793050d75c572e70ca11ccceb5517ced6b1",
+    "zh:63c6548a06de1231c8ee5570e42ca09c4b3db336578ded39b938f2156f06dd2e",
+    "zh:697e434c6bdee0502cc3deb098263b8dcd63948e8a96d61722811628dce2eba1",
     "zh:78d5eefdd9e494defcb3c68d282b8f96630502cac21d1ea161f53cfe9bb483b3",
-    "zh:a357ab512e5ebc6d1fda1382503109766e21bbfdfaa9ccda43d313c122069b30",
-    "zh:c51bfb15e7d52cc1a2eaec2a903ac2aff15d162c172b1b4c17675190e8147615",
-    "zh:e0951ee6fa9df90433728b96381fb867e3db98f66f735e0c3e24f8f16903f0ad",
-    "zh:e3cdcb4e73740621dabd82ee6a37d6cfce7fee2a03d8074df65086760f5cf556",
-    "zh:eff58323099f1bd9a0bec7cb04f717e7f1b2774c7d612bf7581797e1622613a0",
+    "zh:a0b8e44927e6327852bbfdc9d408d802569367f1e22a95bcdd7181b1c3b07601",
+    "zh:b7d3af018683ef22794eea9c218bc72d7c35a2b3ede9233b69653b3c782ee436",
+    "zh:d63b911d618a6fe446c65bfc21e793a7663e934b2fef833d42d3ccd38dd8d68d",
+    "zh:fa985cd0b11e6d651f47cff3055f0a9fd085ec190b6dbe99bf5448174434cdea",
   ]
 }
diff --git a/examples/default/README.md b/examples/default/README.md
index f3129d71bc..ae5f4230ea 100644
--- a/examples/default/README.md
+++ b/examples/default/README.md
@@ -42,7 +42,7 @@ terraform output -raw webhook_secret
 
 | Name | Version |
 |------|---------|
-|  [random](#provider\_random) | 3.6.3 |
+|  [random](#provider\_random) | 3.7.1 |
 
 ## Modules
 
diff --git a/examples/default/main.tf b/examples/default/main.tf
index 42608fae40..301406f82f 100644
--- a/examples/default/main.tf
+++ b/examples/default/main.tf
@@ -32,6 +32,7 @@ module "runners" {
     webhook_secret = random_id.random.hex
   }
 
+  enable_dynamic_ec2_types = true
   # configure the block device mappings, default for Amazon Linux2
   # block_device_mappings = [{
   #   device_name           = "/dev/xvda"
@@ -98,7 +99,7 @@ module "runners" {
   }
 
   # Enable debug logging for the lambda functions
-  # log_level = "debug"
+  log_level = "debug"
 
   # tracing_config = {
   #   mode                  = "Active"
diff --git a/lambdas/functions/control-plane/src/scale-runners/scale-up.ts b/lambdas/functions/control-plane/src/scale-runners/scale-up.ts
index b7e402e967..6861978269 100644
--- a/lambdas/functions/control-plane/src/scale-runners/scale-up.ts
+++ b/lambdas/functions/control-plane/src/scale-runners/scale-up.ts
@@ -244,7 +244,8 @@ export async function scaleUp(eventSource: string, payload: ActionRequestMessage
   if (eventSource !== 'aws:sqs') throw Error('Cannot handle non-SQS events!');
 
   const dynamicEc2TypesEnabled = yn(process.env.ENABLE_DYNAMIC_EC2_TYPES, { default: false });
-  const requestedInstanceType = payload.labels?.find(label => label.startsWith('ghr-ec2-'))?.replace('ghr-ec2-', '');
+  const labelPrefix = process.env.WORKFLOW_LABEL_TYPE_PREFIX || 'ghr-ec2-';
+  const requestedInstanceType = payload.labels?.find(label => label.startsWith(labelPrefix))?.replace(labelPrefix, '');
 
   if (dynamicEc2TypesEnabled && requestedInstanceType) {
     logger.info(`Dynamic EC2 instance type requested: ${requestedInstanceType}`);
@@ -261,7 +262,7 @@ export async function scaleUp(eventSource: string, payload: ActionRequestMessage
   // Combine configured runner labels with dynamic EC2 instance type label if present
   let runnerLabels = process.env.RUNNER_LABELS || '';
   if (dynamicEc2TypesEnabled && requestedInstanceType) {
-    const ec2Label = `ghr-ec2-${requestedInstanceType}`;
+    const ec2Label = `${labelPrefix}${requestedInstanceType}`;
     runnerLabels = runnerLabels ? `${runnerLabels},${ec2Label}` : ec2Label;
     logger.debug(`Added dynamic EC2 instance type label: ${ec2Label} to runner config.`);
   }
diff --git a/main.tf b/main.tf
index d85153097d..c22c97dca6 100644
--- a/main.tf
+++ b/main.tf
@@ -187,7 +187,7 @@ module "runners" {
   github_app_parameters                = local.github_app_parameters
   enable_organization_runners          = var.enable_organization_runners
   enable_ephemeral_runners             = var.enable_ephemeral_runners
-  enable_dynamic_ec2_types             = var.enable_dynamic_ec2_types
+  dynamic_ec2                          = var.dynamic_ec2
   enable_job_queued_check              = var.enable_job_queued_check
   enable_jit_config                    = var.enable_jit_config
   enable_on_demand_failover_for_errors = var.enable_runner_on_demand_failover_for_errors
diff --git a/modules/multi-runner/README.md b/modules/multi-runner/README.md
index dca32e2662..7391d1fd6d 100644
--- a/modules/multi-runner/README.md
+++ b/modules/multi-runner/README.md
@@ -148,7 +148,7 @@ module "multi-runner" {
 |  [logging\_retention\_in\_days](#input\_logging\_retention\_in\_days) | Specifies the number of days you want to retain log events for the lambda log group. Possible values are: 0, 1, 3, 5, 7, 14, 30, 60, 90, 120, 150, 180, 365, 400, 545, 731, 1827, and 3653. | `number` | `180` | no |
 |  [matcher\_config\_parameter\_store\_tier](#input\_matcher\_config\_parameter\_store\_tier) | The tier of the parameter store for the matcher configuration. Valid values are `Standard`, and `Advanced`. | `string` | `"Standard"` | no |
 |  [metrics](#input\_metrics) | Configuration for metrics created by the module, by default metrics are disabled to avoid additional costs. When metrics are enable all metrics are created unless explicit configured otherwise. | object({
    enable    = optional(bool, false)
    namespace = optional(string, "GitHub Runners")
    metric = optional(object({
      enable_github_app_rate_limit    = optional(bool, true)
      enable_job_retry                = optional(bool, true)
      enable_spot_termination_warning = optional(bool, true)
    }), {})
  }) | `{}` | no |
-|  [multi\_runner\_config](#input\_multi\_runner\_config) | multi\_runner\_config = {map(object({
    runner_config = object({
      runner_os           = string
      runner_architecture = string
      runner_metadata_options = optional(map(any), {
        instance_metadata_tags      = "enabled"
        http_endpoint               = "enabled"
        http_tokens                 = "required"
        http_put_response_hop_limit = 1
      })
      ami_filter                              = optional(map(list(string)), { state = ["available"] })
      ami_owners                              = optional(list(string), ["amazon"])
      ami_id_ssm_parameter_name               = optional(string, null)
      ami_kms_key_arn                         = optional(string, "")
      create_service_linked_role_spot         = optional(bool, false)
      credit_specification                    = optional(string, null)
      delay_webhook_event                     = optional(number, 30)
      disable_runner_autoupdate               = optional(bool, false)
      ebs_optimized                           = optional(bool, false)
      enable_ephemeral_runners                = optional(bool, false)
      enable_job_queued_check                 = optional(bool, null)
      enable_on_demand_failover_for_errors    = optional(list(string), [])
      enable_organization_runners             = optional(bool, false)
      enable_runner_binaries_syncer           = optional(bool, true)
      enable_ssm_on_runners                   = optional(bool, false)
      enable_userdata                         = optional(bool, true)
      instance_allocation_strategy            = optional(string, "lowest-price")
      instance_max_spot_price                 = optional(string, null)
      instance_target_capacity_type           = optional(string, "spot")
      instance_types                          = list(string)
      job_queue_retention_in_seconds          = optional(number, 86400)
      minimum_running_time_in_minutes         = optional(number, null)
      pool_runner_owner                       = optional(string, null)
      runner_as_root                          = optional(bool, false)
      runner_boot_time_in_minutes             = optional(number, 5)
      runner_disable_default_labels           = optional(bool, false)
      runner_extra_labels                     = optional(list(string), [])
      runner_group_name                       = optional(string, "Default")
      runner_name_prefix                      = optional(string, "")
      runner_run_as                           = optional(string, "ec2-user")
      runners_maximum_count                   = number
      runner_additional_security_group_ids    = optional(list(string), [])
      scale_down_schedule_expression          = optional(string, "cron(*/5 * * * ? *)")
      scale_up_reserved_concurrent_executions = optional(number, 1)
      userdata_template                       = optional(string, null)
      userdata_content                        = optional(string, null)
      enable_jit_config                       = optional(bool, null)
      enable_runner_detailed_monitoring       = optional(bool, false)
      enable_cloudwatch_agent                 = optional(bool, true)
      cloudwatch_config                       = optional(string, null)
      userdata_pre_install                    = optional(string, "")
      userdata_post_install                   = optional(string, "")
      runner_hook_job_started                 = optional(string, "")
      runner_hook_job_completed               = optional(string, "")
      runner_ec2_tags                         = optional(map(string), {})
      runner_iam_role_managed_policy_arns     = optional(list(string), [])
      vpc_id                                  = optional(string, null)
      subnet_ids                              = optional(list(string), null)
      idle_config = optional(list(object({
        cron             = string
        timeZone         = string
        idleCount        = number
        evictionStrategy = optional(string, "oldest_first")
      })), [])
      runner_log_files = optional(list(object({
        log_group_name   = string
        prefix_log_group = bool
        file_path        = string
        log_stream_name  = string
      })), null)
      block_device_mappings = optional(list(object({
        delete_on_termination = optional(bool, true)
        device_name           = optional(string, "/dev/xvda")
        encrypted             = optional(bool, true)
        iops                  = optional(number)
        kms_key_id            = optional(string)
        snapshot_id           = optional(string)
        throughput            = optional(number)
        volume_size           = number
        volume_type           = optional(string, "gp3")
        })), [{
        volume_size = 30
      }])
      pool_config = optional(list(object({
        schedule_expression          = string
        schedule_expression_timezone = optional(string)
        size                         = number
      })), [])
      job_retry = optional(object({
        enable             = optional(bool, false)
        delay_in_seconds   = optional(number, 300)
        delay_backoff      = optional(number, 2)
        lambda_memory_size = optional(number, 256)
        lambda_timeout     = optional(number, 30)
        max_attempts       = optional(number, 1)
      }), {})
    })
    matcherConfig = object({
      labelMatchers = list(list(string))
      exactMatch    = optional(bool, false)
      priority      = optional(number, 999)
    })
    redrive_build_queue = optional(object({
      enabled         = bool
      maxReceiveCount = number
      }), {
      enabled         = false
      maxReceiveCount = null
    })
  })) | n/a | yes |
+|  [multi\_runner\_config](#input\_multi\_runner\_config) | multi\_runner\_config = {map(object({
    runner_config = object({
      runner_os           = string
      runner_architecture = string
      runner_metadata_options = optional(map(any), {
        instance_metadata_tags      = "enabled"
        http_endpoint               = "enabled"
        http_tokens                 = "required"
        http_put_response_hop_limit = 1
      })
      ami_filter                              = optional(map(list(string)), { state = ["available"] })
      ami_owners                              = optional(list(string), ["amazon"])
      ami_id_ssm_parameter_name               = optional(string, null)
      ami_kms_key_arn                         = optional(string, "")
      create_service_linked_role_spot         = optional(bool, false)
      credit_specification                    = optional(string, null)
      delay_webhook_event                     = optional(number, 30)
      disable_runner_autoupdate               = optional(bool, false)
      ebs_optimized                           = optional(bool, false)
      enable_ephemeral_runners                = optional(bool, false)
      dynamic_ec2 = optional(object({
        enable_types              = bool
        workflow_label_type_prefix = string
      }), {
        enable_types              = false
        workflow_label_type_prefix = "ghr-ec2-"
      })
      enable_job_queued_check                 = optional(bool, null)
      enable_on_demand_failover_for_errors    = optional(list(string), [])
      enable_organization_runners             = optional(bool, false)
      enable_runner_binaries_syncer           = optional(bool, true)
      enable_ssm_on_runners                   = optional(bool, false)
      enable_userdata                         = optional(bool, true)
      instance_allocation_strategy            = optional(string, "lowest-price")
      instance_max_spot_price                 = optional(string, null)
      instance_target_capacity_type           = optional(string, "spot")
      instance_types                          = list(string)
      job_queue_retention_in_seconds          = optional(number, 86400)
      minimum_running_time_in_minutes         = optional(number, null)
      pool_runner_owner                       = optional(string, null)
      runner_as_root                          = optional(bool, false)
      runner_boot_time_in_minutes             = optional(number, 5)
      runner_disable_default_labels           = optional(bool, false)
      runner_extra_labels                     = optional(list(string), [])
      runner_group_name                       = optional(string, "Default")
      runner_name_prefix                      = optional(string, "")
      runner_run_as                           = optional(string, "ec2-user")
      runners_maximum_count                   = number
      runner_additional_security_group_ids    = optional(list(string), [])
      scale_down_schedule_expression          = optional(string, "cron(*/5 * * * ? *)")
      scale_up_reserved_concurrent_executions = optional(number, 1)
      userdata_template                       = optional(string, null)
      userdata_content                        = optional(string, null)
      enable_jit_config                       = optional(bool, null)
      enable_runner_detailed_monitoring       = optional(bool, false)
      enable_cloudwatch_agent                 = optional(bool, true)
      cloudwatch_config                       = optional(string, null)
      userdata_pre_install                    = optional(string, "")
      userdata_post_install                   = optional(string, "")
      runner_hook_job_started                 = optional(string, "")
      runner_hook_job_completed               = optional(string, "")
      runner_ec2_tags                         = optional(map(string), {})
      runner_iam_role_managed_policy_arns     = optional(list(string), [])
      vpc_id                                  = optional(string, null)
      subnet_ids                              = optional(list(string), null)
      idle_config = optional(list(object({
        cron             = string
        timeZone         = string
        idleCount        = number
        evictionStrategy = optional(string, "oldest_first")
      })), [])
      runner_log_files = optional(list(object({
        log_group_name   = string
        prefix_log_group = bool
        file_path        = string
        log_stream_name  = string
      })), null)
      block_device_mappings = optional(list(object({
        delete_on_termination = optional(bool, true)
        device_name           = optional(string, "/dev/xvda")
        encrypted             = optional(bool, true)
        iops                  = optional(number)
        kms_key_id            = optional(string)
        snapshot_id           = optional(string)
        throughput            = optional(number)
        volume_size           = number
        volume_type           = optional(string, "gp3")
        })), [{
        volume_size = 30
      }])
      pool_config = optional(list(object({
        schedule_expression          = string
        schedule_expression_timezone = optional(string)
        size                         = number
      })), [])
      job_retry = optional(object({
        enable             = optional(bool, false)
        delay_in_seconds   = optional(number, 300)
        delay_backoff      = optional(number, 2)
        lambda_memory_size = optional(number, 256)
        lambda_timeout     = optional(number, 30)
        max_attempts       = optional(number, 1)
      }), {})
    })
    matcherConfig = object({
      labelMatchers = list(list(string))
      exactMatch    = optional(bool, false)
      priority      = optional(number, 999)
    })
    redrive_build_queue = optional(object({
      enabled         = bool
      maxReceiveCount = number
      }), {
      enabled         = false
      maxReceiveCount = null
    })
  })) | n/a | yes |
 |  [pool\_lambda\_reserved\_concurrent\_executions](#input\_pool\_lambda\_reserved\_concurrent\_executions) | Amount of reserved concurrent executions for the scale-up lambda function. A value of 0 disables lambda from being triggered and -1 removes any concurrency limitations. | `number` | `1` | no |
 |  [pool\_lambda\_timeout](#input\_pool\_lambda\_timeout) | Time out for the pool lambda in seconds. | `number` | `60` | no |
 |  [prefix](#input\_prefix) | The prefix used for naming resources | `string` | `"github-actions"` | no |
diff --git a/modules/multi-runner/variables.tf b/modules/multi-runner/variables.tf
index 58ce5d6278..7c2a2f6641 100644
--- a/modules/multi-runner/variables.tf
+++ b/modules/multi-runner/variables.tf
@@ -75,7 +75,13 @@ variable "multi_runner_config" {
       disable_runner_autoupdate               = optional(bool, false)
       ebs_optimized                           = optional(bool, false)
       enable_ephemeral_runners                = optional(bool, false)
-      enable_dynamic_ec2_types                = optional(bool, false)
+      dynamic_ec2 = optional(object({
+        enable_types              = bool
+        workflow_label_type_prefix = string
+      }), {
+        enable_types              = false
+        workflow_label_type_prefix = "ghr-ec2-"
+      })
       enable_job_queued_check                 = optional(bool, null)
       enable_on_demand_failover_for_errors    = optional(list(string), [])
       enable_organization_runners             = optional(bool, false)
@@ -180,7 +186,7 @@ variable "multi_runner_config" {
         disable_runner_autoupdate: "Disable the auto update of the github runner agent. Be aware there is a grace period of 30 days, see also the [GitHub article](https://github.blog/changelog/2022-02-01-github-actions-self-hosted-runners-can-now-disable-automatic-updates/)"
         ebs_optimized: "The EC2 EBS optimized configuration."
         enable_ephemeral_runners: "Enable ephemeral runners, runners will only be used once."
-        enable_dynamic_ec2_types: "Enable dynamic EC2 instance types based on workflow job labels. When enabled, jobs can request specific instance types via the 'gh-ec2-instance-type' label (e.g., 'gh-ec2-t3.large')."
+        dynamic_ec2: "Configuration for dynamic EC2 instance types feature. This object allows you to enable dynamic instance types and configure the label prefix used in workflows."
         enable_job_queued_check: "(Optional) Only scale if the job event received by the scale up lambda is is in the state queued. By default enabled for non ephemeral runners and disabled for ephemeral. Set this variable to overwrite the default behavior."
         enable_on_demand_failover_for_errors: "Enable on-demand failover. For example to fall back to on demand when no spot capacity is available the variable can be set to `InsufficientInstanceCapacity`. When not defined the default behavior is to retry later."
         enable_organization_runners: "Register runners to organization, instead of repo level"
diff --git a/modules/runners/README.md b/modules/runners/README.md
index 2d8e11a0c3..abe0bc5bb0 100644
--- a/modules/runners/README.md
+++ b/modules/runners/README.md
@@ -144,6 +144,7 @@ yarn run dist
 |  [create\_service\_linked\_role\_spot](#input\_create\_service\_linked\_role\_spot) | (optional) create the service linked role for spot instances that is required by the scale-up lambda. | `bool` | `false` | no |
 |  [credit\_specification](#input\_credit\_specification) | The credit option for CPU usage of a T instance. Can be unset, "standard" or "unlimited". | `string` | `null` | no |
 |  [disable\_runner\_autoupdate](#input\_disable\_runner\_autoupdate) | Disable the auto update of the github runner agent. Be aware there is a grace period of 30 days, see also the [GitHub article](https://github.blog/changelog/2022-02-01-github-actions-self-hosted-runners-can-now-disable-automatic-updates/) | `bool` | `false` | no |
+|  [dynamic\_ec2](#input\_dynamic\_ec2) | Configuration for dynamic EC2 instance types feature. | object({
    enable_types              = bool
    workflow_label_type_prefix = string
  }) | {
  "enable_types": false,
  "workflow_label_type_prefix": "ghr-ec2-"
} | no |
 |  [ebs\_optimized](#input\_ebs\_optimized) | The EC2 EBS optimized configuration. | `bool` | `false` | no |
 |  [egress\_rules](#input\_egress\_rules) | List of egress rules for the GitHub runner instances. | list(object({
    cidr_blocks      = list(string)
    ipv6_cidr_blocks = list(string)
    prefix_list_ids  = list(string)
    from_port        = number
    protocol         = string
    security_groups  = list(string)
    self             = bool
    to_port          = number
    description      = string
  })) | [| no | | [enable\_cloudwatch\_agent](#input\_enable\_cloudwatch\_agent) | Enabling the cloudwatch agent on the ec2 runner instances, the runner contains default config. Configuration can be overridden via `cloudwatch_config`. | `bool` | `true` | no | diff --git a/modules/runners/scale-up.tf b/modules/runners/scale-up.tf index 36c062c763..7ac47e073b 100644 --- a/modules/runners/scale-up.tf +++ b/modules/runners/scale-up.tf @@ -28,7 +28,8 @@ resource "aws_lambda_function" "scale_up" { AMI_ID_SSM_PARAMETER_NAME = var.ami_id_ssm_parameter_name DISABLE_RUNNER_AUTOUPDATE = var.disable_runner_autoupdate ENABLE_EPHEMERAL_RUNNERS = var.enable_ephemeral_runners - ENABLE_DYNAMIC_EC2_TYPES = var.enable_dynamic_ec2_types + ENABLE_DYNAMIC_EC2_TYPES = var.dynamic_ec2.enable_types + WORKFLOW_LABEL_TYPE_PREFIX = var.dynamic_ec2.workflow_label_type_prefix ENABLE_JIT_CONFIG = var.enable_jit_config ENABLE_JOB_QUEUED_CHECK = local.enable_job_queued_check ENABLE_METRIC_GITHUB_APP_RATE_LIMIT = var.metrics.enable && var.metrics.metric.enable_github_app_rate_limit diff --git a/modules/runners/variables.tf b/modules/runners/variables.tf index 1127411dfa..103c73f101 100644 --- a/modules/runners/variables.tf +++ b/modules/runners/variables.tf @@ -526,10 +526,16 @@ variable "enable_ephemeral_runners" { default = false } -variable "enable_dynamic_ec2_types" { - description = "Enable dynamic EC2 instance types based on workflow job labels. When enabled, jobs can request specific instance types via the 'gh:ec2:instance-type' label." - type = bool - default = false +variable "dynamic_ec2" { + description = "Configuration for dynamic EC2 instance types feature." + type = object({ + enable_types = bool + workflow_label_type_prefix = string + }) + default = { + enable_types = false + workflow_label_type_prefix = "ghr-ec2-" + } } variable "enable_job_queued_check" { diff --git a/variables.tf b/variables.tf index 14f97af78f..fd43ed052b 100644 --- a/variables.tf +++ b/variables.tf @@ -647,10 +647,16 @@ variable "enable_ephemeral_runners" { default = false } -variable "enable_dynamic_ec2_types" { - description = "Enable dynamic EC2 instance types based on workflow job labels. When enabled, jobs can request specific instance types via the 'gh-ec2-instance-type' label (e.g., 'gh-ec2-t3.large')." - type = bool - default = false +variable "dynamic_ec2" { + description = "Configuration for dynamic EC2 instance types feature." + type = object({ + enable_types = bool + workflow_label_type_prefix = string + }) + default = { + enable_types = false + workflow_label_type_prefix = "ghr-ec2-" + } } variable "enable_job_queued_check" {
{
"cidr_blocks": [
"0.0.0.0/0"
],
"description": null,
"from_port": 0,
"ipv6_cidr_blocks": [
"::/0"
],
"prefix_list_ids": null,
"protocol": "-1",
"security_groups": null,
"self": null,
"to_port": 0
}
]