278 lines
		
	
	
		
			11 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			278 lines
		
	
	
		
			11 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
"""Route53 unit tests specific to query_logging_config APIs."""
 | 
						|
import pytest
 | 
						|
 | 
						|
import boto3
 | 
						|
from botocore.exceptions import ClientError
 | 
						|
 | 
						|
from moto import mock_logs
 | 
						|
from moto import mock_route53
 | 
						|
from moto.core import ACCOUNT_ID
 | 
						|
from moto.core.utils import get_random_hex
 | 
						|
 | 
						|
# The log group must be in the us-east-1 region.
 | 
						|
TEST_REGION = "us-east-1"
 | 
						|
 | 
						|
 | 
						|
def create_hosted_zone_id(route53_client, hosted_zone_test_name):
 | 
						|
    """Return ID of a newly created Route53 public hosted zone"""
 | 
						|
    response = route53_client.create_hosted_zone(
 | 
						|
        Name=hosted_zone_test_name,
 | 
						|
        CallerReference=f"test_caller_ref_{get_random_hex(6)}",
 | 
						|
    )
 | 
						|
    assert response["ResponseMetadata"]["HTTPStatusCode"] == 201
 | 
						|
    assert "HostedZone" in response and response["HostedZone"]["Id"]
 | 
						|
    return response["HostedZone"]["Id"]
 | 
						|
 | 
						|
 | 
						|
def create_log_group_arn(logs_client, hosted_zone_test_name):
 | 
						|
    """Return ARN of a newly created CloudWatch log group."""
 | 
						|
    log_group_name = f"/aws/route53/{hosted_zone_test_name}"
 | 
						|
    response = logs_client.create_log_group(logGroupName=log_group_name)
 | 
						|
    assert response["ResponseMetadata"]["HTTPStatusCode"] == 200
 | 
						|
 | 
						|
    log_group_arn = None
 | 
						|
    response = logs_client.describe_log_groups()
 | 
						|
    for entry in response["logGroups"]:
 | 
						|
        if entry["logGroupName"] == log_group_name:
 | 
						|
            log_group_arn = entry["arn"]
 | 
						|
            break
 | 
						|
    return log_group_arn
 | 
						|
 | 
						|
 | 
						|
@mock_logs
 | 
						|
@mock_route53
 | 
						|
def test_create_query_logging_config_bad_args():
 | 
						|
    """Test bad arguments to create_query_logging_config()."""
 | 
						|
    client = boto3.client("route53", region_name=TEST_REGION)
 | 
						|
    logs_client = boto3.client("logs", region_name=TEST_REGION)
 | 
						|
 | 
						|
    hosted_zone_test_name = f"route53_query_log_{get_random_hex(6)}.test"
 | 
						|
    hosted_zone_id = create_hosted_zone_id(client, hosted_zone_test_name)
 | 
						|
    log_group_arn = create_log_group_arn(logs_client, hosted_zone_test_name)
 | 
						|
 | 
						|
    # Check exception:  NoSuchHostedZone
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.create_query_logging_config(
 | 
						|
            HostedZoneId="foo", CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
        )
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "NoSuchHostedZone"
 | 
						|
    assert "No hosted zone found with ID: foo" in err["Message"]
 | 
						|
 | 
						|
    # Check exception:  InvalidInput (bad CloudWatch Logs log ARN)
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.create_query_logging_config(
 | 
						|
            HostedZoneId=hosted_zone_id,
 | 
						|
            CloudWatchLogsLogGroupArn=f"arn:aws:logs:{TEST_REGION}:{ACCOUNT_ID}:foo-bar:foo",
 | 
						|
        )
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "InvalidInput"
 | 
						|
    assert "The ARN for the CloudWatch Logs log group is invalid" in err["Message"]
 | 
						|
 | 
						|
    # Check exception:  InvalidInput (CloudWatch Logs log not in us-east-1)
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.create_query_logging_config(
 | 
						|
            HostedZoneId=hosted_zone_id,
 | 
						|
            CloudWatchLogsLogGroupArn=log_group_arn.replace(TEST_REGION, "us-west-1"),
 | 
						|
        )
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "InvalidInput"
 | 
						|
    assert "The ARN for the CloudWatch Logs log group is invalid" in err["Message"]
 | 
						|
 | 
						|
    # Check exception:  NoSuchCloudWatchLogsLogGroup
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.create_query_logging_config(
 | 
						|
            HostedZoneId=hosted_zone_id,
 | 
						|
            CloudWatchLogsLogGroupArn=log_group_arn.replace(
 | 
						|
                hosted_zone_test_name, "foo"
 | 
						|
            ),
 | 
						|
        )
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "NoSuchCloudWatchLogsLogGroup"
 | 
						|
    assert "The specified CloudWatch Logs log group doesn't exist" in err["Message"]
 | 
						|
 | 
						|
    # Check exception:  QueryLoggingConfigAlreadyExists
 | 
						|
    client.create_query_logging_config(
 | 
						|
        HostedZoneId=hosted_zone_id, CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
    )
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.create_query_logging_config(
 | 
						|
            HostedZoneId=hosted_zone_id, CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
        )
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "QueryLoggingConfigAlreadyExists"
 | 
						|
    assert (
 | 
						|
        "A query logging configuration already exists for this hosted zone"
 | 
						|
        in err["Message"]
 | 
						|
    )
 | 
						|
 | 
						|
 | 
						|
@mock_logs
 | 
						|
@mock_route53
 | 
						|
def test_create_query_logging_config_good_args():
 | 
						|
    """Test a valid create_logging_config() request."""
 | 
						|
    client = boto3.client("route53", region_name=TEST_REGION)
 | 
						|
    logs_client = boto3.client("logs", region_name=TEST_REGION)
 | 
						|
 | 
						|
    hosted_zone_test_name = f"route53_query_log_{get_random_hex(6)}.test"
 | 
						|
    hosted_zone_id = create_hosted_zone_id(client, hosted_zone_test_name)
 | 
						|
    log_group_arn = create_log_group_arn(logs_client, hosted_zone_test_name)
 | 
						|
 | 
						|
    response = client.create_query_logging_config(
 | 
						|
        HostedZoneId=hosted_zone_id, CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
    )
 | 
						|
    config = response["QueryLoggingConfig"]
 | 
						|
    assert config["HostedZoneId"] == hosted_zone_id.split("/")[-1]
 | 
						|
    assert config["CloudWatchLogsLogGroupArn"] == log_group_arn
 | 
						|
    assert config["Id"]
 | 
						|
 | 
						|
    location = response["Location"]
 | 
						|
    assert (
 | 
						|
        location
 | 
						|
        == f"https://route53.amazonaws.com/2013-04-01/queryloggingconfig/{config['Id']}"
 | 
						|
    )
 | 
						|
 | 
						|
 | 
						|
@mock_logs
 | 
						|
@mock_route53
 | 
						|
def test_delete_query_logging_config():
 | 
						|
    """Test valid and invalid delete_query_logging_config requests."""
 | 
						|
    client = boto3.client("route53", region_name=TEST_REGION)
 | 
						|
    logs_client = boto3.client("logs", region_name=TEST_REGION)
 | 
						|
 | 
						|
    # Create a query logging config that can then be deleted.
 | 
						|
    hosted_zone_test_name = f"route53_query_log_{get_random_hex(6)}.test"
 | 
						|
    hosted_zone_id = create_hosted_zone_id(client, hosted_zone_test_name)
 | 
						|
    log_group_arn = create_log_group_arn(logs_client, hosted_zone_test_name)
 | 
						|
 | 
						|
    query_response = client.create_query_logging_config(
 | 
						|
        HostedZoneId=hosted_zone_id, CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
    )
 | 
						|
 | 
						|
    # Test the deletion.
 | 
						|
    query_id = query_response["QueryLoggingConfig"]["Id"]
 | 
						|
    response = client.delete_query_logging_config(Id=query_id)
 | 
						|
    # There is no response other than the usual ResponseMetadata.
 | 
						|
    assert list(response.keys()) == ["ResponseMetadata"]
 | 
						|
 | 
						|
    # Test the deletion of a non-existent query logging config, i.e., the
 | 
						|
    # one that was just deleted.
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.delete_query_logging_config(Id=query_id)
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "NoSuchQueryLoggingConfig"
 | 
						|
    assert "The query logging configuration does not exist" in err["Message"]
 | 
						|
 | 
						|
 | 
						|
@mock_logs
 | 
						|
@mock_route53
 | 
						|
def test_get_query_logging_config():
 | 
						|
    """Test valid and invalid get_query_logging_config requests."""
 | 
						|
    client = boto3.client("route53", region_name=TEST_REGION)
 | 
						|
    logs_client = boto3.client("logs", region_name=TEST_REGION)
 | 
						|
 | 
						|
    # Create a query logging config that can then be retrieved.
 | 
						|
    hosted_zone_test_name = f"route53_query_log_{get_random_hex(6)}.test"
 | 
						|
    hosted_zone_id = create_hosted_zone_id(client, hosted_zone_test_name)
 | 
						|
    log_group_arn = create_log_group_arn(logs_client, hosted_zone_test_name)
 | 
						|
 | 
						|
    query_response = client.create_query_logging_config(
 | 
						|
        HostedZoneId=hosted_zone_id, CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
    )
 | 
						|
 | 
						|
    # Test the retrieval.
 | 
						|
    query_id = query_response["QueryLoggingConfig"]["Id"]
 | 
						|
    response = client.get_query_logging_config(Id=query_id)
 | 
						|
    config = response["QueryLoggingConfig"]
 | 
						|
    assert config["HostedZoneId"] == hosted_zone_id.split("/")[-1]
 | 
						|
    assert config["CloudWatchLogsLogGroupArn"] == log_group_arn
 | 
						|
    assert config["Id"]
 | 
						|
 | 
						|
    # Test the retrieval of a non-existent query logging config.
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.get_query_logging_config(Id="1234567890")
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "NoSuchQueryLoggingConfig"
 | 
						|
    assert "The query logging configuration does not exist" in err["Message"]
 | 
						|
 | 
						|
 | 
						|
@mock_logs
 | 
						|
@mock_route53
 | 
						|
def test_list_query_logging_configs_bad_args():
 | 
						|
    """Test bad arguments to list_query_logging_configs()."""
 | 
						|
    client = boto3.client("route53", region_name=TEST_REGION)
 | 
						|
    logs_client = boto3.client("logs", region_name=TEST_REGION)
 | 
						|
 | 
						|
    # Check exception:  NoSuchHostedZone
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.list_query_logging_configs(HostedZoneId="foo", MaxResults="10")
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "NoSuchHostedZone"
 | 
						|
    assert "No hosted zone found with ID: foo" in err["Message"]
 | 
						|
 | 
						|
    # Create a couple of query logging configs to work with.
 | 
						|
    for _ in range(3):
 | 
						|
        hosted_zone_test_name = f"route53_query_log_{get_random_hex(6)}.test"
 | 
						|
        hosted_zone_id = create_hosted_zone_id(client, hosted_zone_test_name)
 | 
						|
        log_group_arn = create_log_group_arn(logs_client, hosted_zone_test_name)
 | 
						|
        client.create_query_logging_config(
 | 
						|
            HostedZoneId=hosted_zone_id, CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
        )
 | 
						|
 | 
						|
    # Retrieve a query logging config, then request more with an invalid token.
 | 
						|
    client.list_query_logging_configs(MaxResults="1")
 | 
						|
    with pytest.raises(ClientError) as exc:
 | 
						|
        client.list_query_logging_configs(NextToken="foo")
 | 
						|
    err = exc.value.response["Error"]
 | 
						|
    assert err["Code"] == "InvalidPaginationToken"
 | 
						|
    assert (
 | 
						|
        "Route 53 can't get the next page of query logging configurations "
 | 
						|
        "because the specified value for NextToken is invalid." in err["Message"]
 | 
						|
    )
 | 
						|
 | 
						|
 | 
						|
@mock_logs
 | 
						|
@mock_route53
 | 
						|
def test_list_query_logging_configs_good_args():
 | 
						|
    """Test valid arguments to list_query_logging_configs()."""
 | 
						|
    client = boto3.client("route53", region_name=TEST_REGION)
 | 
						|
    logs_client = boto3.client("logs", region_name=TEST_REGION)
 | 
						|
 | 
						|
    # Test when there are no query logging configs.
 | 
						|
    response = client.list_query_logging_configs()
 | 
						|
    query_logging_configs = response["QueryLoggingConfigs"]
 | 
						|
    assert len(query_logging_configs) == 0
 | 
						|
 | 
						|
    # Create a couple of query logging configs to work with.
 | 
						|
    zone_ids = []
 | 
						|
    for _ in range(10):
 | 
						|
        hosted_zone_test_name = f"route53_query_log_{get_random_hex(6)}.test"
 | 
						|
        hosted_zone_id = create_hosted_zone_id(client, hosted_zone_test_name)
 | 
						|
        zone_ids.append(hosted_zone_id)
 | 
						|
 | 
						|
        log_group_arn = create_log_group_arn(logs_client, hosted_zone_test_name)
 | 
						|
        client.create_query_logging_config(
 | 
						|
            HostedZoneId=hosted_zone_id, CloudWatchLogsLogGroupArn=log_group_arn
 | 
						|
        )
 | 
						|
 | 
						|
    # Verify all 10 of the query logging configs can be retrieved in one go.
 | 
						|
    response = client.list_query_logging_configs()
 | 
						|
    query_logging_configs = response["QueryLoggingConfigs"]
 | 
						|
    assert len(query_logging_configs) == 10
 | 
						|
    for idx, query_logging_config in enumerate(query_logging_configs):
 | 
						|
        assert query_logging_config["HostedZoneId"] == zone_ids[idx].split("/")[-1]
 | 
						|
 | 
						|
    # Request only two of the query logging configs and verify there's a
 | 
						|
    # next_token.
 | 
						|
    response = client.list_query_logging_configs(MaxResults="2")
 | 
						|
    assert len(response["QueryLoggingConfigs"]) == 2
 | 
						|
    assert response["NextToken"]
 | 
						|
 | 
						|
    # Request the remaining 8 query logging configs and verify there is
 | 
						|
    # no next token.
 | 
						|
    response = client.list_query_logging_configs(
 | 
						|
        MaxResults="8", NextToken=response["NextToken"]
 | 
						|
    )
 | 
						|
    assert len(response["QueryLoggingConfigs"]) == 8
 | 
						|
    assert "NextToken" not in response
 |