support - intial commit to kick off trusted advisor checks (#3685)

* support - intial commit to kick off trusted advisor checks

* edit - expanded testing to include checking for expected check ids and
check names.

Added server testing

added support resource json to manifest file and simplified
support response return from reviewed comments

* Streamline loading of resource files

* edit - ensured regions are assigned in models

Co-authored-by: Bert Blommers <info@bertblommers.nl>
This commit is contained in:
Connor 2021-02-14 12:22:16 +00:00 committed by GitHub
parent e8f1522d1a
commit 4d0ee82f98
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
14 changed files with 1690 additions and 8 deletions

View File

@ -5,5 +5,6 @@ include moto/ec2/resources/instance_type_offerings/*/*.json
include moto/ec2/resources/amis.json
include moto/cognitoidp/resources/*.json
include moto/dynamodb2/parsing/reserved_keywords.txt
include moto/support/resources/*.json
recursive-include moto/templates *
recursive-include tests *

View File

@ -120,6 +120,7 @@ mock_kinesisvideoarchivedmedia = lazy_load(
".kinesisvideoarchivedmedia", "mock_kinesisvideoarchivedmedia"
)
mock_medialive = lazy_load(".medialive", "mock_medialive")
mock_support = lazy_load(".support", "mock_support")
# import logging
# logging.getLogger('boto').setLevel(logging.CRITICAL)

View File

@ -77,6 +77,7 @@ BACKENDS = {
"kinesisvideoarchivedmedia_backends",
),
"forecast": ("forecast", "forecast_backends"),
"support": ("support", "support_backends"),
}

View File

@ -34,6 +34,7 @@ from moto.core.utils import (
)
from moto.core import ACCOUNT_ID
from moto.kms import kms_backends
from moto.utilities.utils import load_resource
from os import listdir
from .exceptions import (
@ -169,12 +170,7 @@ from .utils import (
)
def _load_resource(filename):
with open(filename, "r") as f:
return json.load(f)
INSTANCE_TYPES = _load_resource(
INSTANCE_TYPES = load_resource(
resource_filename(__name__, "resources/instance_types.json")
)
@ -190,10 +186,10 @@ for location_type in listdir(resource_filename(__name__, offerings_path)):
)
INSTANCE_TYPE_OFFERINGS[location_type][
region.replace(".json", "")
] = _load_resource(full_path)
] = load_resource(full_path)
AMIS = _load_resource(
AMIS = load_resource(
os.environ.get("MOTO_AMIS_PATH")
or resource_filename(__name__, "resources/amis.json"),
)

6
moto/support/__init__.py Normal file
View File

@ -0,0 +1,6 @@
from __future__ import unicode_literals
from .models import support_backends
from ..core.models import base_decorator
support_backend = support_backends["us-east-1"]
mock_support = base_decorator(support_backends)

View File

@ -0,0 +1 @@
from __future__ import unicode_literals

37
moto/support/models.py Normal file
View File

@ -0,0 +1,37 @@
from __future__ import unicode_literals
from boto3 import Session
from pkg_resources import resource_filename
from moto.core import BaseBackend
from moto.utilities.utils import load_resource
checks_json = "resources/describe_trusted_advisor_checks.json"
ADVISOR_CHECKS = load_resource(resource_filename(__name__, checks_json))
class SupportBackend(BaseBackend):
def __init__(self, region_name=None):
super(SupportBackend, self).__init__()
self.region_name = region_name
def reset(self):
region_name = self.region_name
self.__dict__ = {}
self.__init__(region_name)
def describe_trusted_advisor_checks(self, language):
# The checks are a static response
checks = ADVISOR_CHECKS["checks"]
return checks
support_backends = {}
# Only currently supported in us-east-1
support_backends["us-east-1"] = SupportBackend("us-east-1")
for region in Session().get_available_regions("support"):
support_backends[region] = SupportBackend(region)
for region in Session().get_available_regions("support", partition_name="aws-us-gov"):
support_backends[region] = SupportBackend(region)
for region in Session().get_available_regions("support", partition_name="aws-cn"):
support_backends[region] = SupportBackend(region)

File diff suppressed because it is too large Load Diff

20
moto/support/responses.py Normal file
View File

@ -0,0 +1,20 @@
from __future__ import unicode_literals
from moto.core.responses import BaseResponse
from .models import support_backends
import json
class SupportResponse(BaseResponse):
SERVICE_NAME = "support"
@property
def support_backend(self):
return support_backends[self.region]
def describe_trusted_advisor_checks(self):
language = self._get_param("language")
checks = self.support_backend.describe_trusted_advisor_checks(
language=language,
)
return json.dumps({"checks": checks})

11
moto/support/urls.py Normal file
View File

@ -0,0 +1,11 @@
from __future__ import unicode_literals
from .responses import SupportResponse
url_bases = [
"https?://support.(.+).amazonaws.com",
]
url_paths = {
"{0}/$": SupportResponse.dispatch,
}

View File

@ -1,3 +1,4 @@
import json
import random
import string
@ -8,3 +9,14 @@ def random_string(length=None):
[random.choice(string.ascii_letters + string.digits) for i in range(n)]
)
return random_str
def load_resource(filename):
"""
Open a file, and return the contents as JSON.
Usage:
from pkg_resources import resource_filename
load_resource(resource_filename(__name__, "resources/file.json"))
"""
with open(filename, "r") as f:
return json.load(f)

View File

View File

@ -0,0 +1,60 @@
from __future__ import unicode_literals
import sure # noqa
import moto.server as server
"""
Test the different server responses for support
"""
def test_describe_trusted_advisor_checks_returns_check_names():
"""
Check that the correct names of checks are returned
"""
backend = server.create_backend_app("support")
test_client = backend.test_client()
res = test_client.get("/?Action=DescribeTrustedAdvisorChecks&Version=2015-12-01")
res.data.should.contain(b"Low Utilization Amazon EC2 Instances")
res.data.should.contain(b"ELB Application Load Balancers")
def test_describe_trusted_advisor_checks_does_not_return_wrong_check_names():
"""
Check that the wrong names of checks are not returned
"""
backend = server.create_backend_app("support")
test_client = backend.test_client()
res = test_client.get("/?Action=DescribeTrustedAdvisorChecks&Version=2015-12-01")
res.data.doesnot.contain(b"Low Utilization Amazon Foo Instances")
res.data.doesnot.contain(b"ELB Application Bar Balancers")
def test_describe_trusted_advisor_checks_returns_check_ids():
"""
Check that some random ids of checks are returned
"""
backend = server.create_backend_app("support")
test_client = backend.test_client()
res = test_client.get("/?Action=DescribeTrustedAdvisorChecks&Version=2015-12-01")
res.data.should.contain(b"DAvU99Dc4C")
res.data.should.contain(b"zXCkfM1nI3")
def test_describe_trusted_advisor_checks_does_not_return_wrong_id():
"""
Check that some wrong ids of checks are not returned
"""
backend = server.create_backend_app("support")
test_client = backend.test_client()
res = test_client.get("/?Action=DescribeTrustedAdvisorChecks&Version=2015-12-01")
res.data.doesnot.contain(b"DAvU99DcBAR")
res.data.doesnot.contain(b"zXCkfM1nFOO")

View File

@ -0,0 +1,45 @@
from __future__ import unicode_literals
import boto3
import sure # noqa
from moto import mock_support
@mock_support
def test_describe_trusted_advisor_checks_returns_amount_of_checks():
"""
test that the 104 checks that are listed under trusted advisor currently
are returned
"""
client = boto3.client("support", "us-east-1")
response = client.describe_trusted_advisor_checks(language="en",)
response["checks"].should.be.length_of(104)
@mock_support
def test_describe_trusted_advisor_checks_returns_an_expected_id():
"""
test that a random check id is returned
"""
client = boto3.client("support", "us-east-1")
response = client.describe_trusted_advisor_checks(language="en",)
check_ids = []
for check in response["checks"]:
check_ids.append(check["id"])
check_ids.should.contain("zXCkfM1nI3")
@mock_support
def test_describe_trusted_advisor_checks_returns_an_expected_check_name():
"""
test that a random check name is returned
"""
client = boto3.client("support", "us-east-1")
response = client.describe_trusted_advisor_checks(language="en",)
check_names = []
for check in response["checks"]:
check_names.append(check["name"])
check_names.should.contain("Unassociated Elastic IP Addresses")