Use the Conformity Knowledge Base AI to help improve your Cloud Posture

Web-Tier ELBs Health Check

Trend Cloud One™ – Conformity is a continuous assurance tool that provides peace of mind for your cloud infrastructure, delivering over 1000 automated best practice checks.

Risk Level: High (not acceptable risk)
Rule ID: ELB-021

Ensure that your web-tier Classic Load Balancer is using the appropriate health check configuration in order to monitor the availability of the EC2 instances associated with the load balancer through application layer. An application layer health check is an HTTP-based test performed periodically to determine the availability of the EC2 instances registered to the load balancer. The status of the backend instances that are healthy at the time of the health check is "InService" and the status of the instances that are unhealthy at the time of the health check is "OutOfService". When a load balancer determines that a backend EC2 instance is unhealthy, it stops routing requests to that instance. The load balancer resumes routing requests to the backend instance when it has been restored to a healthy state. This conformity rule assumes that all the AWS cloud resources created within your web tier are tagged with <web_tier_tag>:<web_tier_tag_value>, where <web_tier_tag> represents the tag name and <web_tier_tag_value> represents the tag value. Before running this rule by the Trend Cloud One™ – Conformity engine, the web-tier tags must be configured in the rule settings, on your Conformity account console.

This rule resolution is part of the Conformity Security & Compliance tool for AWS.

Reliability

Improve the reliability of the applications behind your web-tier Classic Load Balancer by using the right health check configuration. Always use application layer health checks instead of TCP health checks (where a specified TCP port is probed to make sure it is accepting connections) for your web-tier Classic Load Balancer.

Note: Make sure that you replace all <web_tier_tag>:<web_tier_tag_value> tag placeholders outlined in the conformity rule content with your own tag set created for the web tier.


Audit

To determine if your web-tier Classic Load Balancers are using the right health check configuration, perform the following actions:

Using AWS Console

01 Sign in to your Trend Cloud One™ – Conformity account, access Configure Health Check for Web-Tier Load Balancers conformity rule settings, and copy the tag set defined for the AWS cloud resources available within your web tier (e.g. <web_tier_tag>:<web_tier_tag_value>).

02 Sign in to the AWS Management Console.

03 Navigate to Amazon EC2 console at https://console.aws.amazon.com/ec2/v2/.

04 In the main navigation panel, under Load Balancing, choose Load Balancers.

05 Click inside the Filter by tags and attributes or search by keyword box, select Type and choose classic to list the Classic Load Balancers available in the current AWS region.

06 Paste the tag set copied at step no. 1 in the Filter by tags and attributes or search by keyword box, add a space before and after the separation colon (i.e. <web_tier_tag> : <web_tier_tag_value>), then press Enter. This filtering technique will return only the load balancers tagged for the web tier. If no results are returned by the console, there are no Classic Load Balancers tagged within your web tier and the Audit process ends here. If the Amazon EC2 console returns one or more load balancers, continue the Audit with the next step.

07 Select the web-tier Classic Load Balancer that you want to examine.

08 Select the Health Check tab from the console bottom panel and verify the health check configuration parameters available for the selected load balancer. If the ping protocol used by the load balancer is TCP or SSL, i.e. the Ping Target attribute is set to TCP:<port-number> or SSL:<port-number>, the health check configuration set for the selected Classic Load Balancer is not using HTTP-based checks (i.e. health checks performed at application level) to determine the health of the registered instances, therefore the existing health check configuration is not suitable for a web-tier load balancer.

09 Repeat steps no. 7 and 8 for each web-tier Classic Load Balancer provisioned within the current AWS region.

10 Change the AWS cloud region from the console navigation bar and repeat the Audit process for other regions.

Using AWS CLI

01 Sign in to your Trend Cloud One™ – Conformity account, access Configure Health Check for Web-Tier Load Balancers conformity rule settings, and copy the tag set defined for the AWS cloud resources available within your web tier (e.g. <web_tier_tag>:<web_tier_tag_value>).

02 Run describe-load-balancers command (OSX/Linux/UNIX) with custom query filters to list the name of each Classic Load Balancer available in the selected AWS region:

aws elb describe-load-balancers
  --region us-east-1
  --query 'LoadBalancerDescriptions[*].LoadBalancerName'

03 The command output should return an array with the requested load balancer name(s):

[
    "cc-frontend-load-balancer",
    "cc-project5-load-balancer"
]

04 Run describe-tags command (OSX/Linux/UNIX) using the name of the Classic Load Balancer that you want to examine as the identifier parameter and custom query filters to describe the tag sets defined for the selected load balancer:

aws elb describe-tags
  --region us-east-1
  --load-balancer-name cc-frontend-load-balancer
  --query 'TagDescriptions[*].Tags[]'

05 The describe-tags command request should return one of the following outputs:

  1. If the command output returns an empty array (i.e. []), as shown in the example below, the verified Classic Load Balancer is not tagged at all, therefore the Audit process for the selected resource ends here:
    []
    
  2. If the describe-tags command output returns a tag set that is different from the one defined for your web/app/data tier, as shown in the example below, the verified load balancer is not a component of the web/app/data tier, therefore the Audit process for the selected resource ends here:
    [
        {
            "Value": "Role",
            "Key": "Front-End"
        }
    ]
    
  3. If the tag set returned by the describe-tags command output reveals that the selected load balancer is a component of a web tier, as shown in the example below, the Audit process continues with the next step:
    [
        {
            "Key": "<web_tier_tag>",
            "Value": "<web_tier_tag_value>"
        }
    ]
    

06 Run describe-load-balancers command (OSX/Linux/UNIX) using the name of the web-tier load balancer that you want to examine as the identifier parameter, to describe the configuration of the health checks conducted on the selected load balancer:

aws elb describe-load-balancers
  --region us-east-1
  --load-balancer-name cc-frontend-load-balancer
  --query 'LoadBalancerDescriptions[*].{HealthCheck:HealthCheck}'

07 The command output should return the requested configuration information:

[
    {
        "HealthCheck": {
            "Target": "TCP:80",
            "Interval": 30,
            "Timeout": 5,
            "UnhealthyThreshold": 2,
            "HealthyThreshold": 10
        }
    }
]

Check the health check configuration details returned by the describe-load-balancer-policies command output. If the ping protocol used by the load balancer is either TCP or SSL, i.e. the "Target" property is set to "TCP:<port_number>" or "SSL:<port_number>", as shown in the output example above, the health check configuration set for the selected Classic Load Balancer is not using HTTP-based checks to determine the health of the registered instances, therefore the current health check configuration is not appropriate for a web-tier load balancer.

08 Repeat steps no. 6 and 7 for each web-tier Classic Load Balancer provisioned in the selected AWS region.

09 Change the AWS cloud region by updating the --region command parameter value and repeat the Audit process for other regions.

Remediation / Resolution

To reconfigure your web-tier Classic Load Balancer in order to use application layer health checks instead of TCP health checks, perform the following operations:

Using AWS CloudFormation

01 CloudFormation template (JSON):

{
  "AWSTemplateFormatVersion": "2010-09-09",
  "Description": "Configure Health Check for Web-Tier Classic Load Balancer",
  "Resources": {
    "ClassicLoadBalancer": {
      "Type" : "AWS::ElasticLoadBalancing::LoadBalancer",
      "Properties" : {
        "LoadBalancerName" : "cc-frontend-load-balancer",
        "Scheme" : "internet-facing",
        "SecurityGroups" : [ "sg-0abcdabcdabcdabcd" ],
        "Subnets" : [ "subnet-0abcd1234abcd1234", "subnet-0abcdabcdabcdabcd", "subnet-01234abcd1234abcd", "subnet-01234123412341234" ],
        "Instances" : [ "i-0abcd1234abcd1234", "i-0abcdabcdabcdabcd" ],
        "Listeners": [{
            "InstancePort": "80",
            "InstanceProtocol": "HTTP",
            "LoadBalancerPort": "443",
            "Protocol": "HTTPS",
            "PolicyNames": [ "cc-secure-negotiation-policy" ],
            "SSLCertificateId": "arn:aws:acm:us-east-1:123456789012:certificate/abcd1234-abcd-1234-abcd-1234abcd1234"
        }],
        "Policies": [{
            "PolicyName": "cc-secure-negotiation-policy",
            "PolicyType": "SSLNegotiationPolicyType",
            "Attributes": [{
                "Name": "Reference-Security-Policy",
                "Value": "ELBSecurityPolicy-TLS-1-2-2017-01"
            }]
        }],
        "HealthCheck": {
            "Target": "HTTP:80/index.html",
            "HealthyThreshold": "10",
            "UnhealthyThreshold": "2",
            "Interval": "30",
            "Timeout": "5"
        },
        "Tags" : [{
           "Key" : "<web_tier_tag>",
           "Value" : "<web_tier_tag_value>"
        }]
      }
    }
  }
}

02 CloudFormation template (YAML):

AWSTemplateFormatVersion: '2010-09-09'
Description: Configure Health Check for Web-Tier Classic Load Balancer
Resources:
  ClassicLoadBalancer:
    Type: AWS::ElasticLoadBalancing::LoadBalancer
    Properties:
      LoadBalancerName: cc-frontend-load-balancer
      Scheme: internet-facing
      SecurityGroups:
        - sg-0abcdabcdabcdabcd
      Subnets:
        - subnet-0abcd1234abcd1234
        - subnet-0abcdabcdabcdabcd
        - subnet-01234abcd1234abcd
        - subnet-01234123412341234
      Instances:
        - i-0abcd1234abcd1234
        - i-0abcdabcdabcdabcd
      Listeners:
        - InstancePort: '80'
          InstanceProtocol: HTTP
          LoadBalancerPort: '443'
          Protocol: HTTPS
          PolicyNames:
            - cc-secure-negotiation-policy
          SSLCertificateId: arn:aws:acm:us-east-1:123456789012:certificate/abcd1234-abcd-1234-abcd-1234abcd1234
      Policies:
        - PolicyName: cc-secure-negotiation-policy
          PolicyType: SSLNegotiationPolicyType
          Attributes:
            - Name: Reference-Security-Policy
              Value: ELBSecurityPolicy-TLS-1-2-2017-01
      HealthCheck:
        Target: HTTP:80/index.html
        HealthyThreshold: '10'
        UnhealthyThreshold: '2'
        Interval: '30'
        Timeout: '5'
      Tags:
        - Key: <web_tier_tag>
          Value: <web_tier_tag_value>

Using Terraform (AWS Provider)

01 Terraform configuration file (.tf):

terraform {
  required_providers {
    aws = {
      source  = "hashicorp/aws"
      version = "~> 4.0"
    }
  }

  required_version = ">= 0.14.9"
}

provider "aws" {
  region  = "us-east-1"
}

resource "aws_elb" "classic-load-balancer" {
  name               = "cc-frontend-load-balancer"
  internal           = false
  security_groups    = ["sg-0abcdabcdabcdabcd"]
  subnets            = ["subnet-0abcd1234abcd1234", "subnet-0abcdabcdabcdabcd", "subnet-01234abcd1234abcd", "subnet-01234123412341234"]
  instances          = ["i-0abcd1234abcd1234", "i-0abcdabcdabcdabcd"]

  listener {
    instance_port      = 80
    instance_protocol  = "http"
    lb_port            = 443
    lb_protocol        = "https"
    ssl_certificate_id = "arn:aws:acm:us-east-1:123456789012:certificate/abcd1234-abcd-1234-abcd-1234abcd1234"
  }

  # Configure Health Check for Web-Tier Classic Load Balancer
  health_check {
    healthy_threshold   = 10
    unhealthy_threshold = 2
    timeout             = 5
    target              = "HTTP:80/index.html"
    interval            = 30
  }

  tags = {
      Name = "<web_tier_tag>"
      Value = "<web_tier_tag_value>"
  }

}

resource "aws_load_balancer_policy" "cc-ssl-negotiation-policy" {
  load_balancer_name = aws_elb.classic-load-balancer.name
  policy_name        = "cc-secure-negotiation-policy"
  policy_type_name   = "SSLNegotiationPolicyType"
  policy_attribute {
    name  = "Reference-Security-Policy"
    value = "ELBSecurityPolicy-TLS-1-2-2017-01"
  }
}

resource "aws_load_balancer_listener_policy" "cc-https-listener-policy" {
  load_balancer_name = aws_elb.classic-load-balancer.name
  load_balancer_port = 443
  policy_names = [
    aws_load_balancer_policy.cc-ssl-negotiation-policy.policy_name
  ]
}

Using AWS Console

01 Sign in to the AWS Management Console.

02 Navigate to Amazon EC2 console at https://console.aws.amazon.com/ec2/v2/.

03 In the main navigation panel, under Load Balancing, choose Load Balancers.

04 Click inside the Filter by tags and attributes or search by keyword box, select Type and choose classic to list the Classic Load Balancers available in the current AWS region.

05 Select the web-tier Classic Load Balancer that you want to reconfigure.

06 Select the Health Check tab from the console bottom panel and choose Edit Health Check to update the health check configuration.

07 In Configure Health Check configuration box, select HTTP or HTTPS from the Ping Protocol dropdown list and configure the Ping Port and Ping Path parameters based on your application requirements. For Advanced Details, customize the health check settings to meet your specific needs or leave the default settings unchanged for default behavior. Choose Save to apply the changes and return to the EC2 console.

08 Repeat steps no. 5 – 7 for each web-tier Classic Load Balancer that you want to reconfigure, available within the current AWS region.

09 Change the AWS cloud region from the console navigation bar and repeat the Remediation process for other regions.

Using AWS CLI

01 Run configure-health-check command (OSX/Linux/UNIX) to configure the health check settings to use when evaluating the health state of the Amazon EC2 instances behind your web-tier Classic Load Balancer. The following command example updates the health check configuration for a load balancer named "cc-frontend-load-balancer" using an HTTP-based ping target with the port set to 80 and the path set to "/index.html":

aws elb configure-health-check
  --region us-east-1
  --load-balancer-name cc-frontend-load-balancer
  --health-check Target=HTTP:80/index.html,Interval=30,UnhealthyThreshold=2,HealthyThreshold=10,Timeout=5

02 The command output should return the new configuration information available for the load balancer health check:

{
    "HealthCheck": {
        "Target": "HTTP:80/index.html",
        "Interval": 30,
        "Timeout": 5,
        "UnhealthyThreshold": 2,
        "HealthyThreshold": 10
    }
}

03 Repeat steps no. 1 and 2 for each web-tier Classic Load Balancer that you want to reconfigure, available in the selected AWS region.

04 Change the AWS cloud region by updating the --region command parameter value and repeat the Remediation process for other regions.

References

Publication date Mar 8, 2018