Application Load Balancer (ALB) module for Yandex.Cloud

Features

  • Create Application Load Balancer and all it components
  • Create managed or self signed CM certificates for ALB on demand
  • Create a DNS record with external ALB IP address
  • Create a security group with default rules and define custom security rules
  • Easy to use in other resources via outputs

ALB definition

First of all, Application Load Balancer requires the following input data:

  1. One or more VPC networks with subnets (you will need to specify network ID, zone names, and subnet IDs).
  2. Security group with all required ingress and egress rules.
  3. Public DNS zone for ALB certificate (for this, you will need public zone ID).
  4. Virtual machine group that will act as a target group.

Next, you need to define a variable that describes all required ALB components:

  • alb_load_balancer : Map of all ALB components, such as target groups, backend groups, HTTP routers, virtual hosts, ALB locations, and ALB listeners.

For ALB TLS listeners, you need to:

  1. Set the create_certificate parameter value to true.
  2. Define the alb_certificates variable with all required certificates.
  3. Specify public_dns_zone_id.
  4. List certificate_ids for specifying uploaded certificates to Certificate Manager as a list of IDs.

As an optional step, you can set a time interval using cert_waiting_timer. This is a timer for waiting until a certificate will be issued by Let's Encrypt.

You can provide self managed certificates as both strings and file names.

NOTES:

  1. alb_load_balancer variable describes parameters for all ALB component in a description section.
  2. Flag create_alb is true by default, so all ALM components will be create by alb_load_balancer definition. If it is false, you should to provide an ID of existing ALB HTTP router to http_router_id variable and define only alb_target_groups, alb_backend_groups and alb_virtual_hosts structures.
  3. alb_backend_group is linked with target groups by two additional variables - target_groups_names_list and existing_target_groups_ids. 3.1. First variable points to a list of target groups names defined in a alb_target_groups variable. These target groups will be created before backend group. 3.2. Second one defines a list of previously created target groups IDs. You should to know it's ID and pass it a list.
  4. ALB components dependencies section describes dependencies between all ALB components.

ALB component dependencies

ALB components are linked together with a name. The components are organized as a three-tier structure:

  • Top tier: Load balancer.
  • Middle tier: ALB listener, which may point to ALB HTTP router and other infrastructure elements.
  • Bottom tier: Target group.

The canary_balancer example shows these dependencies as a nested map of objects, while the example-3-canary example implements this scenario. You could find these examples in the Examples folder.

// this is just a pseudocode example
canary_balancer = {
  canary_listener = {
    canary_http_router = {
      canary-vh-production = {
        canary-bg-production = {
          canary-backend-blue = {
            target-group-prod-blue = {
              targets = []
            }
          },
          canary-backend-green = {
            target-group-prod-green = {
              targets = []
            }
          }
        }
      },
      canary-vh-staging = {
        canary-bg-staging = {
          canary-backend-blue = {
            target-group-stage-blue = {
              targets = []
            }
          },
          canary-backend-green = {
            target-group-stage-green = {
              targets = []
            }
          }
        }
      }
    }
  }
}

ALB load balancer example

This example creates ALB load balancer with two target groups, HTTP and GRPC backend groups, two HTTP routers, virtual hosts for each backend group and ALB listeners with ALB locations.

module "alb" {
  source               = "../../"

  network_id           = "<NETWORK-ID>"
  public_dns_zone_id   = "<PUBLIC_DNS_ZONE_ID>"
  public_dns_zone_name = "<PUBLIC_DNS_ZONE_NAME>"
  
  // ALB load balancer
  alb_load_balancer = {
    name = "load-balancer-test"
    
    alb_target_groups  = {
      "target-group-test" = {
        targets = [
          {
            ip_address = "<INSTANCE-IP>"
            private_ipv4_address = true
          },
          {
            subnet_id  = "<SUBNET-ID-B>"
            ip_address = "<INSTANCE-IP>"
          },
          {
            subnet_id  = "<SUBNET-ID-C>"
            ip_address = "<INSTANCE-IP>"
          }
        ]
      }
    }

    alb_backend_groups          = {
      "http-backend-group-test" = {
        http_backends           = [
          {
            name                       = "http-backend"
            port                       = 8080
            weight                     = 100
            target_groups_names_list   = ["target-group-test"]  // link to target group name from alb_target_groups variable
            //existing_target_groups_ids = ["<EXISTING-TARGET-GROUP-ID-1>", "<EXISTING-TARGET-GROUP-ID-2>"] // link to the list of exsisting target groups ids
            healthcheck = {
              healthcheck_port = 8080
              http_healthcheck = {
                path           = "/"
              }
            }
          }
        ]
      }
    }

    alb_http_routers  = ["http-router-test"]

    alb_virtual_hosts = {
      "virtual-router-test" = {
        http_router_name = "http-router-test"
        authority = ["test.example.com"]
        route = {
          name = "http-virtual-route"
          http_route = {
            http_route_action = {
              backend_group_name = "http-backend-group-test"
            }
          }
        }
      }
    }

    // ALB locations
    alb_locations = [
      {
        zone      = "ru-central1-a"
        subnet_id = "<SUBNET-ID-ZONE-A>"
      },
      {
        zone      = "ru-central1-b"
        subnet_id = "<SUBNET-ID-ZONE-B>"
      },
      {
        zone      = "ru-central1-d"
        subnet_id = "<SUBNET-ID-ZONE-D>"
      }
    ]

    alb_listeners = [
      {
        name = "alb-listener-test"
        endpoint = {
          address = {
            external_ipv4_address = {}
          }
          ports = ["8080"]
        }
        http = {
          handler = {
            http_router_name = "http-router-test"
          }
        }
      }
    ]

    log_options = {
      disable = true
    }
  }
}

ALB components definition examples

alb_load_balancer defines next ALB components:

Target group

alb_target_groups  = {
  "target-group-http" = {
    targets = [
      {
        subnet_id  = "<SUBNET-ID-A>"
        ip_address = "<INSTANCE-IP>"
      },
      {
        ip_address = "<INSTANCE-IP>"
        private_ipv4_address = true
      },
      {
        subnet_id  = "<SUBNET-ID-C>"
        ip_address = "<INSTANCE-IP>"
      }
    ]
  },
  "target-group-stream" = {
    targets = [
      {
        subnet_id  = "<SUBNET-ID-A>"
        ip_address = "<INSTANCE-IP>"
      },
      {
        subnet_id  = "<SUBNET-ID-B>"
        ip_address = "<INSTANCE-IP>"
      }
    ]
  },
  "target-group-grpc" = {
    targets = [
      {
        subnet_id  = "<SUBNET-ID-A>"
        ip_address = "<INSTANCE-IP>"
      },
      {
        subnet_id  = "<SUBNET-ID-B>"
        ip_address = "<INSTANCE-IP>"
      },
      {
        ip_address = "<INSTANCE-IP>"
        private_ipv4_address = true
      }
    ]
  }
}

Backend group

Only one type of backends http_backend or grpc_backend or stream_backend should be specified.

alb_backend_groups  = {
  "http-bg" = {
    http_backends  = [
      {
        name   = "http-backend"
        port   = 80
        weight = 100
        http2  = "true"
        load_balancing_config = {
          panic_threshold = 50
          locality_aware_routing_percent = 50
          mode = "ROUND_ROBIN" // Value: ROUND_ROBIN, RANDOM, LEAST_REQUEST, MAGLEV_HASH
        }
        healthcheck = {
          healthcheck_port = 80
          timeout = "1s"
          interval = "1s"
          interval_jitter_percent = 50
          healthy_threshold = 50
          unhealthy_threshold = 50
          http_healthcheck = {
            host = ""
            path = "/"
            http2 = true
          }
        }
        target_groups_names_list     = ["target-group-http"]  // link to target group name from alb_target_groups variable
        //existing_target_groups_ids = ["<EXISTING-TARGET-GROUP-ID-1>", "<EXISTING-TARGET-GROUP-ID-2>"] // link to the list of exsisting target groups ids
      }
    ]
  },
  "stream-bg" = {
    stream_backends  = [
      {
        name   = "stream-backend"
        port   = 80
        weight = 100
        load_balancing_config = {
          panic_threshold = 50
          locality_aware_routing_percent = 50
          strict_locality = ""
          mode = "ROUND_ROBIN" // Value: ROUND_ROBIN, RANDOM, LEAST_REQUEST, MAGLEV_HASH
        }
        healthcheck = {
          healthcheck_port = 80
          timeout = "1s"
          interval = "1s"
          interval_jitter_percent = 50
          healthy_threshold = 50
          unhealthy_threshold = 50
          stream_healthcheck = {
            send = ""
            receive = ""
          }
        }
        target_groups_names_list     = ["target-group-stream"]  // link to target group name from alb_target_groups variable
        //existing_target_groups_ids = ["<EXISTING-TARGET-GROUP-ID-1>", "<EXISTING-TARGET-GROUP-ID-2>"] // link to the list of exsisting target groups ids
      }
    ]
  },
  "grpc-bg" = {
    grpc_backends  = [
      {
        name   = "grpc-backend"
        port   = 80
        weight = 100
        load_balancing_config = {
          panic_threshold = 50
          locality_aware_routing_percent = 50
          mode = "ROUND_ROBIN" // Value: ROUND_ROBIN, RANDOM, LEAST_REQUEST, MAGLEV_HASH
        }
        healthcheck = {
          healthcheck_port = 80
            timeout = "1s"
            interval = "1s"
            interval_jitter_percent = 50
            healthy_threshold = 50
            unhealthy_threshold = 50
          grpc_healthcheck = {
            service_name = "<grpc-service-name>"
          }
        }
        target_groups_names_list     = ["target-group-grpc"]  // link to target group name from alb_target_groups variable
        //existing_target_groups_ids = ["<EXISTING-TARGET-GROUP-ID-1>", "<EXISTING-TARGET-GROUP-ID-2>"] // link to the list of exsisting target groups ids
      }
    ]
  }
}

HTTP router

This list describes two HTTP routers with default values.

alb_http_routers  = ["http-router-a","http-router-b"]

Virtual host

alb_virtual_hosts = {
  "vhost-a" = {
    http_router_name = "http-router-a"
    authority = ["site-a.example.net"]
    // Only one type of actions append or replace or remove should be specified.
    modify_request_headers = {
      name = "vhost-a-modify-request-headers"
      append = ""
      // replace
      // remove = ""
    }
    modify_response_headers = {
      name = "vhost-a-modify-response-headers"
      append = ""
      // replace
      // remove = ""
    }
    // Exactly one type of actions http_route_action or redirect_action or direct_response_action should be specified.
    route = {
      name = "route-a"
      http_route = {
        http_match = {
          http_method = ["GET"]
          path = "/"
        }
        http_route_action = {
          backend_group_name = "http-bg"  // link to backend group
          timeout = "60s"
          host_rewrite = "<host-rewrite-specifier>"
          prefix_rewrite = "<path-prefix>"
          upgrade_types = ["websocket"]
        }
      }
    }
  },
  "vhost-b" = {
    http_router_name = "http-router-b"
    authority = ["site-b.example.net"]
    route = {
      name = "route-b"
      grpc_route = {
        grpc_match = {
          fqmn = {
            prefix = "/prefix"
          }
        }
        grpc_route_action = {
          backend_group_name = "grpc-bg" // link to backend group
          max_timeout = "60s"
          idle_timeout = "60s"
          host_rewrite = "<host-rewrite-specifier>"
        }
      }
    }
  }
}

ALB Load balancer

ALB load balancer requires two structures - alb_locations and alb_listeners for it's definition.

Default parameters:

  • description - (Optional) A description of the ALB Load Balancer.
  • labels - (Optional) A set of key/value label pairs to assign ALB Load Balancer.
  • region_id - (Optional) ID of the region that the Load Balancer is located at.
  • network_id - (Required) ID of the network that the Load Balancer is located at.
  • security_groups_ids - (Optional) A list of ID's of security groups attached to the Load Balancer.

Mandatory parameters:

  • alb_allocations - (Required) Allocation zones for the Load Balancer instance.
    • alb_locations is using for it's definition
  • listener - (Optional) List of listeners for the Load Balancer.
    • name - (Required) Name of the backend.
    • endpoint - (Required) Network endpoints (addresses and ports) of the listener.
      • address - (Required) One or more addresses to listen on. Exactly one type of addresses external_ipv4_address or internal_ipv4_address or external_ipv6_address should be specified.
        • external_ipv4_address - (Optional) External IPv4 address.
          • address - (Optional) Provided by the client or computed automatically.
        • internal_ipv4_address - (Optional) Internal IPv4 address.
          • address - (Optional) Provided by the client or computed automatically.
          • subnet_id - (Optional) Provided by the client or computed automatically
        • external_ipv6_address - (Optional) External IPv6 address.
          • address - (Optional) Provided by the client or computed automatically.
      • ports - (Required) One or more ports to listen on.
    • http - (Optional) HTTP listener resource.
    • stream - (Optional) Stream listener resource.
    • tls - (Optional) TLS listener resource.

Exactly one listener type: http or tls or stream should be specified.

// ALB locations
alb_locations = [
  {
    zone      = "ru-central1-a"
    subnet_id = "<SUBNET-ID-ZONE-A>"
  },
  {
    zone      = "ru-central1-b"
    subnet_id = "<SUBNET-ID-ZONE-B>"
  },
  {
    zone      = "ru-central1-d"
    subnet_id = "<SUBNET-ID-ZONE-D>"
  }
]

alb_listeners = [
  {
    name = "listener-http"
    endpoint = {
      address = {
        // Exactly one type of addresses external_ipv4_address or internal_ipv4_address or external_ipv6_address should be specified.
        external_ipv4_address = {
          adress = "<ADDRESS>"    // if empty it will be computed automatically
        }
        //internal_ipv4_address = {}
        //external_ipv6_address = {}
      }
      ports = ["80"]
    }
    // Exactly one listener type: http or tls or stream should be specified.
    http = {
      redirects = {
        http_to_https = true
      }
    }
  },
  {
    name = "listener-stream"
    endpoint = {
      address = {
        external_ipv4_address = {}
      }
      ports = ["8081"]
    }
    // Exactly one listener type: http or tls or stream should be specified.
    stream = {
      handler = {
        backend_group_name = "stream-backend" // link to backend group
      }
    }
  },
  {
    name = "listener-https-tls"
    endpoint = {
      address = {
        external_ipv4_address = {}  // if empty it will be computed automatically
      }
      ports = ["443"]
    }
    tls = {
      default_handler = {
        http_handler = {
          http_router_name = "router-default"
        }
        certificate_ids = ["asddj6ugadf43522dfsa"]  // certificate id from Certificate Manager 
      }
      sni_handlers = [
        {
          name = "vhosting-sni-a"
          server_names = ["site-a.example.net"]
          handler = {
            http_handler = {
              http_router_name = "http-router-a"
            }
            cert_name = "certificate-a"
          }
        },
        {
          name = "sni-b"
          server_names = ["site-b.example.net"]
          handler = {
            http_handler = {
              http_router_name = "http-router-b"
            }
            cert_name = "certificate-b" // a name of certificate from `alb_certificates` variable
          }
        }
      ]
    }
  }
]

// Cloud Logging settings
log_options = {
  disable = false
  discard_rule {
    http_code_intervals = ["2XX"]
    discard_percent = 75
  }
}
A common ALB use case is a virtual hosting. Example 2 implements this scenario. 
Example 3 defines a canary (blue-green) deployment scenario.

ALB CM certificates

You can define ALB certificates with the alb_certificates variable. It supports two types of certificates: managed and self signed. A managed certificate is issued by Let's Encrypt, it requires domains list and managed options, such as challenge_type and challenge_count. Self signed certificates can be created on your own, e.g., using the OpenSSL tool.

The ALB module uses the following variables:

  1. create_certificate: Flag that enables or disables a block with a CM certificate.
  2. using_self_signed: Set it to true if you are using a self-signed certificate.
  3. alb_certificates: List of all certificates.
  4. public_dns_zone_id: Public DNS zone ID for issuing certificates with Let's Encrypt.
  5. cert_waiting_timer: Timer for waiting for a certificate issued by Let's

The following examples describe managed and self-signed certificates:

// Managed certificates
module "alb" {
  source              = "../../"
  network_id          = "NETWORK_ID"
  
  create_certificate = true
  using_self_signed  = true
  alb_certificates = [
    {
      name    = "certificate-a"
      domains = ["app-a.example.net"]
      managed = {
        challenge_type  = "DNS_CNAME"
        challenge_count = 1
      }
    },
    {
      name    = "certificate-b"
      domains = ["app-b.example.net"]
      managed = {
        challenge_type  = "DNS_CNAME"
        challenge_count = 1
      }
    }
  ]
  public_dns_zone_id = "PUBLIC_DNS_ZONE_ID"
  cert_waiting_timer = "600s"   // waiting 10 minutes until CM certificates will be ISSUED

  // ...
}

// Self signed certificates
module "alb" {
  source              = "../../"
  network_id          = "NETWORK_ID"
  
  # Certificate Manager
  create_certificate = true
  using_self_signed  = true
  alb_certificates = [
    {
      name    = "certificate-a"
      self_managed = {
        certificate_filename = "site-a/server.crt"
        private_key_filename = "site-a/server.key"
      }
    },
    {
      name    = "certificate-b"
      self_managed = {
        certificate_filename = "site-b/server.crt"
        private_key_filename = "site-b/server.key"
      }
    }
  ]

  // ...
}

How to configure Terraform for Yandex Cloud

  • Install YC CLI
  • Add environment variables for terraform auth in Yandex.Cloud
export YC_TOKEN=$(yc iam create-token)
export YC_CLOUD_ID=$(yc config get cloud-id)
export YC_FOLDER_ID=$(yc config get folder-id)

Requirements

Name Version
terraform >= 1.0.0
random > 3.3
time 0.9.1
yandex >= 0.88.0

Providers

Name Version
random 3.5.1
time 0.9.1
yandex 0.89.0

Modules

No modules.

Resources

Name Type
random_string.unique_id resource
time_sleep.wait_for_cert_will_be_issued resource
yandex_alb_backend_group.backend_group resource
yandex_alb_http_router.http_router resource
yandex_alb_load_balancer.alb_load_balancer resource
yandex_alb_target_group.target_group resource
yandex_alb_virtual_host.virtual_router resource
yandex_cm_certificate.alb_cm_certificate resource
yandex_dns_recordset.alb_cm_certificate_dns_name resource
yandex_dns_recordset.alb_external_ip_dns_name resource
yandex_vpc_security_group.alb_custom_rules_sg resource
yandex_vpc_security_group.alb_main_sg resource
yandex_vpc_security_group_rule.egress_rules resource
yandex_vpc_security_group_rule.ingress_rules resource
yandex_client_config.client data source

Inputs

Name Description Type Default Required
alb_backend_groups_labels Default backend group labels map(string)
{
"created_by": "terraform_yc_module"
}
no
alb_certificates List of maps for ALB certificates.

Notes:
- Use only one type, either managed or self_managed
- Resource creation awaits getting challenges from issue provider.
- Self-managed certificates support only one type of private_key or private_key_lockbox_secret
- You can provide self managed certificates and private keys as both strings and file names.
- All self-signed certificates must be located in <path.module>/content/tls/<your_folder>.
- Self-managed private keys can be read from Lockbox; for this, you need to specify the Lockbox private key secret ID and secret key.

Parameters:
- name
- description
- labels
- domains - a list of domains for this certificate.
- managed:
- challenge_type - (Required) Domain owner-check method. Possible values:
"DNS_CNAME" - you will need to create a CNAME dns record with the specified value. Recommended for fully automated certificate renewal;
"DNS_TXT" - you will need to create a TXT dns record with specified value;
"HTTP" - you will need to place specified value into specified url.
- challenge_count - (Optional). Expected number of challenge count needed to validate certificate.
- self_managed:
- certificate_string - (Required) Certificate as a string with chain.
- private_key_string - (Optional) Private key as a string of certificate.
- certificate_filename - (Required) Certificate filename with chain.
- private_key_filename - (Optional) Private key filename of certificate.
- private_key_lockbox_secret - (Optional) Lockbox secret specification for getting private key.
- private_key_lockbox_secret_id
- private_key_lockbox_secret_key
any {} no
alb_certificates_labels Default certificates labels map(string)
{
"created_by": "terraform_yc_module"
}
no
alb_http_routers_labels Default ALB HTTP Routers labels map(string)
{
"created_by": "terraform_yc_module"
}
no
alb_load_balancer ALB load balancer map that defines all required resources for target groups, backend groups, HTTP routers, virtual hosts and alb load balancer.

Required components:
1. Target groups
2. Backend groups
3. HTTP routers
4. Virtual hosts
5. Load balancer

1. Target groups

A map of maps for each target group

Parameters:
- targets - a list of targets
- ip_address - (Required) IP address of the target.
- subnet_id - (Required) ID of the subnet that targets are connected to. All targets in the target group must be connected to the same subnet within a single availability zone.
- private_ipv4_address - (Optional) Boolean. If it is True, ip_address is only required parameter, subnet_id needs to be omited.

Example:
alb_target_groups  = {
"target-group-1" = {
targets = [
{
subnet_id = "e9b5udt8asf9r9qn6nf6"
ip_address = "10.128.0.1"
},
{
subnet_id = "e2lu07tr481h35012c8p"
ip_address = "10.129.0.1"
},
{
ip_address = "10.130.0.1"
private_ipv4_address = true
}
]
}
}
2. Backend groups

A map for maps for each Backend group

Parameters:
- name - Name of the Backend Group.
- labels - Labels to assign to this backend group.
- backend
- http_backend - (Optional) Http backend specification that will be used by the ALB Backend Group.
- grpc_backend - (Optional) Grpc backend specification that will be used by the ALB Backend Group.
- stream_backend - (Optional) Stream backend specification that will be used by the ALB Backend Group.

Backend parameters:
- name - (Required) Name of the backend.
- port - (Optional) Port for incoming traffic.
- weight - (Optional) Weight of the backend. Traffic will be split between backends of the same BackendGroup according to their weights.
- http2 - (Optional) Enables HTTP2 for upstream requests. If not set, HTTP 1.1 will be used by default.
- target_group_ids - (Required) References target groups for the backend.
- load_balancing_config - (Optional) Load Balancing Config specification that will be used by this backend.
- panic_threshold - (Optional) If percentage of healthy hosts in the backend is lower than panic_threshold, traffic will be routed to all backends no matter what the health status is. This helps to avoid healthy backends overloading when everything is bad. Zero means no panic threshold.
- locality_aware_routing_percent - (Optional) Percent of traffic to be sent to the same availability zone. The rest will be equally divided between other zones.
- strict_locality - (Optional) If set, will route requests only to the same availability zone. Balancer won't know about endpoints in other zones.
- mode - (Optional) Load balancing mode for the backend. Possible values: "ROUND_ROBIN", "RANDOM", "LEAST_REQUEST", "MAGLEV_HASH".
- healthcheck - (Optional) Healthcheck specification that will be used by this backend.
- timeout - (Required) Time to wait for a health check response.
- interval - (Required) Interval between health checks.
- interval_jitter_percent - (Optional) An optional jitter amount as a percentage of interval. If specified, during every interval value of (interval_ms * interval_jitter_percent / 100) will be added to the wait time.
- healthy_threshold - (Optional) Number of consecutive successful health checks required to promote endpoint into the healthy state. 0 means 1. Note that during startup, only a single successful health check is required to mark a host healthy.
- unhealthy_threshold - (Optional) Number of consecutive failed health checks required to demote endpoint into the unhealthy state. 0 means 1. Note that for HTTP health checks, a single 503 immediately makes endpoint unhealthy.
- healthcheck_port - (Optional) Optional alternative port for health checking.
- stream_healthcheck - (Optional) Stream Healthcheck specification that will be used by this healthcheck. Structure is documented below.
- send - (Optional) Message sent to targets during TCP data transfer. If not specified, no data is sent to the target.
- receive - (Optional) Data that must be contained in the messages received from targets for a successful health check. If not specified, no messages are expected from targets, and those that are received are not checked.
- http_healthcheck - (Optional) Http Healthcheck specification that will be used by this healthcheck. Structure is documented below.
- host - (Optional) "Host" HTTP header value.
- path - (Required) HTTP path.
- http2 - (Optional) If set, health checks will use HTTP2.
- grpc_healthcheck - (Optional) Grpc Healthcheck specification that will be used by this healthcheck. Structure is documented below.
- service_name - (Optional) Service name for grpc.health.v1.HealthCheckRequest message.
- tls - (Optional) Tls specification that will be used by this backend.
- sni - (Optional) SNI string for TLS connections.
- validation_context.0.trusted_ca_id - (Optional) Trusted CA certificate ID in the Certificate Manager.
- validation_context.0.trusted_ca_bytes - (Optional) PEM-encoded trusted CA certificate chain.

Notes:
1. Only one type of backends http_backend or grpc_backend or stream_backend should be specified.
2. Only one of validation_context.0.trusted_ca_id or validation_context.0.trusted_ca_bytes should be specified.
3. Only one of stream_healthcheck or http_healthcheck or grpc_healthcheck should be specified.

How backend group is linked with target group:
1. First of all, target_groups_names_list variable is a list of target groups names from alb_target_groups variable. These target groups will be created before backend group!
2. Second, existing_target_groups_ids variable is a list of existing target groups IDs. Use it if you want to link backend group with an existing target groups.

Example:
alb_backend_groups         = {
"test-bg-a" = {
http_backends = [
{
name = "bg-a"
port = 80
weight = 100
healthcheck = {
healthcheck_port = 80
http_healthcheck = {
path = "/"
}
}
//
target_groups_names_list = ["tg-a"]
//existing_target_groups_ids = ["", "TG2-ID"]
}
]
},
"test-bg-b" = {
http_backends = [
{
name = "bg-b"
port = 80
weight = 100
healthcheck = {
healthcheck_port = 80
http_healthcheck = {
path = "/"
}
}
target_groups_names_list = ["tg-b"]
//existing_target_groups_ids = ["", "TG2-ID"]
}
]
}
}
3. HTTP routers

A list of HTTP routers names

Example:
alb_http_routers  = ["http-router-1", "http-router-2"]
4. Virtual hosts

ALB virtual hosts map of maps.
ALB virtual host support only two types of routes - HTTP and GRPC. Stream is not supported!

Parameters:
- name - Name of a specific ALB virtual router.
- http_router_id - (Required) The ID of the HTTP router to which the virtual host belongs.
- authority - (Optional) A list of domains (host/authority header) that will be matched to this virtual host.
Wildcard hosts are supported in the form of '.foo.com' or '-bar.foo.com'.
If not specified, all domains will be matched.
- modify_request_headers OR modify_response_headers - Apply the following modifications to the request or response headers.
- name - (Required) name of the header to modify.
- append - (Optional) Append string to the header value.
- replace - (Optional) New value for a header. Header values support the following formatters.
- remove - (Optional) If set, remove the header.
- route - (Optional) A Route resource. Routes are matched in-order.
Be careful when adding them to the end. For instance, having http '/' match first makes all other routes unused.
- name - (Required) name of the route.
- http_route - (Optional) HTTP route resource.
- http_match - (Optional) Checks "/" prefix by default.
- http_method - (Optional) List of methods(strings).
- path - (Optional) If not set, '/' is assumed.
- exact - (Optional) Match exactly.
- prefix - (Optional) Match prefix.
- regex - (Optional) Match regex.
- http_route_action - (Optional) HTTP route action resource.
- backend_group_id - (Required) Backend group to route requests.
- timeout - (Optional) Specifies the request timeout (overall time request processing is allowed to take) for the route. If not set, default is 60 seconds.
- idle_timeout - (Optional) Specifies the idle timeout (time without any data transfer for the active request) for the route. It is useful for streaming scenarios (i.e. long-polling, server-sent events) - one should set idle_timeout to something meaningful and timeout to the maximum time the stream is allowed to be alive. If not specified, there is no per-route idle timeout.
- host_rewrite - (Optional) Host rewrite specifier.
- auto_host_rewrite - (Optional) If set, will automatically rewrite host.
- prefix_rewrite - (Optional) If not empty, matched path prefix will be replaced by this value.
- upgrade_types - (Optional) List of upgrade types. Only specified upgrade types will be allowed. For example, "websocket".
- redirect_action - (Optional) Redirect action resource.
- replace_scheme - (Optional) Replaces scheme. If the original scheme is http or https, will also remove the 80 or 443 port, if present.
- replace_host - (Optional) Replaces hostname.
- replace_port - (Optional) Replaces port.
- replace_path - (Optional) Replace path.
- replace_prefix - (Optional) Replace only matched prefix.
Example: match:{ prefx_match: "/some" }
redirect: { replace_prefix: "/other" }
will redirect "/something" to "/otherthing".
- remove query - (Optional) If set, remove query part.
- response_code - (Optional) The HTTP status code to use in the redirect response. Supported values are: moved_permanently, found, see_other, temporary_redirect, permanent_redirect.
- direct_response_action - (Required) Direct response action resource.
- status - (Optional) HTTP response status. Should be between 100 and 599.
- body - (Optional) Response body text.
- grpc_route - (Optional) GRPC route resource.
- grpc_match - (Optional) Checks "/" prefix by default.
- fqmn - (Optional) If not set, all services/methods are assumed.
- exact - (Optional) Match exactly.
- prefix - (Optional) Match prefix.
- regex - (Optional) Match regex.
- grpc_route_action - (Optional) GRPC route action resource.
- backend_group_id - (Required) Backend group to route requests.
- max_timeout - (Optional) Lower timeout may be specified by the client (using grpc-timeout header). If not set, default is 60 seconds.
- idle_timeout - (Optional) Specifies the idle timeout (time without any data transfer for the active request) for the route. It is useful for streaming scenarios - one should set idle_timeout to something meaningful and max_timeout to the maximum time the stream is allowed to be alive. If not specified, there is no per-route idle timeout.
- host_rewrite - (Optional) Host rewrite specifier.
- auto_host_rewrite - (Optional) If set, will automatically rewrite host.
- grpc_status_response_action - (Required) GRPC status response action resource.
- status - (Optional) The status of the response. Supported values are: ok, invalid_argumet, not_found, permission_denied, unauthenticated, unimplemented, internal, unavailable.

Notes:
- Exactly one listener type: http or tls or stream should be specified.
- Exactly one type of addresses external_ipv4_address or internal_ipv4_address or external_ipv6_address should be specified.
- Only one type of HTTP protocol settings http2_options or allow_http10 should be specified.
- For modify_request_headers OR modify_response_headers only one type of actions 'append' or 'replace' or 'remove' should be specified.
- Exactly one type of actions http_route_action or redirect_action or direct_response_action should be specified.
- Only one type of host rewrite specifiers host_rewrite or auto_host_rewrite should be specified.
- Only one type of paths replace_path or replace_prefix should be specified.
- Exactly one type of actions grpc_route_action or grpc_status_response_action should be specified.
- Only one type of host rewrite specifiers host_rewrite or auto_host_rewrite should be specified.
- Exactly one type of string matches exact, prefix or regex should be specified.

How virtual host is linked with HTTP router and Backend group?
1. http_router_name variable is a link to HTTP router name.
2. backend_group_name variable is a link to Backend group.

Example:
alb_virtual_hosts = {
"virtual-router-1" = {
http_router_name = "http-router-1"
route = {
name = "http-virtual-route"
http_route = {
http_route_action = {
backend_group_name = "http-backend-group-1"
}
}
}
}
}
5. ALB load balancer

Default parameters:
- description - (Optional) A description of the ALB Load Balancer.
- labels - (Optional) A set of key/value label pairs to assign ALB Load Balancer.
- region_id - (Optional) ID of the region that the Load Balancer is located at.
- network_id - (Required) ID of the network that the Load Balancer is located at.
- security_groups_ids - (Optional) A list of ID's of security groups attached to the Load Balancer.

All supported parameters:
- alb_locations - (Required) Allocation zones for the Load Balancer instance.
- zone - (Required) ID of the zone that location is located at.
- subnet_id - (Required) ID of the subnet that location is located at.
- disable_traffic - (Optional) If set, will disable all L7 instances in the zone for request handling.
- listener - (Optional) List of listeners for the Load Balancer.
- name - (Required) Name of the backend.
- endpoint - (Required) Network endpoints (addresses and ports) of the listener.
- address - (Required) One or more addresses to listen on.
- external_ipv4_address - (Optional) External IPv4 address.
- address - (Optional) Provided by the client or computed automatically.
- internal_ipv4_address - (Optional) Internal IPv4 address.
- address - (Optional) Provided by the client or computed automatically.
- subnet_id - (Optional) Provided by the client or computed automatically
- external_ipv6_address - (Optional) External IPv6 address.
- address - (Optional) Provided by the client or computed automatically.
- ports - (Required) One or more ports to listen on.
- http - (Optional) HTTP listener resource. Note: Only one type of fields handler or redirects should be specified.
- handler - (Optional) HTTP handler that sets plaintext HTTP router. The structure is documented below.
- http_router_id - (Optional) HTTP router id.
- rewrite_request_id - (Optional) When unset, will preserve the incoming x-request-id header, otherwise would rewrite it with a new value.
- http2_options - (Optional) If set, will enable HTTP2 protocol for the handler.
- max_concurrent_streams - (Optional) Maximum number of concurrent streams.
- allow_http10 - (Optional) If set, will enable only HTTP1 protocol with HTTP1.0 support.
- redirects - (Optional) Shortcut for adding http -> https redirects.
- http_to_https - (Optional) If set redirects all unencrypted HTTP requests to the same URI with scheme changed to https.
- stream - (Optional) Stream listener resource.
- handler - (Optional) Stream handler that sets plaintext Stream backend group.
- backend_group_id - (Optional) Backend group id.
- tls - (Optional) TLS listener resource.
- default_handler - (Required) TLS handler resource.
- http_handler - (Required) HTTP handler resource.
- http_router_id - (Optional) HTTP router id.
- rewrite_request_id - (Optional) When unset, will preserve the incoming x-request-id header, otherwise would rewrite it with a new value.
- http2_options - (Optional) If set, will enable HTTP2 protocol for the handler.
- max_concurrent_streams - (Optional) Maximum number of concurrent streams.
- allow_http10 - (Optional) If set, will enable only HTTP1 protocol with HTTP1.0 support.
- stream_handler - (Required) Stream handler resource.
- backend_group_id - (Optional) Backend group id.
- certificate_ids - (Required) Certificate IDs in the Certificate Manager. Multiple TLS certificates can be associated with the same context to allow both RSA and ECDSA certificates. Only the first certificate of each type will be used.
- sni_handler - (Optional) SNI match resource.
- name - (Required) name of SNI match.
- server_names - (Required) A set of server names.
- handler - (Required) TLS handler resource.
- http_handler - (Required) HTTP handler resource. The structure is documented below.
- stream_handler - (Required) Stream handler resource. The structure is documented below.
- certificate_ids - (Required) Certificate IDs in the Certificate Manager. Multiple TLS certificates can be associated with the same context to allow both RSA and ECDSA certificates. Only the first certificate of each type will be used.
- log_options - (Optional) Cloud Logging settings.
- disable (Optional) Set to true to disable Cloud Logging for the balancer
- log_group_id (Optional) Cloud Logging group ID to send logs to. Leave empty to use the balancer folder default log group.
- discard_rule (Optional) List of rules to discard a fraction of logs.
- http_codes (Optional) list of http codes 100-599
- http_code_intervals (Optional) list of http code intervals 1XX-5XX or ALL
- grpc_codes (Optional) list of grpc codes by name, e.g, ["NOT_FOUND", "RESOURCE_EXHAUSTED"]

Notes:
1. Exactly one listener type: http or tls or stream should be specified.
2. sni_handler is a list of SNI handlers.
3. if create_certificate = true, certificate should be passed as a name of newly created certificates or as a list of previously created CM certificate ids.

How ALB load balancers is linked with HTTP router and Backend group?
1. http_router_name variable is a link to HTTP router name.
2. backend_group_name variable is a link to Backend group.

ALB TLS certificate could be passed by:
1. certificate_ids variable, it is a list of already created certificate ids
2. cert_name variable is a name for ONLY ONE certificate from alb_certificates list!

Example:
alb_locations = [
{
zone = "ru-central1-a"
subnet_id = ""
},
{
zone = "ru-central1-b"
subnet_id = ""
},
{
zone = "ru-central1-d"
subnet_id = ""
}
]

alb_listeners = [
{
name = "listener-http"
endpoint = {
address = {
external_ipv4_address = {}
}
ports = ["80"]
}
http = {
redirects = {
http_to_https = true
}
}
},
{
name = "listener-https"
endpoint = {
address = {
external_ipv4_address = {}
}
ports = ["443"]
}
tls = {
default_handler = {
http_handler = {
http_router_name = ""
}
cert_name = "" // a name of CM certificate
}
sni_handlers = [
{
name = "sni-a"
server_names = ["site-a.example.net"]
handler = {
http_handler = {
http_router_name = ""
}
cert_name = ""
}
},
{
name = "vhosting-sni-b"
server_names = ["site-b.example.net"]
handler = {
http_handler = {
http_router_name = ""
}
cert_name = ""
}
}
]
}
}
]

log_options = {
disable = true
}
any n/a yes
alb_load_balancer_labels Default ALB Load Balancer labels map(string)
{
"created_by": "terraform_yc_module"
}
no
alb_target_group_labels Default target group labels map(string)
{
"created_by": "terraform_yc_module"
}
no
allowed_ips List of allowed IPv4 CIDR blocks list(string)
[
"0.0.0.0/0"
]
no
cert_waiting_timer A timer value for waiting until ALB TLS certificate will be ISSUED. string "300s" no
create_alb Flag for enabling or disabling ALB load balancer creation bool true no
create_certificate Flag for enabling / disabling creation of a CM certificates and DNS name for it. bool false no
custom_egress_rules A map definition of custom security egress rules.

Example:
custom_egress_rules = {
"rule1" = {
protocol = "ANY"
description = "rule-1"
v4_cidr_blocks = ["10.0.1.0/24", "10.0.2.0/24"]
from_port = 8090
to_port = 8099
},
"rule2" = {
protocol = "UDP"
description = "rule-2"
v4_cidr_blocks = ["10.0.1.0/24"]
from_port = 8090
to_port = 8099
}
}
any {} no
custom_ingress_rules A map definition of custom security ingress rules.

Example:
custom_ingress_rules = {
"rule1" = {
protocol = "TCP"
description = "rule-1"
v4_cidr_blocks = ["0.0.0.0/0"]
from_port = 3000
to_port = 32767
},
"rule2" = {
protocol = "TCP"
description = "rule-2"
v4_cidr_blocks = ["0.0.0.0/0"]
port = 443
},
"rule3" = {
protocol = "TCP"
description = "rule-3"
predefined_target = "self_security_group"
from_port = 0
to_port = 65535
}
}
any {} no
enable_default_rules Controls creation of default security rules.

Default security rules:
- allows all outgoing traffic. Nodes can connect to Yandex Container Registry, Yandex Object Storage, Docker Hub, and so on
- allow access to ALB via port 80
- allow access to ALB via port 443
- allows availability checks from load balancer's address range
bool true no
folder_id ID of the folder to which the resource belongs. If omitted, the provider folder is used string null no
http_router_id If flag create_alb is False, you need to specify ID of existing ALB HTTP router. string null no
network_id ID of the network that the Load Balancer is located at string n/a yes
public_dns_zone_id Public DNS zone ID for ALB CM certificates.
As a default value is specified a PLACEHOLDER, changed it to a valid DNS zone ID.
string "<PUBLIC_DNS_ZONE_ID>" no
public_dns_zone_name Public DNS zone name
As a default value is specified a PLACEHOLDER, changed it to a valid DNS zone name.
string "<PUBLIC_DNS_ZONE_NAME>" no
security_groups_ids_list List of security group IDs to which the ALB belongs list(string) [] no
timeouts Target group timeouts map(string)
{
"create": "15m",
"delete": "15m",
"update": "15m"
}
no
tls_cert_path Relative path to self signed ALB TLS certificate according module.path. string "content/tls" no
traffic_disabled If set, will disable all L7 instances in the zone for request handling. bool false no
using_self_signed This flag indicates that self signed certificate is using. bool false no

Outputs

Name Description
alb_backend_group_ids ALB backend group IDs
alb_backend_group_names ALB backend group names
alb_dns_record_cname ALB DNS record with external IP address
alb_http_router_ids ALB HTTP router IDs
alb_http_router_names ALB HTTP routers names
alb_load_balancer_id ALB ID
alb_load_balancer_name ALB name
alb_load_balancer_public_ips ALB public IPs
alb_target_group_ids ALB target group IDs
alb_target_group_names ALB target group names
alb_virtual_host_ids ALB virtual router IDs
alb_virtual_host_names ALB virtual hosts names