Remove deprecated decorators + boto dependency (#4378)

This commit is contained in:
Bert Blommers 2022-01-18 14:18:57 -01:00 committed by GitHub
parent 3adb5ea84f
commit aa70ee254d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
139 changed files with 560 additions and 23697 deletions

View File

@ -1,38 +0,0 @@
.. _boto:
=============
Boto vs Boto3
=============
Boto3 is the latest Python SDK, and as such the SDK targeted by Moto. All our `@mock_`-decorators should be usable against any boto3-version.
Still stuck on boto, the former SDK? Moto does have some support, in the form of our deprecated services:
.. sourcecode:: python
from moto import mock_ec2_deprecated
import boto
@mock_ec2_deprecated
def test_something_with_ec2():
ec2_conn = boto.ec2.connect_to_region('us-east-1')
ec2_conn.get_only_instances(instance_ids='i-123456')
When using both boto2 and boto3, one can do this to avoid confusion:
.. sourcecode:: python
from moto import mock_ec2_deprecated as mock_ec2_b2
from moto import mock_ec2
If you want to use Server Mode, the easiest way is to create a boto config file (`~/.boto`) with the following values:
.. code-block:: bash
[Boto]
is_secure = False
https_validate_certificates = False
proxy_port = 5000
proxy = 127.0.0.1

View File

@ -33,7 +33,6 @@ Additional Resources
docs/getting_started
docs/server_mode
docs/faq
docs/boto
docs/iam
docs/aws_config

View File

@ -26,68 +26,47 @@ def lazy_load(
mock_acm = lazy_load(".acm", "mock_acm")
mock_apigateway = lazy_load(".apigateway", "mock_apigateway")
mock_apigateway_deprecated = lazy_load(".apigateway", "mock_apigateway_deprecated")
mock_appsync = lazy_load(".appsync", "mock_appsync", boto3_name="appsync")
mock_athena = lazy_load(".athena", "mock_athena")
mock_applicationautoscaling = lazy_load(
".applicationautoscaling", "mock_applicationautoscaling"
)
mock_autoscaling = lazy_load(".autoscaling", "mock_autoscaling")
mock_autoscaling_deprecated = lazy_load(".autoscaling", "mock_autoscaling_deprecated")
mock_lambda = lazy_load(
".awslambda", "mock_lambda", boto3_name="lambda", backend="lambda_backends"
)
mock_lambda_deprecated = lazy_load(".awslambda", "mock_lambda_deprecated")
mock_batch = lazy_load(".batch", "mock_batch")
mock_budgets = lazy_load(".budgets", "mock_budgets")
mock_cloudformation = lazy_load(".cloudformation", "mock_cloudformation")
mock_cloudformation_deprecated = lazy_load(
".cloudformation", "mock_cloudformation_deprecated"
)
mock_cloudfront = lazy_load(".cloudfront", "mock_cloudfront")
mock_cloudtrail = lazy_load(".cloudtrail", "mock_cloudtrail", boto3_name="cloudtrail")
mock_cloudwatch = lazy_load(".cloudwatch", "mock_cloudwatch")
mock_cloudwatch_deprecated = lazy_load(".cloudwatch", "mock_cloudwatch_deprecated")
mock_codecommit = lazy_load(".codecommit", "mock_codecommit")
mock_codepipeline = lazy_load(".codepipeline", "mock_codepipeline")
mock_cognitoidentity = lazy_load(
".cognitoidentity", "mock_cognitoidentity", boto3_name="cognito-identity"
)
mock_cognitoidentity_deprecated = lazy_load(
".cognitoidentity", "mock_cognitoidentity_deprecated"
)
mock_cognitoidp = lazy_load(".cognitoidp", "mock_cognitoidp", boto3_name="cognito-idp")
mock_cognitoidp_deprecated = lazy_load(".cognitoidp", "mock_cognitoidp_deprecated")
mock_config = lazy_load(".config", "mock_config")
mock_datapipeline = lazy_load(".datapipeline", "mock_datapipeline")
mock_datapipeline_deprecated = lazy_load(
".datapipeline", "mock_datapipeline_deprecated"
)
mock_datasync = lazy_load(".datasync", "mock_datasync")
mock_dax = lazy_load(".dax", "mock_dax")
mock_dms = lazy_load(".dms", "mock_dms")
mock_ds = lazy_load(".ds", "mock_ds", boto3_name="ds")
mock_dynamodb = lazy_load(".dynamodb", "mock_dynamodb", warn_repurpose=True)
mock_dynamodb_deprecated = lazy_load(".dynamodb", "mock_dynamodb_deprecated")
mock_dynamodb2 = lazy_load(".dynamodb2", "mock_dynamodb2", backend="dynamodb_backends2")
mock_dynamodb2_deprecated = lazy_load(".dynamodb2", "mock_dynamodb2_deprecated")
mock_dynamodbstreams = lazy_load(".dynamodbstreams", "mock_dynamodbstreams")
mock_elasticbeanstalk = lazy_load(
".elasticbeanstalk", "mock_elasticbeanstalk", backend="eb_backends"
)
mock_ec2 = lazy_load(".ec2", "mock_ec2")
mock_ec2_deprecated = lazy_load(".ec2", "mock_ec2_deprecated")
mock_ec2instanceconnect = lazy_load(".ec2instanceconnect", "mock_ec2instanceconnect")
mock_ecr = lazy_load(".ecr", "mock_ecr")
mock_ecr_deprecated = lazy_load(".ecr", "mock_ecr_deprecated")
mock_ecs = lazy_load(".ecs", "mock_ecs")
mock_ecs_deprecated = lazy_load(".ecs", "mock_ecs_deprecated")
mock_elastictranscoder = lazy_load(".elastictranscoder", "mock_elastictranscoder")
mock_elb = lazy_load(".elb", "mock_elb")
mock_elb_deprecated = lazy_load(".elb", "mock_elb_deprecated")
mock_elbv2 = lazy_load(".elbv2", "mock_elbv2")
mock_emr = lazy_load(".emr", "mock_emr")
mock_emr_deprecated = lazy_load(".emr", "mock_emr_deprecated")
mock_emrcontainers = lazy_load(
".emrcontainers", "mock_emrcontainers", boto3_name="emr-containers"
)
@ -96,31 +75,22 @@ mock_events = lazy_load(".events", "mock_events")
mock_firehose = lazy_load(".firehose", "mock_firehose")
mock_forecast = lazy_load(".forecast", "mock_forecast")
mock_glacier = lazy_load(".glacier", "mock_glacier")
mock_glacier_deprecated = lazy_load(".glacier", "mock_glacier_deprecated")
mock_glue = lazy_load(".glue", "mock_glue")
mock_guardduty = lazy_load(".guardduty", "mock_guardduty")
mock_iam = lazy_load(".iam", "mock_iam")
mock_iam_deprecated = lazy_load(".iam", "mock_iam_deprecated")
mock_iot = lazy_load(".iot", "mock_iot")
mock_iotdata = lazy_load(".iotdata", "mock_iotdata", boto3_name="iot-data")
mock_kinesis = lazy_load(".kinesis", "mock_kinesis")
mock_kinesis_deprecated = lazy_load(".kinesis", "mock_kinesis_deprecated")
mock_kms = lazy_load(".kms", "mock_kms")
mock_kms_deprecated = lazy_load(".kms", "mock_kms_deprecated")
mock_logs = lazy_load(".logs", "mock_logs")
mock_logs_deprecated = lazy_load(".logs", "mock_logs_deprecated")
mock_managedblockchain = lazy_load(".managedblockchain", "mock_managedblockchain")
mock_opsworks = lazy_load(".opsworks", "mock_opsworks")
mock_opsworks_deprecated = lazy_load(".opsworks", "mock_opsworks_deprecated")
mock_organizations = lazy_load(".organizations", "mock_organizations")
mock_polly = lazy_load(".polly", "mock_polly")
mock_ram = lazy_load(".ram", "mock_ram")
mock_rds = lazy_load(".rds", "mock_rds", warn_repurpose=True)
mock_rds_deprecated = lazy_load(".rds", "mock_rds_deprecated")
mock_rds2 = lazy_load(".rds2", "mock_rds2", boto3_name="rds")
mock_rds2_deprecated = lazy_load(".rds2", "mock_rds2_deprecated")
mock_redshift = lazy_load(".redshift", "mock_redshift")
mock_redshift_deprecated = lazy_load(".redshift", "mock_redshift_deprecated")
mock_resourcegroups = lazy_load(
".resourcegroups", "mock_resourcegroups", boto3_name="resource-groups"
)
@ -128,29 +98,22 @@ mock_resourcegroupstaggingapi = lazy_load(
".resourcegroupstaggingapi", "mock_resourcegroupstaggingapi"
)
mock_route53 = lazy_load(".route53", "mock_route53")
mock_route53_deprecated = lazy_load(".route53", "mock_route53_deprecated")
mock_route53resolver = lazy_load(
".route53resolver", "mock_route53resolver", boto3_name="route53resolver"
)
mock_s3 = lazy_load(".s3", "mock_s3")
mock_s3_deprecated = lazy_load(".s3", "mock_s3_deprecated")
mock_sagemaker = lazy_load(".sagemaker", "mock_sagemaker")
mock_secretsmanager = lazy_load(".secretsmanager", "mock_secretsmanager")
mock_ses = lazy_load(".ses", "mock_ses")
mock_ses_deprecated = lazy_load(".ses", "mock_ses_deprecated")
mock_sns = lazy_load(".sns", "mock_sns")
mock_sns_deprecated = lazy_load(".sns", "mock_sns_deprecated")
mock_sqs = lazy_load(".sqs", "mock_sqs")
mock_sqs_deprecated = lazy_load(".sqs", "mock_sqs_deprecated")
mock_ssm = lazy_load(".ssm", "mock_ssm")
mock_ssoadmin = lazy_load(".ssoadmin", "mock_ssoadmin", boto3_name="sso-admin")
mock_stepfunctions = lazy_load(
".stepfunctions", "mock_stepfunctions", backend="stepfunction_backends"
)
mock_sts = lazy_load(".sts", "mock_sts")
mock_sts_deprecated = lazy_load(".sts", "mock_sts_deprecated")
mock_swf = lazy_load(".swf", "mock_swf")
mock_swf_deprecated = lazy_load(".swf", "mock_swf_deprecated")
mock_timestreamwrite = lazy_load(
".timestreamwrite", "mock_timestreamwrite", boto3_name="timestream-write"
)

View File

@ -1,6 +1,5 @@
from .models import apigateway_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
apigateway_backend = apigateway_backends["us-east-1"]
mock_apigateway = base_decorator(apigateway_backends)
mock_apigateway_deprecated = deprecated_base_decorator(apigateway_backends)

View File

@ -1,6 +1,5 @@
from .models import athena_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
athena_backend = athena_backends["us-east-1"]
mock_athena = base_decorator(athena_backends)
mock_athena_deprecated = deprecated_base_decorator(athena_backends)

View File

@ -1,6 +1,5 @@
from .models import autoscaling_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
autoscaling_backend = autoscaling_backends["us-east-1"]
mock_autoscaling = base_decorator(autoscaling_backends)
mock_autoscaling_deprecated = deprecated_base_decorator(autoscaling_backends)

View File

@ -1,6 +1,5 @@
from .models import lambda_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
lambda_backend = lambda_backends["us-east-1"]
mock_lambda = base_decorator(lambda_backends)
mock_lambda_deprecated = deprecated_base_decorator(lambda_backends)

View File

@ -1,6 +1,5 @@
from .models import cloudformation_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
cloudformation_backend = cloudformation_backends["us-east-1"]
mock_cloudformation = base_decorator(cloudformation_backends)
mock_cloudformation_deprecated = deprecated_base_decorator(cloudformation_backends)

View File

@ -57,7 +57,6 @@ from .exceptions import (
ValidationError,
UnsupportedAttribute,
)
from moto.packages.boto.cloudformation.stack import Output
# List of supported CloudFormation models
MODEL_LIST = CloudFormationModel.__subclasses__()
@ -78,6 +77,17 @@ DEFAULT_REGION = "us-east-1"
logger = logging.getLogger("moto")
class Output(object):
def __init__(self, connection=None):
self.connection = connection
self.description = None
self.key = None
self.value = None
def __repr__(self):
return 'Output:"%s"="%s"' % (self.key, self.value)
class LazyDict(dict):
def __getitem__(self, key):
val = dict.__getitem__(self, key)

View File

@ -1,5 +1,4 @@
from .models import cloudwatch_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
mock_cloudwatch = base_decorator(cloudwatch_backends)
mock_cloudwatch_deprecated = deprecated_base_decorator(cloudwatch_backends)

View File

@ -1,5 +1,4 @@
from .models import cognitoidentity_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
mock_cognitoidentity = base_decorator(cognitoidentity_backends)
mock_cognitoidentity_deprecated = deprecated_base_decorator(cognitoidentity_backends)

View File

@ -1,5 +1,4 @@
from .models import cognitoidp_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
mock_cognitoidp = base_decorator(cognitoidp_backends)
mock_cognitoidp_deprecated = deprecated_base_decorator(cognitoidp_backends)

View File

@ -16,7 +16,6 @@ from botocore.awsrequest import AWSResponse
from moto import settings
import responses
from moto.packages.httpretty import HTTPretty
from unittest.mock import patch
from .custom_responses_mock import (
get_response_mock,
@ -25,7 +24,6 @@ from .custom_responses_mock import (
reset_responses_mock,
)
from .utils import (
convert_httpretty_response,
convert_regex_to_flask_path,
convert_flask_to_responses_response,
)
@ -177,28 +175,6 @@ class BaseMockAWS:
del os.environ[k]
class HttprettyMockAWS(BaseMockAWS):
def reset(self):
HTTPretty.reset()
def enable_patching(self):
if not HTTPretty.is_enabled():
HTTPretty.enable()
for method in HTTPretty.METHODS:
for backend in self.backends_for_urls.values():
for key, value in backend.urls.items():
HTTPretty.register_uri(
method=method,
uri=re.compile(key),
body=convert_httpretty_response(value),
)
def disable_patching(self):
HTTPretty.disable()
HTTPretty.reset()
RESPONSES_METHODS = [
responses.GET,
responses.DELETE,
@ -681,12 +657,6 @@ class BaseBackend:
else:
return mocked_backend
def deprecated_decorator(self, func=None):
if func:
return HttprettyMockAWS({"global": self})(func)
else:
return HttprettyMockAWS({"global": self})
# def list_config_service_resources(self, resource_ids, resource_name, limit, next_token):
# """For AWS Config. This will list all of the resources of the given type and optional resource name and region"""
# raise NotImplementedError()
@ -792,7 +762,7 @@ class base_decorator:
self.backends = backends
def __call__(self, func=None):
if self.mock_backend != HttprettyMockAWS and settings.TEST_SERVER_MODE:
if settings.TEST_SERVER_MODE:
mocked_backend = ServerModeMockAWS(self.backends)
else:
mocked_backend = self.mock_backend(self.backends)
@ -803,10 +773,6 @@ class base_decorator:
return mocked_backend
class deprecated_base_decorator(base_decorator):
mock_backend = HttprettyMockAWS
class MotoAPIBackend(BaseBackend):
def reset(self):
import moto.backends as backends

View File

@ -106,29 +106,7 @@ def convert_regex_to_flask_path(url_path):
return url_path
class convert_httpretty_response(object):
def __init__(self, callback):
self.callback = callback
@property
def __name__(self):
# For instance methods, use class and method names. Otherwise
# use module and method name
if inspect.ismethod(self.callback):
outer = self.callback.__self__.__class__.__name__
else:
outer = self.callback.__module__
return "{0}.{1}".format(outer, self.callback.__name__)
def __call__(self, request, url, headers, **kwargs):
result = self.callback(request, url, headers)
status, headers, response = result
if "server" not in headers:
headers["server"] = "amazon.com"
return status, headers, response
class convert_flask_to_httpretty_response(object):
class convert_to_flask_response(object):
def __init__(self, callback):
self.callback = callback

View File

@ -1,5 +1,4 @@
from .models import datapipeline_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
mock_datapipeline = base_decorator(datapipeline_backends)
mock_datapipeline_deprecated = deprecated_base_decorator(datapipeline_backends)

View File

@ -1,6 +1,5 @@
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
from .models import datasync_backends
datasync_backend = datasync_backends["us-east-1"]
mock_datasync = base_decorator(datasync_backends)
mock_datasync_deprecated = deprecated_base_decorator(datasync_backends)

View File

@ -2,4 +2,3 @@ from .models import dynamodb_backend
dynamodb_backends = {"global": dynamodb_backend}
mock_dynamodb = dynamodb_backend.decorator
mock_dynamodb_deprecated = dynamodb_backend.deprecated_decorator

View File

@ -1,6 +1,5 @@
from moto.dynamodb2.models import dynamodb_backends as dynamodb_backends2
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
dynamodb_backend2 = dynamodb_backends2["us-east-1"]
mock_dynamodb2 = base_decorator(dynamodb_backends2)
mock_dynamodb2_deprecated = deprecated_base_decorator(dynamodb_backends2)

View File

@ -1,5 +1,4 @@
import re
import sys
from moto.dynamodb2.exceptions import (
InvalidTokenException,
@ -148,16 +147,9 @@ class ExpressionTokenizer(object):
self.token_list = []
self.staged_characters = ""
@classmethod
def is_py2(cls):
return sys.version_info[0] == 2
@classmethod
def make_list(cls, input_expression_str):
if cls.is_py2():
pass
else:
assert isinstance(input_expression_str, str)
assert isinstance(input_expression_str, str)
return ExpressionTokenizer(input_expression_str)._make_list()

View File

@ -1,6 +1,5 @@
from .models import ec2_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
ec2_backend = ec2_backends["us-east-1"]
mock_ec2 = base_decorator(ec2_backends)
mock_ec2_deprecated = deprecated_base_decorator(ec2_backends)

View File

@ -1,6 +1,5 @@
from .models import ecr_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
ecr_backend = ecr_backends["us-east-1"]
mock_ecr = base_decorator(ecr_backends)
mock_ecr_deprecated = deprecated_base_decorator(ecr_backends)

View File

@ -1,6 +1,5 @@
from .models import ecs_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
ecs_backend = ecs_backends["us-east-1"]
mock_ecs = base_decorator(ecs_backends)
mock_ecs_deprecated = deprecated_base_decorator(ecs_backends)

View File

@ -1,6 +1,5 @@
from .models import elb_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
elb_backend = elb_backends["us-east-1"]
mock_elb = base_decorator(elb_backends)
mock_elb_deprecated = deprecated_base_decorator(elb_backends)

View File

@ -2,13 +2,6 @@ import datetime
import pytz
from moto.packages.boto.ec2.elb.attributes import (
LbAttributes,
ConnectionSettingAttribute,
ConnectionDrainingAttribute,
AccessLogAttribute,
CrossZoneLoadBalancingAttribute,
)
from moto.packages.boto.ec2.elb.policies import Policies, OtherPolicy
from collections import OrderedDict
from moto.core import BaseBackend, BaseModel, CloudFormationModel
@ -248,23 +241,11 @@ class FakeLoadBalancer(CloudFormationModel):
@classmethod
def get_default_attributes(cls):
attributes = LbAttributes()
cross_zone_load_balancing = CrossZoneLoadBalancingAttribute()
cross_zone_load_balancing.enabled = False
attributes.cross_zone_load_balancing = cross_zone_load_balancing
connection_draining = ConnectionDrainingAttribute()
connection_draining.enabled = False
attributes.connection_draining = connection_draining
access_log = AccessLogAttribute()
access_log.enabled = False
attributes.access_log = access_log
connection_settings = ConnectionSettingAttribute()
connection_settings.idle_timeout = 60
attributes.connecting_settings = connection_settings
attributes = dict()
attributes["cross_zone_load_balancing"] = {"enabled": False}
attributes["connection_draining"] = {"enabled": False}
attributes["access_log"] = {"enabled": False}
attributes["connection_settings"] = {"idle_timeout": 60}
return attributes
@ -468,25 +449,27 @@ class ELBBackend(BaseBackend):
return load_balancer
def set_cross_zone_load_balancing_attribute(self, load_balancer_name, attribute):
def modify_load_balancer_attributes(
self,
load_balancer_name,
cross_zone=None,
connection_settings=None,
connection_draining=None,
access_log=None,
):
load_balancer = self.get_load_balancer(load_balancer_name)
load_balancer.attributes.cross_zone_load_balancing = attribute
return load_balancer
def set_access_log_attribute(self, load_balancer_name, attribute):
load_balancer = self.get_load_balancer(load_balancer_name)
load_balancer.attributes.access_log = attribute
return load_balancer
def set_connection_draining_attribute(self, load_balancer_name, attribute):
load_balancer = self.get_load_balancer(load_balancer_name)
load_balancer.attributes.connection_draining = attribute
return load_balancer
def set_connection_settings_attribute(self, load_balancer_name, attribute):
load_balancer = self.get_load_balancer(load_balancer_name)
load_balancer.attributes.connecting_settings = attribute
return load_balancer
if cross_zone:
load_balancer.attributes["cross_zone_load_balancing"] = cross_zone
if connection_settings:
load_balancer.attributes["connection_settings"] = connection_settings
if connection_draining:
load_balancer.attributes["connection_draining"] = connection_draining
if "timeout" not in connection_draining:
load_balancer.attributes["connection_draining"][
"timeout"
] = 300 # default
if access_log:
load_balancer.attributes["access_log"] = access_log
def create_lb_other_policy(self, load_balancer_name, other_policy):
load_balancer = self.get_load_balancer(load_balancer_name)

View File

@ -1,9 +1,3 @@
from moto.packages.boto.ec2.elb.attributes import (
ConnectionSettingAttribute,
ConnectionDrainingAttribute,
AccessLogAttribute,
CrossZoneLoadBalancingAttribute,
)
from moto.packages.boto.ec2.elb.policies import AppCookieStickinessPolicy, OtherPolicy
from moto.core.responses import BaseResponse
@ -153,40 +147,30 @@ class ELBResponse(BaseResponse):
"LoadBalancerAttributes.CrossZoneLoadBalancing."
)
if cross_zone:
attribute = CrossZoneLoadBalancingAttribute()
attribute.enabled = cross_zone["enabled"] == "true"
self.elb_backend.set_cross_zone_load_balancing_attribute(
load_balancer_name, attribute
self.elb_backend.modify_load_balancer_attributes(
load_balancer_name, cross_zone=cross_zone
)
access_log = self._get_dict_param("LoadBalancerAttributes.AccessLog.")
if access_log:
attribute = AccessLogAttribute()
attribute.enabled = access_log["enabled"] == "true"
attribute.s3_bucket_name = access_log["s3_bucket_name"]
attribute.s3_bucket_prefix = access_log["s3_bucket_prefix"]
attribute.emit_interval = access_log["emit_interval"]
self.elb_backend.set_access_log_attribute(load_balancer_name, attribute)
self.elb_backend.modify_load_balancer_attributes(
load_balancer_name, access_log=access_log
)
connection_draining = self._get_dict_param(
"LoadBalancerAttributes.ConnectionDraining."
)
if connection_draining:
attribute = ConnectionDrainingAttribute()
attribute.enabled = connection_draining["enabled"] == "true"
attribute.timeout = connection_draining.get("timeout", 300)
self.elb_backend.set_connection_draining_attribute(
load_balancer_name, attribute
self.elb_backend.modify_load_balancer_attributes(
load_balancer_name, connection_draining=connection_draining
)
connection_settings = self._get_dict_param(
"LoadBalancerAttributes.ConnectionSettings."
)
if connection_settings:
attribute = ConnectionSettingAttribute()
attribute.idle_timeout = connection_settings["idle_timeout"]
self.elb_backend.set_connection_settings_attribute(
load_balancer_name, attribute
self.elb_backend.modify_load_balancer_attributes(
load_balancer_name, connection_settings=connection_settings
)
template = self.response_template(MODIFY_ATTRIBUTES_TEMPLATE)
@ -628,23 +612,23 @@ DESCRIBE_ATTRIBUTES_TEMPLATE = """<DescribeLoadBalancerAttributesResponse xmlns
<DescribeLoadBalancerAttributesResult>
<LoadBalancerAttributes>
<AccessLog>
<Enabled>{{ attributes.access_log.enabled }}</Enabled>
{% if attributes.access_log.enabled %}
<S3BucketName>{{ attributes.access_log.s3_bucket_name }}</S3BucketName>
<S3BucketPrefix>{{ attributes.access_log.s3_bucket_prefix }}</S3BucketPrefix>
<EmitInterval>{{ attributes.access_log.emit_interval }}</EmitInterval>
<Enabled>{{ attributes["access_log"]["enabled"] }}</Enabled>
{% if attributes["access_log"]["enabled"] == 'true' %}
<S3BucketName>{{ attributes["access_log"]["s3_bucket_name"] }}</S3BucketName>
<S3BucketPrefix>{{ attributes["access_log"]["s3_bucket_prefix"] }}</S3BucketPrefix>
<EmitInterval>{{ attributes["access_log"]["emit_interval"] }}</EmitInterval>
{% endif %}
</AccessLog>
<ConnectionSettings>
<IdleTimeout>{{ attributes.connecting_settings.idle_timeout }}</IdleTimeout>
<IdleTimeout>{{ attributes["connection_settings"]["idle_timeout"] }}</IdleTimeout>
</ConnectionSettings>
<CrossZoneLoadBalancing>
<Enabled>{{ attributes.cross_zone_load_balancing.enabled }}</Enabled>
</CrossZoneLoadBalancing>
<ConnectionDraining>
{% if attributes.connection_draining.enabled %}
{% if attributes["connection_draining"]["enabled"] == 'true' %}
<Enabled>true</Enabled>
<Timeout>{{ attributes.connection_draining.timeout }}</Timeout>
<Timeout>{{ attributes["connection_draining"]["timeout"] }}</Timeout>
{% else %}
<Enabled>false</Enabled>
{% endif %}
@ -662,23 +646,23 @@ MODIFY_ATTRIBUTES_TEMPLATE = """<ModifyLoadBalancerAttributesResponse xmlns="htt
<LoadBalancerName>{{ load_balancer.name }}</LoadBalancerName>
<LoadBalancerAttributes>
<AccessLog>
<Enabled>{{ attributes.access_log.enabled }}</Enabled>
{% if attributes.access_log.enabled %}
<S3BucketName>{{ attributes.access_log.s3_bucket_name }}</S3BucketName>
<S3BucketPrefix>{{ attributes.access_log.s3_bucket_prefix }}</S3BucketPrefix>
<EmitInterval>{{ attributes.access_log.emit_interval }}</EmitInterval>
<Enabled>{{ attributes["access_log"]["enabled"] == 'true' }}</Enabled>
{% if attributes["access_log"]["enabled"] == 'true' %}
<S3BucketName>{{ attributes["access_log"]["s3_bucket_name"] }}</S3BucketName>
<S3BucketPrefix>{{ attributes["access_log"]["s3_bucket_prefix"] }}</S3BucketPrefix>
<EmitInterval>{{ attributes["access_log"]["emit_interval"] }}</EmitInterval>
{% endif %}
</AccessLog>
<ConnectionSettings>
<IdleTimeout>{{ attributes.connecting_settings.idle_timeout }}</IdleTimeout>
<IdleTimeout>{{ attributes["connection_settings"]["idle_timeout"] }}</IdleTimeout>
</ConnectionSettings>
<CrossZoneLoadBalancing>
<Enabled>{{ attributes.cross_zone_load_balancing.enabled }}</Enabled>
</CrossZoneLoadBalancing>
<ConnectionDraining>
{% if attributes.connection_draining.enabled %}
{% if attributes["connection_draining"]["enabled"] == 'true' %}
<Enabled>true</Enabled>
<Timeout>{{ attributes.connection_draining.timeout }}</Timeout>
<Timeout>{{ attributes["connection_draining"]["timeout"] }}</Timeout>
{% else %}
<Enabled>false</Enabled>
{% endif %}

View File

@ -1,6 +1,5 @@
from .models import emr_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
emr_backend = emr_backends["us-east-1"]
mock_emr = base_decorator(emr_backends)
mock_emr_deprecated = deprecated_base_decorator(emr_backends)

View File

@ -1,6 +1,5 @@
from .models import glacier_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
glacier_backend = glacier_backends["us-east-1"]
mock_glacier = base_decorator(glacier_backends)
mock_glacier_deprecated = deprecated_base_decorator(glacier_backends)

View File

@ -2,4 +2,3 @@ from .models import iam_backend
iam_backends = {"global": iam_backend}
mock_iam = iam_backend.decorator
mock_iam_deprecated = iam_backend.deprecated_decorator

View File

@ -1,6 +1,5 @@
from .models import kinesis_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
kinesis_backend = kinesis_backends["us-east-1"]
mock_kinesis = base_decorator(kinesis_backends)
mock_kinesis_deprecated = deprecated_base_decorator(kinesis_backends)

View File

@ -1,6 +1,5 @@
from .models import kms_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
kms_backend = kms_backends["us-east-1"]
mock_kms = base_decorator(kms_backends)
mock_kms_deprecated = deprecated_base_decorator(kms_backends)

View File

@ -1,5 +1,4 @@
from .models import logs_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
mock_logs = base_decorator(logs_backends)
mock_logs_deprecated = deprecated_base_decorator(logs_backends)

View File

@ -1,8 +1,5 @@
from .models import managedblockchain_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
managedblockchain_backend = managedblockchain_backends["us-east-1"]
mock_managedblockchain = base_decorator(managedblockchain_backends)
mock_managedblockchain_deprecated = deprecated_base_decorator(
managedblockchain_backends
)

View File

@ -1,6 +1,5 @@
from .models import opsworks_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
opsworks_backend = opsworks_backends["us-east-1"]
mock_opsworks = base_decorator(opsworks_backends)
mock_opsworks_deprecated = deprecated_base_decorator(opsworks_backends)

View File

@ -1,9 +0,0 @@
class Output(object):
def __init__(self, connection=None):
self.connection = connection
self.description = None
self.key = None
self.value = None
def __repr__(self):
return 'Output:"%s"="%s"' % (self.key, self.value)

View File

@ -1,100 +0,0 @@
# Permission is hereby granted, free of charge, to any person obtaining a
# copy of this software and associated documentation files (the
# "Software"), to deal in the Software without restriction, including
# without limitation the rights to use, copy, modify, merge, publish, dis-
# tribute, sublicense, and/or sell copies of the Software, and to permit
# persons to whom the Software is furnished to do so, subject to the fol-
# lowing conditions:
#
# The above copyright notice and this permission notice shall be included
# in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
# ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT
# SHALL THE AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
# IN THE SOFTWARE.
#
# Created by Chris Huegle for TellApart, Inc.
class ConnectionSettingAttribute(object):
"""
Represents the ConnectionSetting segment of ELB Attributes.
"""
def __init__(self, connection=None):
self.idle_timeout = None
def __repr__(self):
return "ConnectionSettingAttribute(%s)" % (self.idle_timeout)
class CrossZoneLoadBalancingAttribute(object):
"""
Represents the CrossZoneLoadBalancing segement of ELB Attributes.
"""
def __init__(self, connection=None):
self.enabled = None
def __repr__(self):
return "CrossZoneLoadBalancingAttribute(%s)" % (self.enabled)
class AccessLogAttribute(object):
"""
Represents the AccessLog segment of ELB attributes.
"""
def __init__(self, connection=None):
self.enabled = None
self.s3_bucket_name = None
self.s3_bucket_prefix = None
self.emit_interval = None
def __repr__(self):
return "AccessLog(%s, %s, %s, %s)" % (
self.enabled,
self.s3_bucket_name,
self.s3_bucket_prefix,
self.emit_interval,
)
class ConnectionDrainingAttribute(object):
"""
Represents the ConnectionDraining segment of ELB attributes.
"""
def __init__(self, connection=None):
self.enabled = None
self.timeout = None
def __repr__(self):
return "ConnectionDraining(%s, %s)" % (self.enabled, self.timeout)
class LbAttributes(object):
"""
Represents the Attributes of an Elastic Load Balancer.
"""
def __init__(self, connection=None):
self.connection = connection
self.cross_zone_load_balancing = CrossZoneLoadBalancingAttribute(
self.connection
)
self.access_log = AccessLogAttribute(self.connection)
self.connection_draining = ConnectionDrainingAttribute(self.connection)
self.connecting_settings = ConnectionSettingAttribute(self.connection)
def __repr__(self):
return "LbAttributes(%s, %s, %s, %s)" % (
repr(self.cross_zone_load_balancing),
repr(self.access_log),
repr(self.connection_draining),
repr(self.connecting_settings),
)

View File

@ -1,61 +0,0 @@
# #!/usr/bin/env python
# -*- coding: utf-8 -*-
# <HTTPretty - HTTP client mock for Python>
# Copyright (C) <2011-2013> Gabriel Falcão <gabriel@nacaolivre.org>
#
# Permission is hereby granted, free of charge, to any person
# obtaining a copy of this software and associated documentation
# files (the "Software"), to deal in the Software without
# restriction, including without limitation the rights to use,
# copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the
# Software is furnished to do so, subject to the following
# conditions:
#
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
# OTHER DEALINGS IN THE SOFTWARE.
from __future__ import unicode_literals
__version__ = version = "0.8.10"
from .core import httpretty, httprettified, EmptyRequestHeaders
from .errors import HTTPrettyError, UnmockedError
from .core import URIInfo
HTTPretty = httpretty
activate = httprettified
enable = httpretty.enable
register_uri = httpretty.register_uri
disable = httpretty.disable
is_enabled = httpretty.is_enabled
reset = httpretty.reset
Response = httpretty.Response
GET = httpretty.GET
PUT = httpretty.PUT
POST = httpretty.POST
DELETE = httpretty.DELETE
HEAD = httpretty.HEAD
PATCH = httpretty.PATCH
OPTIONS = httpretty.OPTIONS
CONNECT = httpretty.CONNECT
def last_request():
"""returns the last request"""
return httpretty.last_request
def has_request():
"""returns a boolean indicating whether any request has been made"""
return not isinstance(httpretty.last_request.headers, EmptyRequestHeaders)

View File

@ -1,106 +0,0 @@
# #!/usr/bin/env python
# -*- coding: utf-8 -*-
#
# <HTTPretty - HTTP client mock for Python>
# Copyright (C) <2011-2013> Gabriel Falcão <gabriel@nacaolivre.org>
#
# Permission is hereby granted, free of charge, to any person
# obtaining a copy of this software and associated documentation
# files (the "Software"), to deal in the Software without
# restriction, including without limitation the rights to use,
# copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the
# Software is furnished to do so, subject to the following
# conditions:
#
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
# OTHER DEALINGS IN THE SOFTWARE.
from __future__ import unicode_literals
import sys
import types
PY3 = sys.version_info[0] == 3
if PY3: # pragma: no cover
text_type = str
byte_type = bytes
import io
StringIO = io.BytesIO
basestring = (str, bytes)
class BaseClass(object):
def __repr__(self):
return self.__str__()
else: # pragma: no cover
text_type = unicode
byte_type = str
import StringIO
StringIO = StringIO.StringIO
basestring = basestring
class BaseClass(object):
def __repr__(self):
ret = self.__str__()
if PY3: # pragma: no cover
return ret
else:
return ret.encode("utf-8")
try: # pragma: no cover
from urllib.parse import urlsplit, urlunsplit, parse_qs, quote, quote_plus, unquote
unquote_utf8 = unquote
except ImportError: # pragma: no cover
from urlparse import urlsplit, urlunsplit, parse_qs, unquote
from urllib import quote, quote_plus
def unquote_utf8(qs):
if isinstance(qs, text_type):
qs = qs.encode("utf-8")
s = unquote(qs)
if isinstance(s, byte_type):
return s.decode("utf-8")
else:
return s
try: # pragma: no cover
from http.server import BaseHTTPRequestHandler
except ImportError: # pragma: no cover
from BaseHTTPServer import BaseHTTPRequestHandler
ClassTypes = (type,)
if not PY3: # pragma: no cover
ClassTypes = (type, types.ClassType)
__all__ = [
"PY3",
"StringIO",
"text_type",
"byte_type",
"BaseClass",
"BaseHTTPRequestHandler",
"quote",
"quote_plus",
"urlunsplit",
"urlsplit",
"parse_qs",
"ClassTypes",
]

File diff suppressed because it is too large Load Diff

View File

@ -1,39 +0,0 @@
# #!/usr/bin/env python
# -*- coding: utf-8 -*-
#
# <HTTPretty - HTTP client mock for Python>
# Copyright (C) <2011-2013> Gabriel Falcão <gabriel@nacaolivre.org>
#
# Permission is hereby granted, free of charge, to any person
# obtaining a copy of this software and associated documentation
# files (the "Software"), to deal in the Software without
# restriction, including without limitation the rights to use,
# copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the
# Software is furnished to do so, subject to the following
# conditions:
#
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
# OTHER DEALINGS IN THE SOFTWARE.
from __future__ import unicode_literals
class HTTPrettyError(Exception):
pass
class UnmockedError(HTTPrettyError):
def __init__(self):
super(UnmockedError, self).__init__(
"No mocking was registered, and real connections are "
"not allowed (httpretty.allow_net_connect = False)."
)

View File

@ -1,154 +0,0 @@
# #!/usr/bin/env python
# -*- coding: utf-8 -*-
# <HTTPretty - HTTP client mock for Python>
# Copyright (C) <2011-2013> Gabriel Falcão <gabriel@nacaolivre.org>
#
# Permission is hereby granted, free of charge, to any person
# obtaining a copy of this software and associated documentation
# files (the "Software"), to deal in the Software without
# restriction, including without limitation the rights to use,
# copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the
# Software is furnished to do so, subject to the following
# conditions:
#
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
# OTHER DEALINGS IN THE SOFTWARE.
from __future__ import unicode_literals
import re
from .compat import BaseClass
from .utils import decode_utf8
STATUSES = {
100: "Continue",
101: "Switching Protocols",
102: "Processing",
200: "OK",
201: "Created",
202: "Accepted",
203: "Non-Authoritative Information",
204: "No Content",
205: "Reset Content",
206: "Partial Content",
207: "Multi-Status",
208: "Already Reported",
226: "IM Used",
300: "Multiple Choices",
301: "Moved Permanently",
302: "Found",
303: "See Other",
304: "Not Modified",
305: "Use Proxy",
306: "Switch Proxy",
307: "Temporary Redirect",
308: "Permanent Redirect",
400: "Bad Request",
401: "Unauthorized",
402: "Payment Required",
403: "Forbidden",
404: "Not Found",
405: "Method Not Allowed",
406: "Not Acceptable",
407: "Proxy Authentication Required",
408: "Request a Timeout",
409: "Conflict",
410: "Gone",
411: "Length Required",
412: "Precondition Failed",
413: "Request Entity Too Large",
414: "Request-URI Too Long",
415: "Unsupported Media Type",
416: "Requested Range Not Satisfiable",
417: "Expectation Failed",
418: "I'm a teapot",
420: "Enhance Your Calm",
422: "Unprocessable Entity",
423: "Locked",
424: "Failed Dependency",
424: "Method Failure",
425: "Unordered Collection",
426: "Upgrade Required",
428: "Precondition Required",
429: "Too Many Requests",
431: "Request Header Fields Too Large",
444: "No Response",
449: "Retry With",
450: "Blocked by Windows Parental Controls",
451: "Unavailable For Legal Reasons",
451: "Redirect",
494: "Request Header Too Large",
495: "Cert Error",
496: "No Cert",
497: "HTTP to HTTPS",
499: "Client Closed Request",
500: "Internal Server Error",
501: "Not Implemented",
502: "Bad Gateway",
503: "Service Unavailable",
504: "Gateway Timeout",
505: "HTTP Version Not Supported",
506: "Variant Also Negotiates",
507: "Insufficient Storage",
508: "Loop Detected",
509: "Bandwidth Limit Exceeded",
510: "Not Extended",
511: "Network Authentication Required",
598: "Network read timeout error",
599: "Network connect timeout error",
}
class HttpBaseClass(BaseClass):
GET = "GET"
PUT = "PUT"
POST = "POST"
DELETE = "DELETE"
HEAD = "HEAD"
PATCH = "PATCH"
OPTIONS = "OPTIONS"
CONNECT = "CONNECT"
METHODS = (GET, PUT, POST, DELETE, HEAD, PATCH, OPTIONS, CONNECT)
def parse_requestline(s):
"""
http://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html#sec5
>>> parse_requestline('GET / HTTP/1.0')
('GET', '/', '1.0')
>>> parse_requestline('post /testurl htTP/1.1')
('POST', '/testurl', '1.1')
>>> parse_requestline('Im not a RequestLine')
Traceback (most recent call last):
...
ValueError: Not a Request-Line
"""
methods = "|".join(HttpBaseClass.METHODS)
m = re.match(r"({})\s+(.*)\s+HTTP/(1.[0|1])".format(methods), s, re.I)
if m:
return m.group(1).upper(), m.group(2), m.group(3)
else:
raise ValueError("Not a Request-Line")
def last_requestline(sent_data):
"""
Find the last line in sent_data that can be parsed with parse_requestline
"""
for line in reversed(sent_data):
try:
parse_requestline(decode_utf8(line))
except ValueError:
pass
else:
return line

View File

@ -1,46 +0,0 @@
# #!/usr/bin/env python
# -*- coding: utf-8 -*-
# <HTTPretty - HTTP client mock for Python>
# Copyright (C) <2011-2013> Gabriel Falcão <gabriel@nacaolivre.org>
#
# Permission is hereby granted, free of charge, to any person
# obtaining a copy of this software and associated documentation
# files (the "Software"), to deal in the Software without
# restriction, including without limitation the rights to use,
# copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the
# Software is furnished to do so, subject to the following
# conditions:
#
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
# OTHER DEALINGS IN THE SOFTWARE.
from __future__ import unicode_literals
from .compat import byte_type, text_type
def utf8(s):
if isinstance(s, text_type):
s = s.encode("utf-8")
elif s is None:
return byte_type()
return byte_type(s)
def decode_utf8(s):
if isinstance(s, byte_type):
s = s.decode("utf-8")
elif s is None:
return text_type()
return text_type(s)

View File

@ -1,5 +1,4 @@
from .models import rds_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
mock_rds = base_decorator(rds_backends)
mock_rds_deprecated = deprecated_base_decorator(rds_backends)

View File

@ -1,6 +1,5 @@
from .models import rds2_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
rds2_backend = rds2_backends["us-west-1"]
mock_rds2 = base_decorator(rds2_backends)
mock_rds2_deprecated = deprecated_base_decorator(rds2_backends)

View File

@ -1,5 +1,4 @@
from .models import redshift_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
mock_redshift = base_decorator(redshift_backends)
mock_redshift_deprecated = deprecated_base_decorator(redshift_backends)

View File

@ -2,4 +2,3 @@ from .models import route53_backend
route53_backends = {"global": route53_backend}
mock_route53 = route53_backend.decorator
mock_route53_deprecated = route53_backend.deprecated_decorator

View File

@ -2,4 +2,3 @@ from .models import s3_backend
s3_backends = {"global": s3_backend}
mock_s3 = s3_backend.decorator
mock_s3_deprecated = s3_backend.deprecated_decorator

View File

@ -196,18 +196,6 @@ class FakeKey(BaseModel):
def set_acl(self, acl):
self.acl = acl
def append_to_value(self, value):
self.contentsize += len(value)
self._value_buffer.seek(0, os.SEEK_END)
self._value_buffer.write(value)
self.last_modified = datetime.datetime.utcnow()
self._etag = None # must recalculate etag
if self._is_versioned:
self._version_id = str(uuid.uuid4())
else:
self._version_id = None
def restore(self, days):
self._expiry = datetime.datetime.utcnow() + datetime.timedelta(days)
@ -1674,11 +1662,6 @@ class S3Backend(BaseBackend, CloudWatchMetricProvider):
key.lock_mode = retention[0]
key.lock_until = retention[1]
def append_to_key(self, bucket_name, key_name, value):
key = self.get_object(bucket_name, key_name)
key.append_to_value(value)
return key
def get_object(self, bucket_name, key_name, version_id=None, part_number=None):
key_name = clean_key_name(key_name)
bucket = self.get_bucket(bucket_name)

View File

@ -5,10 +5,10 @@ from typing import List, Union
from botocore.awsrequest import AWSPreparedRequest
from moto import settings
from moto.core.utils import amzn_request_id, str_to_rfc_1123_datetime
from urllib.parse import (
parse_qs,
parse_qsl,
urlparse,
unquote,
urlencode,
@ -17,8 +17,6 @@ from urllib.parse import (
import xmltodict
from moto import settings
from moto.packages.httpretty.core import HTTPrettyRequest
from moto.core.responses import _TemplateEnvironmentMixin, ActionAuthenticatorMixin
from moto.core.utils import path_url
from moto.core import ACCOUNT_ID
@ -972,13 +970,7 @@ class ResponseObject(_TemplateEnvironmentMixin, ActionAuthenticatorMixin):
self._authenticate_and_authorize_s3_action()
# POST to bucket-url should create file from form
if hasattr(request, "form"):
# Not HTTPretty
form = request.form
else:
# HTTPretty, build new form object
body = body.decode()
form = dict(parse_qsl(body))
form = request.form
key = form["key"]
if "file" in form:
@ -1028,15 +1020,11 @@ class ResponseObject(_TemplateEnvironmentMixin, ActionAuthenticatorMixin):
@staticmethod
def _get_path(request):
if isinstance(request, HTTPrettyRequest):
path = request.path
else:
path = (
request.full_path
if hasattr(request, "full_path")
else path_url(request.url)
)
return path
return (
request.full_path
if hasattr(request, "full_path")
else path_url(request.url)
)
def _bucket_response_delete_keys(self, request, body, bucket_name):
template = self.response_template(S3_DELETE_KEYS_RESPONSE)
@ -1587,39 +1575,29 @@ class ResponseObject(_TemplateEnvironmentMixin, ActionAuthenticatorMixin):
template = self.response_template(S3_OBJECT_COPY_RESPONSE)
response_headers.update(new_key.response_dict)
return 200, response_headers, template.render(key=new_key)
streaming_request = hasattr(request, "streaming") and request.streaming
closing_connection = headers.get("connection") == "close"
if closing_connection and streaming_request:
# Closing the connection of a streaming request. No more data
new_key = self.backend.get_object(bucket_name, key_name)
elif streaming_request:
# Streaming request, more data
new_key = self.backend.append_to_key(bucket_name, key_name, body)
else:
# Initial data
new_key = self.backend.put_object(
bucket_name,
key_name,
body,
storage=storage_class,
encryption=encryption,
kms_key_id=kms_key_id,
bucket_key_enabled=bucket_key_enabled,
lock_mode=lock_mode,
lock_legal_status=legal_hold,
lock_until=lock_until,
)
# Initial data
new_key = self.backend.put_object(
bucket_name,
key_name,
body,
storage=storage_class,
encryption=encryption,
kms_key_id=kms_key_id,
bucket_key_enabled=bucket_key_enabled,
lock_mode=lock_mode,
lock_legal_status=legal_hold,
lock_until=lock_until,
)
request.streaming = True
metadata = metadata_from_headers(request.headers)
metadata.update(metadata_from_headers(query))
new_key.set_metadata(metadata)
new_key.set_acl(acl)
new_key.website_redirect_location = request.headers.get(
"x-amz-website-redirect-location"
)
self.backend.set_key_tags(new_key, tagging)
metadata = metadata_from_headers(request.headers)
metadata.update(metadata_from_headers(query))
new_key.set_metadata(metadata)
new_key.set_acl(acl)
new_key.website_redirect_location = request.headers.get(
"x-amz-website-redirect-location"
)
self.backend.set_key_tags(new_key, tagging)
response_headers.update(new_key.response_dict)
return 200, response_headers, ""

View File

@ -17,7 +17,7 @@ from werkzeug.serving import run_simple
import moto.backends as backends
import moto.backend_index as backend_index
from moto.core.utils import convert_flask_to_httpretty_response
from moto.core.utils import convert_to_flask_response
HTTP_METHODS = ["GET", "POST", "PUT", "DELETE", "HEAD", "PATCH", "OPTIONS"]
@ -291,7 +291,7 @@ def create_backend_app(service):
backend = backend_dict["global"]
for url_path, handler in backend.flask_paths.items():
view_func = convert_flask_to_httpretty_response(handler)
view_func = convert_to_flask_response(handler)
if handler.__name__ == "dispatch":
endpoint = "{0}.dispatch".format(handler.__self__.__name__)
else:

View File

@ -2,4 +2,3 @@ from .models import ses_backend
ses_backends = {"global": ses_backend}
mock_ses = ses_backend.decorator
mock_ses_deprecated = ses_backend.deprecated_decorator

View File

@ -1,6 +1,5 @@
from .models import sns_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
sns_backend = sns_backends["us-east-1"]
mock_sns = base_decorator(sns_backends)
mock_sns_deprecated = deprecated_base_decorator(sns_backends)

View File

@ -1,6 +1,5 @@
from .models import sqs_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
sqs_backend = sqs_backends["us-east-1"]
mock_sqs = base_decorator(sqs_backends)
mock_sqs_deprecated = deprecated_base_decorator(sqs_backends)

View File

@ -2,4 +2,3 @@ from .models import sts_backend
sts_backends = {"global": sts_backend}
mock_sts = sts_backend.decorator
mock_sts_deprecated = sts_backend.deprecated_decorator

View File

@ -1,6 +1,5 @@
from .models import swf_backends
from ..core.models import base_decorator, deprecated_base_decorator
from ..core.models import base_decorator
swf_backend = swf_backends["us-east-1"]
mock_swf = base_decorator(swf_backends)
mock_swf_deprecated = deprecated_base_decorator(swf_backends)

View File

@ -4,7 +4,6 @@
black==19.10b0
regex==2019.11.1
flake8==3.7.8
boto>=2.45.0
click
inflection==0.3.1
lxml

View File

@ -3,7 +3,6 @@ from io import open
import os
import re
from setuptools import setup, find_packages
import sys
import moto.__init__ as service_list
# Borrowed from pip at https://github.com/pypa/pip/blob/62c27dee45625e1b63d1e023b0656310f276e050/setup.py#L11-L15

View File

@ -1,33 +1,7 @@
import boto
from unittest import SkipTest
from collections.abc import Iterable, Mapping
from sure import assertion
def version_tuple(v):
return tuple(map(int, (v.split("."))))
# Note: See https://github.com/spulec/moto/issues/201 for why this is a
# separate method.
def skip_test():
raise SkipTest
class requires_boto_gte(object):
"""Decorator for requiring boto version greater than or equal to 'version'"""
def __init__(self, version):
self.version = version
def __call__(self, test):
boto_version = version_tuple(boto.__version__)
required = version_tuple(self.version)
if boto_version >= required:
return test
return skip_test
@assertion
def containing_item_with_attributes(context, **kwargs):
contains = False

View File

@ -1,123 +1,22 @@
import boto
import boto3
import boto.ec2.autoscale
from boto.ec2.autoscale.launchconfig import LaunchConfiguration
from boto.ec2.autoscale.group import AutoScalingGroup
from boto.ec2.autoscale import Tag
import boto.ec2.elb
import sure # noqa # pylint: disable=unused-import
from botocore.exceptions import ClientError
import pytest
from moto import (
mock_autoscaling,
mock_ec2_deprecated,
mock_elb_deprecated,
mock_elb,
mock_autoscaling_deprecated,
mock_ec2,
)
from moto.core import ACCOUNT_ID
from tests.helpers import requires_boto_gte
from .utils import (
setup_networking,
setup_networking_deprecated,
setup_instance_with_networking,
)
from tests import EXAMPLE_AMI_ID
# Has boto3 equivalent
@mock_autoscaling_deprecated
@mock_elb_deprecated
@mock_ec2_deprecated
def test_create_autoscaling_group():
mocked_networking = setup_networking_deprecated()
elb_conn = boto.ec2.elb.connect_to_region("us-east-1")
elb_conn.create_load_balancer("test_lb", zones=[], listeners=[(80, 8080, "http")])
# we attach a couple of machines to the load balancer
# that are not managed by the auto scaling group
INSTANCE_COUNT_START = 3
INSTANCE_COUNT_GROUP = 2
ec2 = boto3.resource("ec2", region_name="us-east-1")
instances = ec2.create_instances(
ImageId=EXAMPLE_AMI_ID,
InstanceType="t1.micro",
MaxCount=INSTANCE_COUNT_START,
MinCount=INSTANCE_COUNT_START,
SubnetId=mocked_networking["subnet1"],
)
instances_ids = [_.id for _ in instances]
elb_conn.register_instances(
"test_lb", instances_ids,
)
conn = boto.ec2.autoscale.connect_to_region("us-east-1")
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
availability_zones=["us-east-1a", "us-east-1b"],
default_cooldown=60,
desired_capacity=INSTANCE_COUNT_GROUP,
health_check_period=100,
health_check_type="EC2",
max_size=INSTANCE_COUNT_GROUP,
min_size=INSTANCE_COUNT_GROUP,
launch_config=config,
load_balancers=["test_lb"],
placement_group="test_placement",
vpc_zone_identifier="{subnet1},{subnet2}".format(
subnet1=mocked_networking["subnet1"], subnet2=mocked_networking["subnet2"]
),
termination_policies=["OldestInstance", "NewestInstance"],
tags=[
Tag(
resource_id="tester_group",
key="test_key",
value="test_value",
propagate_at_launch=True,
)
],
)
conn.create_auto_scaling_group(group)
group = conn.get_all_groups()[0]
group.name.should.equal("tester_group")
set(group.availability_zones).should.equal(set(["us-east-1a", "us-east-1b"]))
group.desired_capacity.should.equal(2)
group.max_size.should.equal(INSTANCE_COUNT_GROUP)
group.min_size.should.equal(INSTANCE_COUNT_GROUP)
group.instances.should.have.length_of(INSTANCE_COUNT_GROUP)
group.vpc_zone_identifier.should.equal(
"{subnet1},{subnet2}".format(
subnet1=mocked_networking["subnet1"], subnet2=mocked_networking["subnet2"]
)
)
group.launch_config_name.should.equal("tester")
group.default_cooldown.should.equal(60)
group.health_check_period.should.equal(100)
group.health_check_type.should.equal("EC2")
list(group.load_balancers).should.equal(["test_lb"])
group.placement_group.should.equal("test_placement")
list(group.termination_policies).should.equal(["OldestInstance", "NewestInstance"])
len(list(group.tags)).should.equal(1)
tag = list(group.tags)[0]
tag.resource_id.should.equal("tester_group")
tag.key.should.equal("test_key")
tag.value.should.equal("test_value")
tag.propagate_at_launch.should.equal(True)
instances_attached = elb_conn.describe_instance_health("test_lb")
len(instances_attached).should.equal(INSTANCE_COUNT_START + INSTANCE_COUNT_GROUP)
@mock_autoscaling
@mock_ec2
@mock_elb
@ -222,47 +121,6 @@ def test_create_autoscaling_group_boto3_within_elb():
attached_ids.should.contain(ec2_instance_id)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_create_autoscaling_groups_defaults():
"""Test with the minimum inputs and check that all of the proper defaults
are assigned for the other attributes"""
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
group = conn.get_all_groups()[0]
group.name.should.equal("tester_group")
group.max_size.should.equal(2)
group.min_size.should.equal(2)
group.launch_config_name.should.equal("tester")
# Defaults
list(group.availability_zones).should.equal(["us-east-1a"]) # subnet1
group.desired_capacity.should.equal(2)
group.vpc_zone_identifier.should.equal(mocked_networking["subnet1"])
group.default_cooldown.should.equal(300)
group.health_check_period.should.equal(300)
group.health_check_type.should.equal("EC2")
list(group.load_balancers).should.equal([])
group.placement_group.should.equal(None)
list(group.termination_policies).should.equal([])
list(group.tags).should.equal([])
@mock_autoscaling
def test_create_autoscaling_groups_defaults_boto3():
"""Test with the minimum inputs and check that all of the proper defaults
@ -371,142 +229,6 @@ def test_propogate_tags():
tags.should.contain({"Value": "TestGroup1", "Key": "aws:autoscaling:groupName"})
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_autoscaling_group_describe_filter():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
group.name = "tester_group2"
conn.create_auto_scaling_group(group)
group.name = "tester_group3"
conn.create_auto_scaling_group(group)
conn.get_all_groups(names=["tester_group", "tester_group2"]).should.have.length_of(
2
)
conn.get_all_groups().should.have.length_of(3)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_autoscaling_update():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
desired_capacity=2,
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
group = conn.get_all_groups()[0]
group.availability_zones.should.equal(["us-east-1a"])
group.vpc_zone_identifier.should.equal(mocked_networking["subnet1"])
group.availability_zones = ["us-east-1b"]
group.vpc_zone_identifier = mocked_networking["subnet2"]
group.update()
group = conn.get_all_groups()[0]
group.availability_zones.should.equal(["us-east-1b"])
group.vpc_zone_identifier.should.equal(mocked_networking["subnet2"])
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_autoscaling_tags_update():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
availability_zones=["us-east-1a"],
desired_capacity=2,
max_size=2,
min_size=2,
launch_config=config,
tags=[
Tag(
resource_id="tester_group",
key="test_key",
value="test_value",
propagate_at_launch=True,
)
],
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
conn.create_or_update_tags(
tags=[
Tag(
resource_id="tester_group",
key="test_key",
value="new_test_value",
propagate_at_launch=True,
),
Tag(
resource_id="tester_group",
key="test_key2",
value="test_value2",
propagate_at_launch=True,
),
]
)
group = conn.get_all_groups()[0]
group.tags.should.have.length_of(2)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_autoscaling_group_delete():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
conn.get_all_groups().should.have.length_of(1)
conn.delete_auto_scaling_group("tester_group")
conn.get_all_groups().should.have.length_of(0)
@mock_autoscaling
def test_autoscaling_group_delete_boto3():
mocked_networking = setup_networking()
@ -535,197 +257,6 @@ def test_autoscaling_group_delete_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
@mock_autoscaling_deprecated
def test_autoscaling_group_describe_instances():
mocked_networking = setup_networking_deprecated()
conn = boto.ec2.autoscale.connect_to_region("us-east-1")
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(2)
instances[0].launch_config_name.should.equal("tester")
instances[0].health_status.should.equal("Healthy")
autoscale_instance_ids = [instance.instance_id for instance in instances]
ec2_conn = boto.ec2.connect_to_region("us-east-1")
reservations = ec2_conn.get_all_reservations()
instances = reservations[0].instances
instances.should.have.length_of(2)
instance_ids = [instance.id for instance in instances]
set(autoscale_instance_ids).should.equal(set(instance_ids))
instances[0].instance_type.should.equal("t2.medium")
# Has boto3 equivalent
@requires_boto_gte("2.8")
@mock_autoscaling_deprecated
def test_set_desired_capacity_up():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
availability_zones=["us-east-1a"],
desired_capacity=2,
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
group = conn.get_all_groups()[0]
group.desired_capacity.should.equal(2)
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(2)
conn.set_desired_capacity("tester_group", 3)
group = conn.get_all_groups()[0]
group.desired_capacity.should.equal(3)
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(3)
# Has boto3 equivalent
@requires_boto_gte("2.8")
@mock_autoscaling_deprecated
def test_set_desired_capacity_down():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
availability_zones=["us-east-1a"],
desired_capacity=2,
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
group = conn.get_all_groups()[0]
group.desired_capacity.should.equal(2)
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(2)
conn.set_desired_capacity("tester_group", 1)
group = conn.get_all_groups()[0]
group.desired_capacity.should.equal(1)
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(1)
# Has boto3 equivalent
@requires_boto_gte("2.8")
@mock_autoscaling_deprecated
def test_set_desired_capacity_the_same():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
availability_zones=["us-east-1a"],
desired_capacity=2,
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
group = conn.get_all_groups()[0]
group.desired_capacity.should.equal(2)
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(2)
conn.set_desired_capacity("tester_group", 2)
group = conn.get_all_groups()[0]
group.desired_capacity.should.equal(2)
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(2)
# Has boto3 equivalent
@mock_autoscaling_deprecated
@mock_elb_deprecated
def test_autoscaling_group_with_elb():
mocked_networking = setup_networking_deprecated()
elb_conn = boto.connect_elb()
zones = ["us-east-1a", "us-east-1b"]
ports = [(80, 8080, "http"), (443, 8443, "tcp")]
elb_conn.create_load_balancer("my-lb", zones, ports)
instances_health = elb_conn.describe_instance_health("my-lb")
instances_health.should.be.empty
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="t2.medium"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
max_size=2,
min_size=2,
launch_config=config,
load_balancers=["my-lb"],
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
group = conn.get_all_groups()[0]
elb = elb_conn.get_all_load_balancers()[0]
group.desired_capacity.should.equal(2)
elb.instances.should.have.length_of(2)
autoscale_instance_ids = set(instance.instance_id for instance in group.instances)
elb_instace_ids = set(instance.id for instance in elb.instances)
autoscale_instance_ids.should.equal(elb_instace_ids)
conn.set_desired_capacity("tester_group", 3)
group = conn.get_all_groups()[0]
elb = elb_conn.get_all_load_balancers()[0]
group.desired_capacity.should.equal(3)
elb.instances.should.have.length_of(3)
autoscale_instance_ids = set(instance.instance_id for instance in group.instances)
elb_instace_ids = set(instance.id for instance in elb.instances)
autoscale_instance_ids.should.equal(elb_instace_ids)
conn.delete_auto_scaling_group("tester_group")
conn.get_all_groups().should.have.length_of(0)
elb = elb_conn.get_all_load_balancers()[0]
elb.instances.should.have.length_of(0)
@mock_autoscaling
@mock_elb
def test_describe_load_balancers():

View File

@ -1,54 +1,15 @@
import base64
import boto
import boto3
from boto.ec2.autoscale.launchconfig import LaunchConfiguration
from boto.ec2.blockdevicemapping import BlockDeviceType, BlockDeviceMapping
from botocore.exceptions import ClientError
import pytest
import sure # noqa # pylint: disable=unused-import
from moto import mock_autoscaling_deprecated
from moto import mock_autoscaling
from moto.core import ACCOUNT_ID
from tests.helpers import requires_boto_gte
from tests import EXAMPLE_AMI_ID
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_create_launch_configuration():
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester",
image_id="ami-abcd1234",
instance_type="t1.micro",
key_name="the_keys",
security_groups=["default", "default2"],
user_data=b"This is some user_data",
instance_monitoring=True,
instance_profile_name="arn:aws:iam::{}:instance-profile/testing".format(
ACCOUNT_ID
),
spot_price=0.1,
)
conn.create_launch_configuration(config)
launch_config = conn.get_all_launch_configurations()[0]
launch_config.name.should.equal("tester")
launch_config.image_id.should.equal("ami-abcd1234")
launch_config.instance_type.should.equal("t1.micro")
launch_config.key_name.should.equal("the_keys")
set(launch_config.security_groups).should.equal(set(["default", "default2"]))
launch_config.user_data.should.equal(b"This is some user_data")
launch_config.instance_monitoring.enabled.should.equal("true")
launch_config.instance_profile_name.should.equal(
"arn:aws:iam::{}:instance-profile/testing".format(ACCOUNT_ID)
)
launch_config.spot_price.should.equal(0.1)
@mock_autoscaling
def test_create_launch_configuration_boto3():
client = boto3.client("autoscaling", region_name="us-east-1")
@ -84,76 +45,6 @@ def test_create_launch_configuration_boto3():
launch_config["BlockDeviceMappings"].should.equal([])
# Has boto3 equivalent
@requires_boto_gte("2.27.0")
@mock_autoscaling_deprecated
def test_create_launch_configuration_with_block_device_mappings():
block_device_mapping = BlockDeviceMapping()
ephemeral_drive = BlockDeviceType()
ephemeral_drive.ephemeral_name = "ephemeral0"
block_device_mapping["/dev/xvdb"] = ephemeral_drive
snapshot_drive = BlockDeviceType()
snapshot_drive.snapshot_id = "snap-1234abcd"
snapshot_drive.volume_type = "standard"
block_device_mapping["/dev/xvdp"] = snapshot_drive
ebs_drive = BlockDeviceType()
ebs_drive.volume_type = "io1"
ebs_drive.size = 100
ebs_drive.iops = 1000
ebs_drive.delete_on_termination = False
block_device_mapping["/dev/xvdh"] = ebs_drive
conn = boto.connect_autoscale(use_block_device_types=True)
config = LaunchConfiguration(
name="tester",
image_id="ami-abcd1234",
instance_type="m1.small",
key_name="the_keys",
security_groups=["default", "default2"],
user_data=b"This is some user_data",
instance_monitoring=True,
instance_profile_name="arn:aws:iam::{}:instance-profile/testing".format(
ACCOUNT_ID
),
spot_price=0.1,
block_device_mappings=[block_device_mapping],
)
conn.create_launch_configuration(config)
launch_config = conn.get_all_launch_configurations()[0]
launch_config.name.should.equal("tester")
launch_config.image_id.should.equal("ami-abcd1234")
launch_config.instance_type.should.equal("m1.small")
launch_config.key_name.should.equal("the_keys")
set(launch_config.security_groups).should.equal(set(["default", "default2"]))
launch_config.user_data.should.equal(b"This is some user_data")
launch_config.instance_monitoring.enabled.should.equal("true")
launch_config.instance_profile_name.should.equal(
"arn:aws:iam::{}:instance-profile/testing".format(ACCOUNT_ID)
)
launch_config.spot_price.should.equal(0.1)
len(launch_config.block_device_mappings).should.equal(3)
returned_mapping = launch_config.block_device_mappings
set(returned_mapping.keys()).should.equal(
set(["/dev/xvdb", "/dev/xvdp", "/dev/xvdh"])
)
returned_mapping["/dev/xvdh"].iops.should.equal(1000)
returned_mapping["/dev/xvdh"].size.should.equal(100)
returned_mapping["/dev/xvdh"].volume_type.should.equal("io1")
returned_mapping["/dev/xvdh"].delete_on_termination.should.be.false
returned_mapping["/dev/xvdp"].snapshot_id.should.equal("snap-1234abcd")
returned_mapping["/dev/xvdp"].volume_type.should.equal("standard")
returned_mapping["/dev/xvdb"].ephemeral_name.should.equal("ephemeral0")
@mock_autoscaling
def test_create_launch_configuration_with_block_device_mappings_boto3():
client = boto3.client("autoscaling", region_name="us-east-1")
@ -214,34 +105,6 @@ def test_create_launch_configuration_with_block_device_mappings_boto3():
xvdb.shouldnt.have.key("Ebs")
# Has boto3 equivalent
@requires_boto_gte("2.12")
@mock_autoscaling_deprecated
def test_create_launch_configuration_for_2_12():
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id="ami-abcd1234", ebs_optimized=True
)
conn.create_launch_configuration(config)
launch_config = conn.get_all_launch_configurations()[0]
launch_config.ebs_optimized.should.equal(True)
# Has boto3 equivalent
@requires_boto_gte("2.25.0")
@mock_autoscaling_deprecated
def test_create_launch_configuration_using_ip_association():
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id="ami-abcd1234", associate_public_ip_address=True
)
conn.create_launch_configuration(config)
launch_config = conn.get_all_launch_configurations()[0]
launch_config.associate_public_ip_address.should.equal(True)
@mock_autoscaling
def test_create_launch_configuration_additional_parameters():
client = boto3.client("autoscaling", region_name="us-east-1")
@ -258,18 +121,6 @@ def test_create_launch_configuration_additional_parameters():
launch_config["AssociatePublicIpAddress"].should.equal(True)
# Has boto3 equivalent
@requires_boto_gte("2.25.0")
@mock_autoscaling_deprecated
def test_create_launch_configuration_using_ip_association_should_default_to_false():
conn = boto.connect_autoscale()
config = LaunchConfiguration(name="tester", image_id="ami-abcd1234")
conn.create_launch_configuration(config)
launch_config = conn.get_all_launch_configurations()[0]
launch_config.associate_public_ip_address.should.equal(False)
@mock_autoscaling
def test_create_launch_configuration_additional_params_default_to_false():
client = boto3.client("autoscaling", region_name="us-east-1")
@ -284,31 +135,6 @@ def test_create_launch_configuration_additional_params_default_to_false():
launch_config["AssociatePublicIpAddress"].should.equal(False)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_create_launch_configuration_defaults():
"""Test with the minimum inputs and check that all of the proper defaults
are assigned for the other attributes"""
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id="ami-abcd1234", instance_type="m1.small"
)
conn.create_launch_configuration(config)
launch_config = conn.get_all_launch_configurations()[0]
launch_config.name.should.equal("tester")
launch_config.image_id.should.equal("ami-abcd1234")
launch_config.instance_type.should.equal("m1.small")
# Defaults
launch_config.key_name.should.equal("")
list(launch_config.security_groups).should.equal([])
launch_config.user_data.should.equal(b"")
launch_config.instance_monitoring.enabled.should.equal("false")
launch_config.instance_profile_name.should.equal(None)
launch_config.spot_price.should.equal(None)
@mock_autoscaling
def test_create_launch_configuration_defaults_boto3():
"""Test with the minimum inputs and check that all of the proper defaults
@ -331,37 +157,6 @@ def test_create_launch_configuration_defaults_boto3():
launch_config.shouldnt.have.key("SpotPrice")
# Has boto3 equivalent
@requires_boto_gte("2.12")
@mock_autoscaling_deprecated
def test_create_launch_configuration_defaults_for_2_12():
conn = boto.connect_autoscale()
config = LaunchConfiguration(name="tester", image_id="ami-abcd1234")
conn.create_launch_configuration(config)
launch_config = conn.get_all_launch_configurations()[0]
launch_config.ebs_optimized.should.equal(False)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_launch_configuration_describe_filter():
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id="ami-abcd1234", instance_type="m1.small"
)
conn.create_launch_configuration(config)
config.name = "tester2"
conn.create_launch_configuration(config)
config.name = "tester3"
conn.create_launch_configuration(config)
conn.get_all_launch_configurations(
names=["tester", "tester2"]
).should.have.length_of(2)
conn.get_all_launch_configurations().should.have.length_of(3)
@mock_autoscaling
def test_launch_configuration_describe_filter_boto3():
client = boto3.client("autoscaling", region_name="us-east-1")
@ -404,21 +199,6 @@ def test_launch_configuration_describe_paginated():
assert "NextToken" not in response2.keys()
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_launch_configuration_delete():
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id="ami-abcd1234", instance_type="m1.small"
)
conn.create_launch_configuration(config)
conn.get_all_launch_configurations().should.have.length_of(1)
conn.delete_launch_configuration("tester")
conn.get_all_launch_configurations().should.have.length_of(0)
@mock_autoscaling
def test_launch_configuration_delete_boto3():
client = boto3.client("autoscaling", region_name="us-east-1")

View File

@ -1,36 +1,13 @@
import boto
import boto3
from boto.ec2.autoscale.launchconfig import LaunchConfiguration
from boto.ec2.autoscale.group import AutoScalingGroup
from boto.ec2.autoscale.policy import ScalingPolicy
import sure # noqa # pylint: disable=unused-import
import pytest
from moto import mock_autoscaling_deprecated, mock_autoscaling
from moto import mock_autoscaling
from .utils import setup_networking_deprecated, setup_networking
from .utils import setup_networking
from tests import EXAMPLE_AMI_ID
def setup_autoscale_group():
mocked_networking = setup_networking_deprecated()
conn = boto.connect_autoscale()
config = LaunchConfiguration(
name="tester", image_id=EXAMPLE_AMI_ID, instance_type="m1.small"
)
conn.create_launch_configuration(config)
group = AutoScalingGroup(
name="tester_group",
max_size=2,
min_size=2,
launch_config=config,
vpc_zone_identifier=mocked_networking["subnet1"],
)
conn.create_auto_scaling_group(group)
return group
def setup_autoscale_group_boto3():
mocked_networking = setup_networking()
client = boto3.client("autoscaling", region_name="us-east-1")
@ -49,28 +26,6 @@ def setup_autoscale_group_boto3():
)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_create_policy():
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="ExactCapacity",
as_name="tester_group",
scaling_adjustment=3,
cooldown=60,
)
conn.create_scaling_policy(policy)
policy = conn.get_all_policies()[0]
policy.name.should.equal("ScaleUp")
policy.adjustment_type.should.equal("ExactCapacity")
policy.as_name.should.equal("tester_group")
policy.scaling_adjustment.should.equal(3)
policy.cooldown.should.equal(60)
@mock_autoscaling
def test_create_policy_boto3():
setup_autoscale_group_boto3()
@ -91,26 +46,6 @@ def test_create_policy_boto3():
policy["Cooldown"].should.equal(60)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_create_policy_default_values():
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="ExactCapacity",
as_name="tester_group",
scaling_adjustment=3,
)
conn.create_scaling_policy(policy)
policy = conn.get_all_policies()[0]
policy.name.should.equal("ScaleUp")
# Defaults
policy.cooldown.should.equal(300)
@mock_autoscaling
def test_create_policy_default_values_boto3():
setup_autoscale_group_boto3()
@ -129,34 +64,6 @@ def test_create_policy_default_values_boto3():
policy["Cooldown"].should.equal(300)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_update_policy():
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="ExactCapacity",
as_name="tester_group",
scaling_adjustment=3,
)
conn.create_scaling_policy(policy)
policy = conn.get_all_policies()[0]
policy.scaling_adjustment.should.equal(3)
# Now update it by creating another with the same name
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="ExactCapacity",
as_name="tester_group",
scaling_adjustment=2,
)
conn.create_scaling_policy(policy)
policy = conn.get_all_policies()[0]
policy.scaling_adjustment.should.equal(2)
@mock_autoscaling
def test_update_policy_boto3():
setup_autoscale_group_boto3()
@ -184,25 +91,6 @@ def test_update_policy_boto3():
policy["ScalingAdjustment"].should.equal(2)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_delete_policy():
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="ExactCapacity",
as_name="tester_group",
scaling_adjustment=3,
)
conn.create_scaling_policy(policy)
conn.get_all_policies().should.have.length_of(1)
conn.delete_policy("ScaleUp")
conn.get_all_policies().should.have.length_of(0)
@mock_autoscaling
def test_delete_policy_boto3():
setup_autoscale_group_boto3()
@ -220,25 +108,6 @@ def test_delete_policy_boto3():
client.describe_policies()["ScalingPolicies"].should.have.length_of(0)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_execute_policy_exact_capacity():
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="ExactCapacity",
as_name="tester_group",
scaling_adjustment=3,
)
conn.create_scaling_policy(policy)
conn.execute_policy("ScaleUp")
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(3)
@mock_autoscaling
def test_execute_policy_exact_capacity_boto3():
setup_autoscale_group_boto3()
@ -256,25 +125,6 @@ def test_execute_policy_exact_capacity_boto3():
instances["AutoScalingInstances"].should.have.length_of(3)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_execute_policy_positive_change_in_capacity():
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="ChangeInCapacity",
as_name="tester_group",
scaling_adjustment=3,
)
conn.create_scaling_policy(policy)
conn.execute_policy("ScaleUp")
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(5)
@mock_autoscaling
def test_execute_policy_positive_change_in_capacity_boto3():
setup_autoscale_group_boto3()
@ -292,25 +142,6 @@ def test_execute_policy_positive_change_in_capacity_boto3():
instances["AutoScalingInstances"].should.have.length_of(5)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_execute_policy_percent_change_in_capacity():
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="PercentChangeInCapacity",
as_name="tester_group",
scaling_adjustment=50,
)
conn.create_scaling_policy(policy)
conn.execute_policy("ScaleUp")
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(3)
@pytest.mark.parametrize(
"adjustment,nr_of_instances", [(1, 3), (50, 3), (100, 4), (250, 7)],
)
@ -332,25 +163,3 @@ def test_execute_policy_percent_change_in_capacity_boto3(adjustment, nr_of_insta
instances = client.describe_auto_scaling_instances()
instances["AutoScalingInstances"].should.have.length_of(nr_of_instances)
# Has boto3 equivalent
@mock_autoscaling_deprecated
def test_execute_policy_small_percent_change_in_capacity():
"""http://docs.aws.amazon.com/AutoScaling/latest/DeveloperGuide/as-scale-based-on-demand.html
If PercentChangeInCapacity returns a value between 0 and 1,
Auto Scaling will round it off to 1."""
setup_autoscale_group()
conn = boto.connect_autoscale()
policy = ScalingPolicy(
name="ScaleUp",
adjustment_type="PercentChangeInCapacity",
as_name="tester_group",
scaling_adjustment=1,
)
conn.create_scaling_policy(policy)
conn.execute_policy("ScaleUp")
instances = list(conn.get_all_autoscaling_instances())
instances.should.have.length_of(3)

View File

@ -1,6 +1,5 @@
import boto3
from boto import vpc as boto_vpc
from moto import mock_ec2, mock_ec2_deprecated
from moto import mock_ec2
@mock_ec2
@ -16,15 +15,6 @@ def setup_networking(region_name="us-east-1"):
return {"vpc": vpc.id, "subnet1": subnet1.id, "subnet2": subnet2.id}
@mock_ec2_deprecated
def setup_networking_deprecated():
conn = boto_vpc.connect_to_region("us-east-1")
vpc = conn.create_vpc("10.11.0.0/16")
subnet1 = conn.create_subnet(vpc.id, "10.11.1.0/24", availability_zone="us-east-1a")
subnet2 = conn.create_subnet(vpc.id, "10.11.2.0/24", availability_zone="us-east-1b")
return {"vpc": vpc.id, "subnet1": subnet1.id, "subnet2": subnet2.id}
@mock_ec2
def setup_instance_with_networking(image_id, instance_type):
mock_data = setup_networking()

View File

@ -1,772 +0,0 @@
import os
import json
import boto
import boto.dynamodb2
import boto.iam
import boto.s3
import boto.s3.key
import boto.cloudformation
from boto.exception import BotoServerError
import sure # noqa # pylint: disable=unused-import
from freezegun import freeze_time
import pytest
from moto import (
mock_cloudformation_deprecated,
mock_s3_deprecated,
mock_sns_deprecated,
mock_sqs_deprecated,
mock_route53_deprecated,
mock_iam_deprecated,
mock_dynamodb2_deprecated,
)
from moto.cloudformation import cloudformation_backends
dummy_template = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 1",
"Resources": {},
}
dummy_template2 = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 2",
"Resources": {},
}
# template with resource which has no delete attribute defined
dummy_template3 = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 3",
"Resources": {
"VPC": {"Properties": {"CidrBlock": "192.168.0.0/16"}, "Type": "AWS::EC2::VPC"}
},
}
dummy_template4 = {
"AWSTemplateFormatVersion": "2010-09-09",
"Resources": {
"myDynamoDBTable": {
"Type": "AWS::DynamoDB::Table",
"Properties": {
"AttributeDefinitions": [
{"AttributeName": "Name", "AttributeType": "S"},
{"AttributeName": "Age", "AttributeType": "S"},
],
"KeySchema": [
{"AttributeName": "Name", "KeyType": "HASH"},
{"AttributeName": "Age", "KeyType": "RANGE"},
],
"ProvisionedThroughput": {
"ReadCapacityUnits": 5,
"WriteCapacityUnits": 5,
},
"TableName": "Person",
},
}
},
}
dummy_template_json = json.dumps(dummy_template)
dummy_template_json2 = json.dumps(dummy_template2)
dummy_template_json3 = json.dumps(dummy_template3)
dummy_template_json4 = json.dumps(dummy_template4)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_create_stack():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
stack = conn.describe_stacks()[0]
stack.stack_id.should.contain(
"arn:aws:cloudformation:us-east-1:123456789:stack/test_stack/"
)
stack.stack_name.should.equal("test_stack")
stack.get_template().should.equal(
{
"GetTemplateResponse": {
"GetTemplateResult": {
"TemplateBody": dummy_template_json,
"ResponseMetadata": {
"RequestId": "2d06e36c-ac1d-11e0-a958-f9382b6eb86bEXAMPLE"
},
}
}
}
)
@mock_cloudformation_deprecated
def test_create_stack_with_other_region():
conn = boto.cloudformation.connect_to_region("us-west-2")
conn.create_stack("test_stack", template_body=dummy_template_json)
stack = conn.describe_stacks()[0]
stack.stack_id.should.contain(
"arn:aws:cloudformation:us-west-2:123456789:stack/test_stack/"
)
stack.stack_name.should.equal("test_stack")
stack.get_template().should.equal(
{
"GetTemplateResponse": {
"GetTemplateResult": {
"TemplateBody": dummy_template_json,
"ResponseMetadata": {
"RequestId": "2d06e36c-ac1d-11e0-a958-f9382b6eb86bEXAMPLE"
},
}
}
}
)
# Has boto3 equivalent
@mock_cloudformation_deprecated
@mock_route53_deprecated
def test_create_stack_hosted_zone_by_id():
conn = boto.connect_cloudformation()
dummy_template = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 1",
"Parameters": {},
"Resources": {
"Bar": {
"Type": "AWS::Route53::HostedZone",
"Properties": {"Name": "foo.bar.baz"},
}
},
}
dummy_template2 = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 2",
"Parameters": {"ZoneId": {"Type": "String"}},
"Resources": {
"Foo": {
"Properties": {"HostedZoneId": {"Ref": "ZoneId"}, "RecordSets": []},
"Type": "AWS::Route53::RecordSetGroup",
}
},
}
conn.create_stack(
"test_stack1", template_body=json.dumps(dummy_template), parameters={}.items()
)
r53_conn = boto.connect_route53()
zone_id = r53_conn.get_zones()[0].id
conn.create_stack(
"test_stack2",
template_body=json.dumps(dummy_template2),
parameters={"ZoneId": zone_id}.items(),
)
stack = conn.describe_stacks()[0]
assert stack.list_resources()
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_creating_stacks_across_regions():
west1_conn = boto.cloudformation.connect_to_region("us-west-1")
west1_conn.create_stack("test_stack", template_body=dummy_template_json)
west2_conn = boto.cloudformation.connect_to_region("us-west-2")
west2_conn.create_stack("test_stack", template_body=dummy_template_json)
list(west1_conn.describe_stacks()).should.have.length_of(1)
list(west2_conn.describe_stacks()).should.have.length_of(1)
# Has boto3 equivalent
@mock_cloudformation_deprecated
@mock_sns_deprecated
@mock_sqs_deprecated
def test_create_stack_with_notification_arn():
sqs_conn = boto.connect_sqs()
queue = sqs_conn.create_queue("fake-queue", visibility_timeout=3)
queue_arn = queue.get_attributes()["QueueArn"]
sns_conn = boto.connect_sns()
topic = sns_conn.create_topic("fake-topic")
topic_arn = topic["CreateTopicResponse"]["CreateTopicResult"]["TopicArn"]
sns_conn.subscribe(topic_arn, "sqs", queue_arn)
conn = boto.connect_cloudformation()
with freeze_time("2015-01-01 12:00:00"):
conn.create_stack(
"test_stack_with_notifications",
template_body=dummy_template_json,
notification_arns=topic_arn,
)
stack = conn.describe_stacks()[0]
[n.value for n in stack.notification_arns].should.contain(topic_arn)
with freeze_time("2015-01-01 12:00:01"):
message = queue.read(1)
msg = json.loads(message.get_body())
msg["Subject"].should.equal("AWS CloudFormation Notification")
msg["Message"].should.contain("StackId='{}'\n".format(stack.stack_id))
msg["Message"].should.contain("Timestamp='2015-01-01T12:00:00.000Z'\n")
msg["Message"].should.contain("LogicalResourceId='test_stack_with_notifications'\n")
msg["Message"].should.contain("ResourceStatus='CREATE_IN_PROGRESS'\n")
msg["Message"].should.contain("ResourceStatusReason='User Initiated'\n")
msg["Message"].should.contain("ResourceType='AWS::CloudFormation::Stack'\n")
msg["Message"].should.contain("StackName='test_stack_with_notifications'\n")
msg.should.have.key("MessageId")
msg.should.have.key("Signature")
msg.should.have.key("SignatureVersion")
msg.should.have.key("Subject")
msg["Timestamp"].should.equal("2015-01-01T12:00:00.000Z")
msg["TopicArn"].should.equal(topic_arn)
msg.should.have.key("Type")
msg.should.have.key("UnsubscribeURL")
with freeze_time("2015-01-01 12:00:02"):
message = queue.read(1)
msg = json.loads(message.get_body())
msg["Message"].should.contain("StackId='{}'\n".format(stack.stack_id))
msg["Message"].should.contain("Timestamp='2015-01-01T12:00:00.000Z'\n")
msg["Message"].should.contain("LogicalResourceId='test_stack_with_notifications'\n")
msg["Message"].should.contain("ResourceStatus='CREATE_COMPLETE'\n")
msg["Message"].should.contain("ResourceStatusReason='None'\n")
msg["Message"].should.contain("ResourceType='AWS::CloudFormation::Stack'\n")
msg["Message"].should.contain("StackName='test_stack_with_notifications'\n")
msg.should.have.key("MessageId")
msg.should.have.key("Signature")
msg.should.have.key("SignatureVersion")
msg.should.have.key("Subject")
msg["Timestamp"].should.equal("2015-01-01T12:00:00.000Z")
msg["TopicArn"].should.equal(topic_arn)
msg.should.have.key("Type")
msg.should.have.key("UnsubscribeURL")
# Has boto3 equivalent
@mock_cloudformation_deprecated
@mock_s3_deprecated
def test_create_stack_from_s3_url():
s3_conn = boto.s3.connect_to_region("us-west-1")
bucket = s3_conn.create_bucket("foobar", location="us-west-1")
key = boto.s3.key.Key(bucket)
key.key = "template-key"
key.set_contents_from_string(dummy_template_json)
key_url = key.generate_url(expires_in=0, query_auth=False)
conn = boto.cloudformation.connect_to_region("us-west-1")
conn.create_stack("new-stack", template_url=key_url)
stack = conn.describe_stacks()[0]
stack.stack_name.should.equal("new-stack")
stack.get_template().should.equal(
{
"GetTemplateResponse": {
"GetTemplateResult": {
"TemplateBody": dummy_template_json,
"ResponseMetadata": {
"RequestId": "2d06e36c-ac1d-11e0-a958-f9382b6eb86bEXAMPLE"
},
}
}
}
)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_describe_stack_by_name():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
stack = conn.describe_stacks("test_stack")[0]
stack.stack_name.should.equal("test_stack")
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_describe_stack_by_stack_id():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
stack = conn.describe_stacks("test_stack")[0]
stack_by_id = conn.describe_stacks(stack.stack_id)[0]
stack_by_id.stack_id.should.equal(stack.stack_id)
stack_by_id.stack_name.should.equal("test_stack")
@mock_dynamodb2_deprecated
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_delete_stack_dynamo_template():
conn = boto.connect_cloudformation()
db_conn = boto.dynamodb2.connect_to_region("us-east-1")
#
conn.create_stack("test_stack", template_body=dummy_template_json4)
db_conn.list_tables()["TableNames"].should.have.length_of(1)
#
conn.delete_stack("test_stack")
db_conn.list_tables()["TableNames"].should.have.length_of(0)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_describe_deleted_stack():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
stack = conn.describe_stacks("test_stack")[0]
stack_id = stack.stack_id
conn.delete_stack(stack.stack_id)
stack_by_id = conn.describe_stacks(stack_id)[0]
stack_by_id.stack_id.should.equal(stack.stack_id)
stack_by_id.stack_name.should.equal("test_stack")
stack_by_id.stack_status.should.equal("DELETE_COMPLETE")
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_get_template_by_name():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
template = conn.get_template("test_stack")
template.should.equal(
{
"GetTemplateResponse": {
"GetTemplateResult": {
"TemplateBody": dummy_template_json,
"ResponseMetadata": {
"RequestId": "2d06e36c-ac1d-11e0-a958-f9382b6eb86bEXAMPLE"
},
}
}
}
)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_list_stacks():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
conn.create_stack("test_stack2", template_body=dummy_template_json)
stacks = conn.list_stacks()
stacks.should.have.length_of(2)
stacks[0].template_description.should.equal("Stack 1")
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_list_stacks_with_filter():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
conn.create_stack("test_stack2", template_body=dummy_template_json)
conn.update_stack("test_stack", template_body=dummy_template_json2)
stacks = conn.list_stacks("CREATE_COMPLETE")
stacks.should.have.length_of(1)
stacks[0].template_description.should.equal("Stack 1")
stacks = conn.list_stacks("UPDATE_COMPLETE")
stacks.should.have.length_of(1)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_delete_stack_by_name():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
conn.describe_stacks().should.have.length_of(1)
conn.delete_stack("test_stack")
conn.describe_stacks().should.have.length_of(0)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_delete_stack_by_id():
conn = boto.connect_cloudformation()
stack_id = conn.create_stack("test_stack", template_body=dummy_template_json)
conn.describe_stacks().should.have.length_of(1)
conn.delete_stack(stack_id)
conn.describe_stacks().should.have.length_of(0)
with pytest.raises(BotoServerError):
conn.describe_stacks("test_stack")
conn.describe_stacks(stack_id).should.have.length_of(1)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_delete_stack_with_resource_missing_delete_attr():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json3)
conn.describe_stacks().should.have.length_of(1)
conn.delete_stack("test_stack")
conn.describe_stacks().should.have.length_of(0)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_bad_describe_stack():
conn = boto.connect_cloudformation()
with pytest.raises(BotoServerError):
conn.describe_stacks("bad_stack")
# Has boto3 equivalent
@mock_cloudformation_deprecated()
def test_cloudformation_params():
dummy_template = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 1",
"Resources": {},
"Parameters": {
"APPNAME": {
"Default": "app-name",
"Description": "The name of the app",
"Type": "String",
}
},
}
dummy_template_json = json.dumps(dummy_template)
cfn = boto.connect_cloudformation()
cfn.create_stack(
"test_stack1",
template_body=dummy_template_json,
parameters=[("APPNAME", "testing123")],
)
stack = cfn.describe_stacks("test_stack1")[0]
stack.parameters.should.have.length_of(1)
param = stack.parameters[0]
param.key.should.equal("APPNAME")
param.value.should.equal("testing123")
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_cloudformation_params_conditions_and_resources_are_distinct():
dummy_template = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 1",
"Conditions": {
"FooEnabled": {"Fn::Equals": [{"Ref": "FooEnabled"}, "true"]},
"FooDisabled": {
"Fn::Not": [{"Fn::Equals": [{"Ref": "FooEnabled"}, "true"]}]
},
},
"Parameters": {
"FooEnabled": {"Type": "String", "AllowedValues": ["true", "false"]}
},
"Resources": {
"Bar": {
"Properties": {"CidrBlock": "192.168.0.0/16"},
"Condition": "FooDisabled",
"Type": "AWS::EC2::VPC",
}
},
}
dummy_template_json = json.dumps(dummy_template)
cfn = boto.connect_cloudformation()
cfn.create_stack(
"test_stack1",
template_body=dummy_template_json,
parameters=[("FooEnabled", "true")],
)
stack = cfn.describe_stacks("test_stack1")[0]
resources = stack.list_resources()
assert not [
resource for resource in resources if resource.logical_resource_id == "Bar"
]
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_stack_tags():
conn = boto.connect_cloudformation()
conn.create_stack(
"test_stack",
template_body=dummy_template_json,
tags={"foo": "bar", "baz": "bleh"},
)
stack = conn.describe_stacks()[0]
dict(stack.tags).should.equal({"foo": "bar", "baz": "bleh"})
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_update_stack():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
conn.update_stack("test_stack", dummy_template_json2)
stack = conn.describe_stacks()[0]
stack.stack_status.should.equal("UPDATE_COMPLETE")
stack.get_template().should.equal(
{
"GetTemplateResponse": {
"GetTemplateResult": {
"TemplateBody": dummy_template_json2,
"ResponseMetadata": {
"RequestId": "2d06e36c-ac1d-11e0-a958-f9382b6eb86bEXAMPLE"
},
}
}
}
)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_update_stack_with_previous_template():
conn = boto.connect_cloudformation()
conn.create_stack("test_stack", template_body=dummy_template_json)
conn.update_stack("test_stack", use_previous_template=True)
stack = conn.describe_stacks()[0]
stack.stack_status.should.equal("UPDATE_COMPLETE")
stack.get_template().should.equal(
{
"GetTemplateResponse": {
"GetTemplateResult": {
"TemplateBody": dummy_template_json,
"ResponseMetadata": {
"RequestId": "2d06e36c-ac1d-11e0-a958-f9382b6eb86bEXAMPLE"
},
}
}
}
)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_update_stack_with_parameters():
dummy_template = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack",
"Resources": {
"VPC": {
"Properties": {"CidrBlock": {"Ref": "Bar"}},
"Type": "AWS::EC2::VPC",
}
},
"Parameters": {"Bar": {"Type": "String"}},
}
dummy_template_json = json.dumps(dummy_template)
conn = boto.connect_cloudformation()
conn.create_stack(
"test_stack",
template_body=dummy_template_json,
parameters=[("Bar", "192.168.0.0/16")],
)
conn.update_stack(
"test_stack",
template_body=dummy_template_json,
parameters=[("Bar", "192.168.0.1/16")],
)
stack = conn.describe_stacks()[0]
assert stack.parameters[0].value == "192.168.0.1/16"
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_update_stack_replace_tags():
conn = boto.connect_cloudformation()
conn.create_stack(
"test_stack", template_body=dummy_template_json, tags={"foo": "bar"}
)
conn.update_stack(
"test_stack", template_body=dummy_template_json, tags={"foo": "baz"}
)
stack = conn.describe_stacks()[0]
stack.stack_status.should.equal("UPDATE_COMPLETE")
# since there is one tag it doesn't come out as a list
dict(stack.tags).should.equal({"foo": "baz"})
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_update_stack_when_rolled_back():
conn = boto.connect_cloudformation()
stack_id = conn.create_stack("test_stack", template_body=dummy_template_json)
cloudformation_backends[conn.region.name].stacks[
stack_id
].status = "ROLLBACK_COMPLETE"
with pytest.raises(BotoServerError) as err:
conn.update_stack("test_stack", dummy_template_json)
ex = err.value
ex.body.should.match(r"is in ROLLBACK_COMPLETE state and can not be updated")
ex.error_code.should.equal("ValidationError")
ex.reason.should.equal("Bad Request")
ex.status.should.equal(400)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_describe_stack_events_shows_create_update_and_delete():
conn = boto.connect_cloudformation()
stack_id = conn.create_stack("test_stack", template_body=dummy_template_json)
conn.update_stack(stack_id, template_body=dummy_template_json2)
conn.delete_stack(stack_id)
# assert begins and ends with stack events
events = conn.describe_stack_events(stack_id)
events[0].resource_type.should.equal("AWS::CloudFormation::Stack")
events[-1].resource_type.should.equal("AWS::CloudFormation::Stack")
# testing ordering of stack events without assuming resource events will not exist
# the AWS API returns events in reverse chronological order
stack_events_to_look_for = iter(
[
("DELETE_COMPLETE", None),
("DELETE_IN_PROGRESS", "User Initiated"),
("UPDATE_COMPLETE", None),
("UPDATE_IN_PROGRESS", "User Initiated"),
("CREATE_COMPLETE", None),
("CREATE_IN_PROGRESS", "User Initiated"),
]
)
try:
for event in events:
event.stack_id.should.equal(stack_id)
event.stack_name.should.equal("test_stack")
event.event_id.should.match(r"[0-9a-f]{8}-([0-9a-f]{4}-){3}[0-9a-f]{12}")
if event.resource_type == "AWS::CloudFormation::Stack":
event.logical_resource_id.should.equal("test_stack")
event.physical_resource_id.should.equal(stack_id)
status_to_look_for, reason_to_look_for = next(stack_events_to_look_for)
event.resource_status.should.equal(status_to_look_for)
if reason_to_look_for is not None:
event.resource_status_reason.should.equal(reason_to_look_for)
except StopIteration:
assert False, "Too many stack events"
list(stack_events_to_look_for).should.be.empty
with pytest.raises(BotoServerError) as exp:
conn.describe_stack_events("non_existing_stack")
err = exp.value
err.message.should.equal("Stack with id non_existing_stack does not exist")
err.body.should.match(r"Stack with id non_existing_stack does not exist")
err.error_code.should.equal("ValidationError")
err.reason.should.equal("Bad Request")
err.status.should.equal(400)
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_create_stack_lambda_and_dynamodb():
conn = boto.connect_cloudformation()
dummy_template = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack Lambda Test 1",
"Parameters": {},
"Resources": {
"func1": {
"Type": "AWS::Lambda::Function",
"Properties": {
"Code": {"S3Bucket": "bucket_123", "S3Key": "key_123"},
"FunctionName": "func1",
"Handler": "handler.handler",
"Role": get_role_name(),
"Runtime": "python2.7",
"Description": "descr",
"MemorySize": 12345,
},
},
"func1version": {
"Type": "AWS::Lambda::Version",
"Properties": {"FunctionName": {"Ref": "func1"}},
},
"tab1": {
"Type": "AWS::DynamoDB::Table",
"Properties": {
"TableName": "tab1",
"KeySchema": [{"AttributeName": "attr1", "KeyType": "HASH"}],
"AttributeDefinitions": [
{"AttributeName": "attr1", "AttributeType": "string"}
],
"ProvisionedThroughput": {
"ReadCapacityUnits": 10,
"WriteCapacityUnits": 10,
},
"StreamSpecification": {"StreamViewType": "KEYS_ONLY"},
},
},
"func1mapping": {
"Type": "AWS::Lambda::EventSourceMapping",
"Properties": {
"FunctionName": {"Ref": "func1"},
"EventSourceArn": {"Fn::GetAtt": ["tab1", "StreamArn"]},
"StartingPosition": "0",
"BatchSize": 100,
"Enabled": True,
},
},
},
}
validate_s3_before = os.environ.get("VALIDATE_LAMBDA_S3", "")
try:
os.environ["VALIDATE_LAMBDA_S3"] = "false"
conn.create_stack(
"test_stack_lambda_1",
template_body=json.dumps(dummy_template),
parameters={}.items(),
)
finally:
os.environ["VALIDATE_LAMBDA_S3"] = validate_s3_before
stack = conn.describe_stacks()[0]
resources = stack.list_resources()
assert len(resources) == 4
# Has boto3 equivalent
@mock_cloudformation_deprecated
def test_create_stack_kinesis():
conn = boto.connect_cloudformation()
dummy_template = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack Kinesis Test 1",
"Parameters": {},
"Resources": {
"stream1": {
"Type": "AWS::Kinesis::Stream",
"Properties": {"Name": "stream1", "ShardCount": 2},
}
},
}
conn.create_stack(
"test_stack_kinesis_1",
template_body=json.dumps(dummy_template),
parameters={}.items(),
)
stack = conn.describe_stacks()[0]
resources = stack.list_resources()
assert len(resources) == 1
def get_role_name():
with mock_iam_deprecated():
iam = boto.connect_iam()
role = iam.create_role("my-role")["create_role_response"]["create_role_result"][
"role"
]["arn"]
return role

View File

@ -25,7 +25,6 @@ from moto import (
from moto import settings
from moto.core import ACCOUNT_ID
from moto.cloudformation import cloudformation_backends
from .test_cloudformation_stack_crud import dummy_template_json2, dummy_template_json4
from tests import EXAMPLE_AMI_ID
@ -48,6 +47,12 @@ dummy_template = {
},
}
dummy_template2 = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 2",
"Resources": {},
}
dummy_template3 = {
"AWSTemplateFormatVersion": "2010-09-09",
"Description": "Stack 3",
@ -56,6 +61,29 @@ dummy_template3 = {
},
}
dummy_template4 = {
"AWSTemplateFormatVersion": "2010-09-09",
"Resources": {
"myDynamoDBTable": {
"Type": "AWS::DynamoDB::Table",
"Properties": {
"AttributeDefinitions": [
{"AttributeName": "Name", "AttributeType": "S"},
{"AttributeName": "Age", "AttributeType": "S"},
],
"KeySchema": [
{"AttributeName": "Name", "KeyType": "HASH"},
{"AttributeName": "Age", "KeyType": "RANGE"},
],
"ProvisionedThroughput": {
"ReadCapacityUnits": 5,
"WriteCapacityUnits": 5,
},
"TableName": "Person",
},
}
},
}
dummy_template_with_parameters = {
"AWSTemplateFormatVersion": "2010-09-09",
@ -278,6 +306,8 @@ dummy_update_template_json = json.dumps(dummy_update_template)
dummy_output_template_json = json.dumps(dummy_output_template)
dummy_import_template_json = json.dumps(dummy_import_template)
dummy_redrive_template_json = json.dumps(dummy_redrive_template)
dummy_template_json2 = json.dumps(dummy_template2)
dummy_template_json4 = json.dumps(dummy_template4)
dummy_unknown_template_json = json.dumps(dummy_unknown_template)

View File

@ -1,4 +1,4 @@
from __future__ import absolute_import, division, print_function
from __future__ import absolute_import, division
# Standard library modules
import unittest

View File

@ -12,12 +12,12 @@ from moto.cloudformation.models import FakeStack
from moto.cloudformation.parsing import (
resource_class_from_type,
parse_condition,
Output,
)
from moto import mock_cloudformation, mock_sqs, mock_ssm, settings
from moto.sqs.models import Queue
from moto.s3.models import FakeBucket
from moto.cloudformation.utils import yaml_tag_constructor
from moto.packages.boto.cloudformation.stack import Output
dummy_template = {

View File

@ -1,225 +0,0 @@
import boto
from boto.ec2.cloudwatch.alarm import MetricAlarm
from boto.s3.key import Key
from datetime import datetime
import sure # noqa # pylint: disable=unused-import
from moto import mock_cloudwatch_deprecated, mock_s3_deprecated
def alarm_fixture(name="tester", action=None):
action = action or ["arn:alarm"]
return MetricAlarm(
name=name,
namespace="{0}_namespace".format(name),
metric="{0}_metric".format(name),
comparison=">=",
threshold=2.0,
period=60,
evaluation_periods=5,
statistic="Average",
description="A test",
dimensions={"InstanceId": ["i-0123456,i-0123457"]},
alarm_actions=action,
ok_actions=["arn:ok"],
insufficient_data_actions=["arn:insufficient"],
unit="Seconds",
)
# Has boto3 equivalent
@mock_cloudwatch_deprecated
def test_create_alarm():
conn = boto.connect_cloudwatch()
alarm = alarm_fixture()
conn.create_alarm(alarm)
alarms = conn.describe_alarms()
alarms.should.have.length_of(1)
alarm = alarms[0]
alarm.name.should.equal("tester")
alarm.namespace.should.equal("tester_namespace")
alarm.metric.should.equal("tester_metric")
alarm.comparison.should.equal(">=")
alarm.threshold.should.equal(2.0)
alarm.period.should.equal(60)
alarm.evaluation_periods.should.equal(5)
alarm.statistic.should.equal("Average")
alarm.description.should.equal("A test")
dict(alarm.dimensions).should.equal({"InstanceId": ["i-0123456,i-0123457"]})
list(alarm.alarm_actions).should.equal(["arn:alarm"])
list(alarm.ok_actions).should.equal(["arn:ok"])
list(alarm.insufficient_data_actions).should.equal(["arn:insufficient"])
alarm.unit.should.equal("Seconds")
assert "tester" in alarm.alarm_arn
# Has boto3 equivalent
@mock_cloudwatch_deprecated
def test_delete_alarm():
conn = boto.connect_cloudwatch()
alarms = conn.describe_alarms()
alarms.should.have.length_of(0)
alarm = alarm_fixture()
conn.create_alarm(alarm)
alarms = conn.describe_alarms()
alarms.should.have.length_of(1)
alarms[0].delete()
alarms = conn.describe_alarms()
alarms.should.have.length_of(0)
# Has boto3 equivalent
@mock_cloudwatch_deprecated
def test_put_metric_data():
conn = boto.connect_cloudwatch()
conn.put_metric_data(
namespace="tester",
name="metric",
value=1.5,
dimensions={"InstanceId": ["i-0123456,i-0123457"]},
)
metrics = conn.list_metrics()
metric_names = [m for m in metrics if m.name == "metric"]
metric_names.should.have(1)
metric = metrics[0]
metric.namespace.should.equal("tester")
metric.name.should.equal("metric")
dict(metric.dimensions).should.equal({"InstanceId": ["i-0123456,i-0123457"]})
# Has boto3 equivalent
@mock_cloudwatch_deprecated
def test_describe_alarms():
conn = boto.connect_cloudwatch()
alarms = conn.describe_alarms()
alarms.should.have.length_of(0)
conn.create_alarm(alarm_fixture(name="nfoobar", action="afoobar"))
conn.create_alarm(alarm_fixture(name="nfoobaz", action="afoobaz"))
conn.create_alarm(alarm_fixture(name="nbarfoo", action="abarfoo"))
conn.create_alarm(alarm_fixture(name="nbazfoo", action="abazfoo"))
enabled = alarm_fixture(name="enabled1", action=["abarfoo"])
enabled.add_alarm_action("arn:alarm")
conn.create_alarm(enabled)
alarms = conn.describe_alarms()
alarms.should.have.length_of(5)
alarms = conn.describe_alarms(alarm_name_prefix="nfoo")
alarms.should.have.length_of(2)
alarms = conn.describe_alarms(alarm_names=["nfoobar", "nbarfoo", "nbazfoo"])
alarms.should.have.length_of(3)
alarms = conn.describe_alarms(action_prefix="afoo")
alarms.should.have.length_of(2)
alarms = conn.describe_alarms(alarm_name_prefix="enabled")
alarms.should.have.length_of(1)
alarms[0].actions_enabled.should.equal("true")
for alarm in conn.describe_alarms():
alarm.delete()
alarms = conn.describe_alarms()
alarms.should.have.length_of(0)
# Has boto3 equivalent
@mock_cloudwatch_deprecated
def test_describe_alarms_for_metric():
conn = boto.connect_cloudwatch()
conn.create_alarm(alarm_fixture(name="nfoobar", action="afoobar"))
conn.create_alarm(alarm_fixture(name="nfoobaz", action="afoobaz"))
conn.create_alarm(alarm_fixture(name="nbarfoo", action="abarfoo"))
conn.create_alarm(alarm_fixture(name="nbazfoo", action="abazfoo"))
alarms = conn.describe_alarms_for_metric("nbarfoo_metric", "nbarfoo_namespace")
alarms.should.have.length_of(1)
alarms = conn.describe_alarms_for_metric("nbazfoo_metric", "nbazfoo_namespace")
alarms.should.have.length_of(1)
# Has boto3 equivalent
@mock_cloudwatch_deprecated
def test_get_metric_statistics():
conn = boto.connect_cloudwatch()
metric_timestamp = datetime(2018, 4, 9, 13, 0, 0, 0)
conn.put_metric_data(
namespace="tester",
name="metric",
value=1.5,
dimensions={"InstanceId": ["i-0123456,i-0123457"]},
timestamp=metric_timestamp,
unit="Count",
)
metric_kwargs = dict(
namespace="tester",
metric_name="metric",
start_time=metric_timestamp,
end_time=datetime.now(),
period=3600,
statistics=["Minimum"],
unit="Count",
)
datapoints = conn.get_metric_statistics(**metric_kwargs)
datapoints.should.have.length_of(1)
datapoint = datapoints[0]
datapoint.should.have.key("Minimum").which.should.equal(1.5)
datapoint.should.have.key("Timestamp").which.should.equal(metric_timestamp)
metric_kwargs = dict(
namespace="tester",
metric_name="metric",
start_time=metric_timestamp,
end_time=datetime.now(),
period=3600,
statistics=["Minimum"],
unit="Percent",
)
datapoints = conn.get_metric_statistics(**metric_kwargs)
datapoints.should.have.length_of(0)
@mock_s3_deprecated
@mock_cloudwatch_deprecated
def test_cloudwatch_return_s3_metrics():
region = "us-east-1"
cw = boto.ec2.cloudwatch.connect_to_region(region)
s3 = boto.s3.connect_to_region(region)
bucket_name_1 = "test-bucket-1"
bucket_name_2 = "test-bucket-2"
bucket1 = s3.create_bucket(bucket_name=bucket_name_1)
key = Key(bucket1)
key.key = "the-key"
key.set_contents_from_string("foobar" * 4)
s3.create_bucket(bucket_name=bucket_name_2)
metrics_s3_bucket_1 = cw.list_metrics(dimensions={"BucketName": bucket_name_1})
# Verify that the OOTB S3 metrics are available for the created buckets
len(metrics_s3_bucket_1).should.be(2)
metric_names = [m.name for m in metrics_s3_bucket_1]
sorted(metric_names).should.equal(["BucketSizeBytes", "NumberOfObjects"])
# Delete everything, to make sure it's not picked up in later tests
bucket1.delete_key("the-key")
s3.delete_bucket("test-bucket-1")
s3.delete_bucket("test-bucket-2")

View File

@ -24,10 +24,9 @@ def test_put_metric_data_no_dimensions():
)
metrics = conn.list_metrics()["Metrics"]
metrics.should.have.length_of(1)
metric = metrics[0]
metric["Namespace"].should.equal("tester")
metric["MetricName"].should.equal("metric")
metrics.should.contain(
{"Namespace": "tester", "MetricName": "metric", "Dimensions": []}
)
@mock_cloudwatch
@ -75,10 +74,9 @@ def test_put_metric_data_with_statistics():
)
metrics = conn.list_metrics()["Metrics"]
metrics.should.have.length_of(1)
metric = metrics[0]
metric["Namespace"].should.equal("tester")
metric["MetricName"].should.equal("statmetric")
metrics.should.contain(
{"Namespace": "tester", "MetricName": "statmetric", "Dimensions": []}
)
# TODO: test statistics - https://github.com/spulec/moto/issues/1615
@ -170,7 +168,6 @@ def test_get_metric_statistics_dimensions():
Statistics=["Average", "Sum"],
**params[0],
)
print(stats)
stats["Datapoints"].should.have.length_of(1)
datapoint = stats["Datapoints"][0]
datapoint["Sum"].should.equal(params[1])
@ -319,14 +316,14 @@ def test_list_metrics():
create_metrics(cloudwatch, namespace="list_test_2/", metrics=4, data_points=2)
# Verify we can retrieve everything
res = cloudwatch.list_metrics()["Metrics"]
len(res).should.equal(16) # 2 namespaces * 4 metrics * 2 data points
assert len(res) >= 16 # 2 namespaces * 4 metrics * 2 data points
# Verify we can filter by namespace/metric name
res = cloudwatch.list_metrics(Namespace="list_test_1/")["Metrics"]
len(res).should.equal(8) # 1 namespace * 4 metrics * 2 data points
res.should.have.length_of(8) # 1 namespace * 4 metrics * 2 data points
res = cloudwatch.list_metrics(Namespace="list_test_1/", MetricName="metric1")[
"Metrics"
]
len(res).should.equal(2) # 1 namespace * 1 metrics * 2 data points
res.should.have.length_of(2) # 1 namespace * 1 metrics * 2 data points
# Verify format
res.should.equal(
[
@ -353,29 +350,34 @@ def test_list_metrics_paginated():
# Add a boatload of metrics
create_metrics(cloudwatch, namespace="test", metrics=100, data_points=1)
# Verify that a single page is returned until we've reached 500
first_page = cloudwatch.list_metrics()
first_page = cloudwatch.list_metrics(Namespace="test")
first_page["Metrics"].shouldnt.be.empty
len(first_page["Metrics"]).should.equal(100)
create_metrics(cloudwatch, namespace="test", metrics=200, data_points=2)
first_page = cloudwatch.list_metrics()
first_page = cloudwatch.list_metrics(Namespace="test")
len(first_page["Metrics"]).should.equal(500)
first_page.shouldnt.contain("NextToken")
# Verify that adding more data points results in pagination
create_metrics(cloudwatch, namespace="test", metrics=60, data_points=10)
first_page = cloudwatch.list_metrics()
first_page = cloudwatch.list_metrics(Namespace="test")
len(first_page["Metrics"]).should.equal(500)
first_page["NextToken"].shouldnt.be.empty
# Retrieve second page - and verify there's more where that came from
second_page = cloudwatch.list_metrics(NextToken=first_page["NextToken"])
second_page = cloudwatch.list_metrics(
Namespace="test", NextToken=first_page["NextToken"]
)
len(second_page["Metrics"]).should.equal(500)
second_page.should.contain("NextToken")
# Last page should only have the last 100 results, and no NextToken (indicating that pagination is finished)
third_page = cloudwatch.list_metrics(NextToken=second_page["NextToken"])
third_page = cloudwatch.list_metrics(
Namespace="test", NextToken=second_page["NextToken"]
)
len(third_page["Metrics"]).should.equal(100)
third_page.shouldnt.contain("NextToken")
# Verify that we can't reuse an existing token
with pytest.raises(ClientError) as e:
cloudwatch.list_metrics(NextToken=first_page["NextToken"])
cloudwatch.list_metrics(Namespace="test", NextToken=first_page["NextToken"])
e.value.response["Error"]["Message"].should.equal(
"Request parameter NextToken is invalid"
)
@ -427,7 +429,7 @@ def test_list_metrics_with_same_dimensions_different_metric_name():
],
)
results = cloudwatch.list_metrics()["Metrics"]
results = cloudwatch.list_metrics(Namespace="unique/")["Metrics"]
results.should.have.length_of(2)
# duplicating existing metric
@ -443,7 +445,7 @@ def test_list_metrics_with_same_dimensions_different_metric_name():
)
# asserting only unique values are returned
results = cloudwatch.list_metrics()["Metrics"]
results = cloudwatch.list_metrics(Namespace="unique/")["Metrics"]
results.should.have.length_of(2)

View File

@ -1,60 +1,70 @@
import boto
from boto.exception import EC2ResponseError
import boto3
import sure # noqa # pylint: disable=unused-import
import os
import unittest
import pytest
from moto import mock_ec2_deprecated, mock_s3_deprecated
from botocore.exceptions import ClientError
from moto import mock_ec2, mock_s3, settings
from unittest import SkipTest
"""
Test the different ways that the decorator can be used
"""
@mock_ec2_deprecated
def test_basic_connect():
boto.connect_ec2()
@mock_ec2_deprecated
@mock_ec2
def test_basic_decorator():
conn = boto.connect_ec2("the_key", "the_secret")
list(conn.get_all_reservations()).should.equal([])
client = boto3.client("ec2", region_name="us-west-1")
client.describe_addresses()["Addresses"].should.equal([])
@pytest.fixture
def aws_credentials():
"""Mocked AWS Credentials for moto."""
os.environ["AWS_ACCESS_KEY_ID"] = "testing"
os.environ["AWS_SECRET_ACCESS_KEY"] = "testing"
os.environ["AWS_SECURITY_TOKEN"] = "testing"
os.environ["AWS_SESSION_TOKEN"] = "testing"
@pytest.mark.network
def test_context_manager():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError):
conn.get_all_reservations()
def test_context_manager(aws_credentials):
client = boto3.client("ec2", region_name="us-west-1")
with pytest.raises(ClientError) as exc:
client.describe_addresses()
err = exc.value.response["Error"]
err["Code"].should.equal("AuthFailure")
err["Message"].should.equal(
"AWS was not able to validate the provided access credentials"
)
with mock_ec2_deprecated():
conn = boto.connect_ec2("the_key", "the_secret")
list(conn.get_all_reservations()).should.equal([])
with pytest.raises(EC2ResponseError):
conn = boto.connect_ec2("the_key", "the_secret")
conn.get_all_reservations()
with mock_ec2():
client = boto3.client("ec2", region_name="us-west-1")
client.describe_addresses()["Addresses"].should.equal([])
@pytest.mark.network
def test_decorator_start_and_stop():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError):
conn.get_all_reservations()
mock = mock_ec2_deprecated()
if settings.TEST_SERVER_MODE:
raise SkipTest("Authentication always works in ServerMode")
mock = mock_ec2()
mock.start()
conn = boto.connect_ec2("the_key", "the_secret")
list(conn.get_all_reservations()).should.equal([])
client = boto3.client("ec2", region_name="us-west-1")
client.describe_addresses()["Addresses"].should.equal([])
mock.stop()
with pytest.raises(EC2ResponseError):
conn.get_all_reservations()
with pytest.raises(ClientError) as exc:
client.describe_addresses()
err = exc.value.response["Error"]
err["Code"].should.equal("AuthFailure")
err["Message"].should.equal(
"AWS was not able to validate the provided access credentials"
)
@mock_ec2_deprecated
@mock_ec2
def test_decorater_wrapped_gets_set():
"""
Moto decorator's __wrapped__ should get set to the tests function
@ -64,29 +74,32 @@ def test_decorater_wrapped_gets_set():
)
@mock_ec2_deprecated
@mock_ec2
class Tester(object):
def test_the_class(self):
conn = boto.connect_ec2()
list(conn.get_all_reservations()).should.have.length_of(0)
client = boto3.client("ec2", region_name="us-west-1")
client.describe_addresses()["Addresses"].should.equal([])
def test_still_the_same(self):
conn = boto.connect_ec2()
list(conn.get_all_reservations()).should.have.length_of(0)
client = boto3.client("ec2", region_name="us-west-1")
client.describe_addresses()["Addresses"].should.equal([])
@mock_s3_deprecated
@mock_s3
class TesterWithSetup(unittest.TestCase):
def setUp(self):
self.conn = boto.connect_s3()
self.conn.create_bucket("mybucket")
self.client = boto3.client("s3")
self.client.create_bucket(Bucket="mybucket")
def test_still_the_same(self):
bucket = self.conn.get_bucket("mybucket")
bucket.name.should.equal("mybucket")
buckets = self.client.list_buckets()["Buckets"]
bucket_names = [b["Name"] for b in buckets]
# There is a potential bug in the class-decorator, where the reset API is not called on start.
# This leads to a situation where 'bucket_names' may contain buckets created by earlier tests
bucket_names.should.contain("mybucket")
@mock_s3_deprecated
@mock_s3
class TesterWithStaticmethod(object):
@staticmethod
def static(*args):

View File

@ -1,38 +1,12 @@
import sure # noqa # pylint: disable=unused-import
import unittest
from boto.sqs.connection import SQSConnection
from boto.sqs.message import Message
from boto.ec2 import EC2Connection
import boto3
from moto import mock_sqs_deprecated, mock_ec2_deprecated
from moto import mock_sqs, mock_ec2
from tests import EXAMPLE_AMI_ID
class TestNestedDecorators(unittest.TestCase):
# Has boto3 equivalent
@mock_sqs_deprecated
def setup_sqs_queue(self):
conn = SQSConnection()
q = conn.create_queue("some-queue")
m = Message()
m.set_body("This is my first message.")
q.write(m)
self.assertEqual(q.count(), 1)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_nested(self):
self.setup_sqs_queue()
conn = EC2Connection()
conn.run_instances(EXAMPLE_AMI_ID)
class TestNestedDecoratorsBoto3(unittest.TestCase):
@mock_sqs
def setup_sqs_queue(self):

View File

@ -1,37 +1,9 @@
import unittest
from moto import mock_dynamodb2_deprecated, mock_dynamodb2
from moto import mock_dynamodb2
import socket
class TestSocketPair(unittest.TestCase):
@mock_dynamodb2_deprecated
def test_asyncio_deprecated(self):
self.assertIn(
"httpretty.core.fakesock.socket",
str(socket.socket),
"Our mock should be present",
)
import asyncio
self.assertIsNotNone(asyncio.get_event_loop())
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_socket_pair_deprecated(self):
self.assertIn(
"httpretty.core.fakesock.socket",
str(socket.socket),
"Our mock should be present",
)
a, b = socket.socketpair()
self.assertIsNotNone(a)
self.assertIsNotNone(b)
if a:
a.close()
if b:
b.close()
@mock_dynamodb2
def test_socket_pair(self):
a, b = socket.socketpair()

View File

@ -7,10 +7,7 @@ from moto import mock_s3
service_names = [
(d[5:], "")
for d in dir(moto)
if d.startswith("mock_")
and not d.endswith("_deprecated")
and not d == "mock_xray_client"
and not d == "mock_all"
if d.startswith("mock_") and not d == "mock_xray_client" and not d == "mock_all"
]

View File

@ -1,9 +1,7 @@
import boto.datapipeline
import sure # noqa # pylint: disable=unused-import
import boto3
import sure # noqa # pylint: disable=unused-import
from moto import mock_datapipeline
from moto import mock_datapipeline_deprecated
from moto.datapipeline.utils import remove_capitalization_of_dict_keys
@ -13,28 +11,6 @@ def get_value_from_fields(key, fields):
return field["stringValue"]
# Has boto3 equivalent
@mock_datapipeline_deprecated
def test_create_pipeline():
conn = boto.datapipeline.connect_to_region("us-west-2")
res = conn.create_pipeline("mypipeline", "some-unique-id")
pipeline_id = res["pipelineId"]
pipeline_descriptions = conn.describe_pipelines([pipeline_id])[
"pipelineDescriptionList"
]
pipeline_descriptions.should.have.length_of(1)
pipeline_description = pipeline_descriptions[0]
pipeline_description["name"].should.equal("mypipeline")
pipeline_description["pipelineId"].should.equal(pipeline_id)
fields = pipeline_description["fields"]
get_value_from_fields("@pipelineState", fields).should.equal("PENDING")
get_value_from_fields("uniqueId", fields).should.equal("some-unique-id")
@mock_datapipeline
def test_create_pipeline_boto3():
conn = boto3.client("datapipeline", region_name="us-west-2")
@ -85,25 +61,6 @@ PIPELINE_OBJECTS = [
]
# Has boto3 equivalent
@mock_datapipeline_deprecated
def test_creating_pipeline_definition():
conn = boto.datapipeline.connect_to_region("us-west-2")
res = conn.create_pipeline("mypipeline", "some-unique-id")
pipeline_id = res["pipelineId"]
conn.put_pipeline_definition(PIPELINE_OBJECTS, pipeline_id)
pipeline_definition = conn.get_pipeline_definition(pipeline_id)
pipeline_definition["pipelineObjects"].should.have.length_of(3)
default_object = pipeline_definition["pipelineObjects"][0]
default_object["name"].should.equal("Default")
default_object["id"].should.equal("Default")
default_object["fields"].should.equal(
[{"key": "workerGroup", "stringValue": "workerGroup"}]
)
@mock_datapipeline
def test_creating_pipeline_definition_boto3():
conn = boto3.client("datapipeline", region_name="us-west-2")
@ -124,27 +81,6 @@ def test_creating_pipeline_definition_boto3():
)
# Has boto3 equivalent
@mock_datapipeline_deprecated
def test_describing_pipeline_objects():
conn = boto.datapipeline.connect_to_region("us-west-2")
res = conn.create_pipeline("mypipeline", "some-unique-id")
pipeline_id = res["pipelineId"]
conn.put_pipeline_definition(PIPELINE_OBJECTS, pipeline_id)
objects = conn.describe_objects(["Schedule", "Default"], pipeline_id)[
"pipelineObjects"
]
objects.should.have.length_of(2)
default_object = [x for x in objects if x["id"] == "Default"][0]
default_object["name"].should.equal("Default")
default_object["fields"].should.equal(
[{"key": "workerGroup", "stringValue": "workerGroup"}]
)
@mock_datapipeline
def test_describing_pipeline_objects_boto3():
conn = boto3.client("datapipeline", region_name="us-west-2")
@ -167,26 +103,6 @@ def test_describing_pipeline_objects_boto3():
)
# Has boto3 equivalent
@mock_datapipeline_deprecated
def test_activate_pipeline():
conn = boto.datapipeline.connect_to_region("us-west-2")
res = conn.create_pipeline("mypipeline", "some-unique-id")
pipeline_id = res["pipelineId"]
conn.activate_pipeline(pipeline_id)
pipeline_descriptions = conn.describe_pipelines([pipeline_id])[
"pipelineDescriptionList"
]
pipeline_descriptions.should.have.length_of(1)
pipeline_description = pipeline_descriptions[0]
fields = pipeline_description["fields"]
get_value_from_fields("@pipelineState", fields).should.equal("SCHEDULED")
@mock_datapipeline
def test_activate_pipeline_boto3():
conn = boto3.client("datapipeline", region_name="us-west-2")
@ -205,20 +121,6 @@ def test_activate_pipeline_boto3():
get_value_from_fields("@pipelineState", fields).should.equal("SCHEDULED")
# Has boto3 equivalent
@mock_datapipeline_deprecated
def test_delete_pipeline():
conn = boto.datapipeline.connect_to_region("us-west-2")
res = conn.create_pipeline("mypipeline", "some-unique-id")
pipeline_id = res["pipelineId"]
conn.delete_pipeline(pipeline_id)
response = conn.list_pipelines()
response["pipelineIdList"].should.have.length_of(0)
@mock_datapipeline
def test_delete_pipeline_boto3():
conn = boto3.client("datapipeline", region_name="us-west-2")
@ -232,26 +134,6 @@ def test_delete_pipeline_boto3():
response["pipelineIdList"].should.have.length_of(0)
# Has boto3 equivalent
@mock_datapipeline_deprecated
def test_listing_pipelines():
conn = boto.datapipeline.connect_to_region("us-west-2")
res1 = conn.create_pipeline("mypipeline1", "some-unique-id1")
res2 = conn.create_pipeline("mypipeline2", "some-unique-id2")
response = conn.list_pipelines()
response["hasMoreResults"].should.be(False)
response["marker"].should.be.none
response["pipelineIdList"].should.have.length_of(2)
response["pipelineIdList"].should.contain(
{"id": res1["pipelineId"], "name": "mypipeline1"}
)
response["pipelineIdList"].should.contain(
{"id": res2["pipelineId"], "name": "mypipeline2"}
)
@mock_datapipeline
def test_listing_pipelines_boto3():
conn = boto3.client("datapipeline", region_name="us-west-2")
@ -271,20 +153,6 @@ def test_listing_pipelines_boto3():
)
# Has boto3 equivalent
@mock_datapipeline_deprecated
def test_listing_paginated_pipelines():
conn = boto.datapipeline.connect_to_region("us-west-2")
for i in range(100):
conn.create_pipeline("mypipeline%d" % i, "some-unique-id%d" % i)
response = conn.list_pipelines()
response["hasMoreResults"].should.be(True)
response["marker"].should.equal(response["pipelineIdList"][-1]["id"])
response["pipelineIdList"].should.have.length_of(50)
@mock_datapipeline
def test_listing_paginated_pipelines_boto3():
conn = boto3.client("datapipeline", region_name="us-west-2")

View File

@ -1,12 +1,7 @@
import boto
import boto.dynamodb
import sure # noqa # pylint: disable=unused-import
import pytest
from moto import mock_dynamodb, mock_dynamodb_deprecated
from moto.dynamodb import dynamodb_backend
from boto.exception import DynamoDBResponseError
from moto import mock_dynamodb
def test_deprecation_warning():
@ -15,45 +10,3 @@ def test_deprecation_warning():
str(record[0].message).should.contain(
"Module mock_dynamodb has been deprecated, and will be repurposed in a later release"
)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_list_tables():
name = "TestTable"
dynamodb_backend.create_table(name, hash_key_attr="name", hash_key_type="S")
conn = boto.connect_dynamodb("the_key", "the_secret")
assert conn.list_tables() == ["TestTable"]
@mock_dynamodb_deprecated
def test_list_tables_layer_1():
dynamodb_backend.create_table("test_1", hash_key_attr="name", hash_key_type="S")
dynamodb_backend.create_table("test_2", hash_key_attr="name", hash_key_type="S")
conn = boto.connect_dynamodb("the_key", "the_secret")
res = conn.layer1.list_tables(limit=1)
expected = {"TableNames": ["test_1"], "LastEvaluatedTableName": "test_1"}
res.should.equal(expected)
res = conn.layer1.list_tables(limit=1, start_table="test_1")
expected = {"TableNames": ["test_2"]}
res.should.equal(expected)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_describe_missing_table():
conn = boto.connect_dynamodb("the_key", "the_secret")
with pytest.raises(DynamoDBResponseError):
conn.describe_table("messages")
# Has boto3 equivalent
# This test is pointless though, as we treat DynamoDB as a global resource
@mock_dynamodb_deprecated
def test_dynamodb_with_connect_to_region():
# this will work if connected with boto.connect_dynamodb()
dynamodb = boto.dynamodb.connect_to_region("us-west-2")
schema = dynamodb.create_schema("column1", str(), "column2", int())
dynamodb.create_table("table1", schema, 200, 200)

View File

@ -1,485 +0,0 @@
import boto
import sure # noqa # pylint: disable=unused-import
from freezegun import freeze_time
from moto import mock_dynamodb_deprecated
from boto.dynamodb import condition
from boto.dynamodb.exceptions import DynamoDBKeyNotFoundError, DynamoDBValidationError
from boto.exception import DynamoDBResponseError
def create_table(conn):
message_table_schema = conn.create_schema(
hash_key_name="forum_name",
hash_key_proto_value=str,
range_key_name="subject",
range_key_proto_value=str,
)
table = conn.create_table(
name="messages", schema=message_table_schema, read_units=10, write_units=10
)
return table
# Has boto3 equivalent
@freeze_time("2012-01-14")
@mock_dynamodb_deprecated
def test_create_table():
conn = boto.connect_dynamodb()
create_table(conn)
expected = {
"Table": {
"CreationDateTime": 1326499200.0,
"ItemCount": 0,
"KeySchema": {
"HashKeyElement": {"AttributeName": "forum_name", "AttributeType": "S"},
"RangeKeyElement": {"AttributeName": "subject", "AttributeType": "S"},
},
"ProvisionedThroughput": {
"ReadCapacityUnits": 10,
"WriteCapacityUnits": 10,
},
"TableName": "messages",
"TableSizeBytes": 0,
"TableStatus": "ACTIVE",
}
}
conn.describe_table("messages").should.equal(expected)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_table():
conn = boto.connect_dynamodb()
create_table(conn)
conn.list_tables().should.have.length_of(1)
conn.layer1.delete_table("messages")
conn.list_tables().should.have.length_of(0)
conn.layer1.delete_table.when.called_with("messages").should.throw(
DynamoDBResponseError
)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_update_table_throughput():
conn = boto.connect_dynamodb()
table = create_table(conn)
table.read_units.should.equal(10)
table.write_units.should.equal(10)
table.update_throughput(5, 6)
table.refresh()
table.read_units.should.equal(5)
table.write_units.should.equal(6)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_item_add_and_describe_and_update():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(
hash_key="LOLCat Forum", range_key="Check this out!", attrs=item_data
)
item.put()
table.has_item("LOLCat Forum", "Check this out!").should.equal(True)
returned_item = table.get_item(
hash_key="LOLCat Forum",
range_key="Check this out!",
attributes_to_get=["Body", "SentBy"],
)
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"subject": "Check this out!",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
}
)
item["SentBy"] = "User B"
item.put()
returned_item = table.get_item(
hash_key="LOLCat Forum",
range_key="Check this out!",
attributes_to_get=["Body", "SentBy"],
)
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"subject": "Check this out!",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
}
)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_item_put_without_table():
conn = boto.connect_dynamodb()
conn.layer1.put_item.when.called_with(
table_name="undeclared-table",
item=dict(hash_key="LOLCat Forum", range_key="Check this out!"),
).should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_get_missing_item():
conn = boto.connect_dynamodb()
table = create_table(conn)
table.get_item.when.called_with(hash_key="tester", range_key="other").should.throw(
DynamoDBKeyNotFoundError
)
table.has_item("foobar", "more").should.equal(False)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_get_item_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.get_item.when.called_with(
table_name="undeclared-table",
key={"HashKeyElement": {"S": "tester"}, "RangeKeyElement": {"S": "test-range"}},
).should.throw(DynamoDBKeyNotFoundError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_get_item_without_range_key():
conn = boto.connect_dynamodb()
message_table_schema = conn.create_schema(
hash_key_name="test_hash",
hash_key_proto_value=int,
range_key_name="test_range",
range_key_proto_value=int,
)
table = conn.create_table(
name="messages", schema=message_table_schema, read_units=10, write_units=10
)
hash_key = 3241526475
range_key = 1234567890987
new_item = table.new_item(hash_key=hash_key, range_key=range_key)
new_item.put()
table.get_item.when.called_with(hash_key=hash_key).should.throw(
DynamoDBValidationError
)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_item():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(
hash_key="LOLCat Forum", range_key="Check this out!", attrs=item_data
)
item.put()
table.refresh()
table.item_count.should.equal(1)
response = item.delete()
response.should.equal({"Attributes": [], "ConsumedCapacityUnits": 0.5})
table.refresh()
table.item_count.should.equal(0)
item.delete.when.called_with().should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_item_with_attribute_response():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(
hash_key="LOLCat Forum", range_key="Check this out!", attrs=item_data
)
item.put()
table.refresh()
table.item_count.should.equal(1)
response = item.delete(return_values="ALL_OLD")
response.should.equal(
{
"Attributes": {
"Body": "http://url_to_lolcat.gif",
"forum_name": "LOLCat Forum",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"SentBy": "User A",
"subject": "Check this out!",
},
"ConsumedCapacityUnits": 0.5,
}
)
table.refresh()
table.item_count.should.equal(0)
item.delete.when.called_with().should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_item_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.delete_item.when.called_with(
table_name="undeclared-table",
key={"HashKeyElement": {"S": "tester"}, "RangeKeyElement": {"S": "test-range"}},
).should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_query():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="the-key", range_key="456", attrs=item_data)
item.put()
item = table.new_item(hash_key="the-key", range_key="123", attrs=item_data)
item.put()
item = table.new_item(hash_key="the-key", range_key="789", attrs=item_data)
item.put()
results = table.query(hash_key="the-key", range_key_condition=condition.GT("1"))
results.response["Items"].should.have.length_of(3)
results = table.query(hash_key="the-key", range_key_condition=condition.GT("234"))
results.response["Items"].should.have.length_of(2)
results = table.query(hash_key="the-key", range_key_condition=condition.GT("9999"))
results.response["Items"].should.have.length_of(0)
results = table.query(
hash_key="the-key", range_key_condition=condition.CONTAINS("12")
)
results.response["Items"].should.have.length_of(1)
results = table.query(
hash_key="the-key", range_key_condition=condition.BEGINS_WITH("7")
)
results.response["Items"].should.have.length_of(1)
results = table.query(
hash_key="the-key", range_key_condition=condition.BETWEEN("567", "890")
)
results.response["Items"].should.have.length_of(1)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_query_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.query.when.called_with(
table_name="undeclared-table",
hash_key_value={"S": "the-key"},
range_key_conditions={
"AttributeValueList": [{"S": "User B"}],
"ComparisonOperator": "EQ",
},
).should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_scan():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="the-key", range_key="456", attrs=item_data)
item.put()
item = table.new_item(hash_key="the-key", range_key="123", attrs=item_data)
item.put()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item = table.new_item(hash_key="the-key", range_key="789", attrs=item_data)
item.put()
results = table.scan()
results.response["Items"].should.have.length_of(3)
results = table.scan(scan_filter={"SentBy": condition.EQ("User B")})
results.response["Items"].should.have.length_of(1)
results = table.scan(scan_filter={"Body": condition.BEGINS_WITH("http")})
results.response["Items"].should.have.length_of(3)
results = table.scan(scan_filter={"Ids": condition.CONTAINS(2)})
results.response["Items"].should.have.length_of(1)
results = table.scan(scan_filter={"Ids": condition.NOT_NULL()})
results.response["Items"].should.have.length_of(1)
results = table.scan(scan_filter={"Ids": condition.NULL()})
results.response["Items"].should.have.length_of(2)
results = table.scan(scan_filter={"PK": condition.BETWEEN(8, 9)})
results.response["Items"].should.have.length_of(0)
results = table.scan(scan_filter={"PK": condition.BETWEEN(5, 8)})
results.response["Items"].should.have.length_of(1)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_scan_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.scan.when.called_with(
table_name="undeclared-table",
scan_filter={
"SentBy": {
"AttributeValueList": [{"S": "User B"}],
"ComparisonOperator": "EQ",
}
},
).should.throw(DynamoDBResponseError)
@mock_dynamodb_deprecated
def test_scan_after_has_item():
conn = boto.connect_dynamodb()
table = create_table(conn)
list(table.scan()).should.equal([])
table.has_item(hash_key="the-key", range_key="123")
list(table.scan()).should.equal([])
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_write_batch():
conn = boto.connect_dynamodb()
table = create_table(conn)
batch_list = conn.new_batch_write_list()
items = []
items.append(
table.new_item(
hash_key="the-key",
range_key="123",
attrs={
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
},
)
)
items.append(
table.new_item(
hash_key="the-key",
range_key="789",
attrs={
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
},
)
)
batch_list.add_batch(table, puts=items)
conn.batch_write_item(batch_list)
table.refresh()
table.item_count.should.equal(2)
batch_list = conn.new_batch_write_list()
batch_list.add_batch(table, deletes=[("the-key", "789")])
conn.batch_write_item(batch_list)
table.refresh()
table.item_count.should.equal(1)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_batch_read():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="the-key", range_key="456", attrs=item_data)
item.put()
item = table.new_item(hash_key="the-key", range_key="123", attrs=item_data)
item.put()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item = table.new_item(hash_key="another-key", range_key="789", attrs=item_data)
item.put()
items = table.batch_get_item([("the-key", "123"), ("another-key", "789")])
# Iterate through so that batch_item gets called
count = len([x for x in items])
count.should.equal(2)

View File

@ -1,405 +0,0 @@
import boto
import sure # noqa # pylint: disable=unused-import
from freezegun import freeze_time
from moto import mock_dynamodb_deprecated
from boto.dynamodb import condition
from boto.dynamodb.exceptions import DynamoDBKeyNotFoundError
from boto.exception import DynamoDBResponseError
def create_table(conn):
message_table_schema = conn.create_schema(
hash_key_name="forum_name", hash_key_proto_value=str
)
table = conn.create_table(
name="messages", schema=message_table_schema, read_units=10, write_units=10
)
return table
# Has boto3 equivalent
@freeze_time("2012-01-14")
@mock_dynamodb_deprecated
def test_create_table():
conn = boto.connect_dynamodb()
create_table(conn)
expected = {
"Table": {
"CreationDateTime": 1326499200.0,
"ItemCount": 0,
"KeySchema": {
"HashKeyElement": {"AttributeName": "forum_name", "AttributeType": "S"}
},
"ProvisionedThroughput": {
"ReadCapacityUnits": 10,
"WriteCapacityUnits": 10,
},
"TableName": "messages",
"TableSizeBytes": 0,
"TableStatus": "ACTIVE",
}
}
conn.describe_table("messages").should.equal(expected)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_table():
conn = boto.connect_dynamodb()
create_table(conn)
conn.list_tables().should.have.length_of(1)
conn.layer1.delete_table("messages")
conn.list_tables().should.have.length_of(0)
conn.layer1.delete_table.when.called_with("messages").should.throw(
DynamoDBResponseError
)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_update_table_throughput():
conn = boto.connect_dynamodb()
table = create_table(conn)
table.read_units.should.equal(10)
table.write_units.should.equal(10)
table.update_throughput(5, 6)
table.refresh()
table.read_units.should.equal(5)
table.write_units.should.equal(6)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_item_add_and_describe_and_update():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="LOLCat Forum", attrs=item_data)
item.put()
returned_item = table.get_item(
hash_key="LOLCat Forum", attributes_to_get=["Body", "SentBy"]
)
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
}
)
item["SentBy"] = "User B"
item.put()
returned_item = table.get_item(
hash_key="LOLCat Forum", attributes_to_get=["Body", "SentBy"]
)
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
}
)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_item_put_without_table():
conn = boto.connect_dynamodb()
conn.layer1.put_item.when.called_with(
table_name="undeclared-table", item=dict(hash_key="LOLCat Forum")
).should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_get_missing_item():
conn = boto.connect_dynamodb()
table = create_table(conn)
table.get_item.when.called_with(hash_key="tester").should.throw(
DynamoDBKeyNotFoundError
)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_get_item_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.get_item.when.called_with(
table_name="undeclared-table", key={"HashKeyElement": {"S": "tester"}}
).should.throw(DynamoDBKeyNotFoundError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_item():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="LOLCat Forum", attrs=item_data)
item.put()
table.refresh()
table.item_count.should.equal(1)
response = item.delete()
response.should.equal({"Attributes": [], "ConsumedCapacityUnits": 0.5})
table.refresh()
table.item_count.should.equal(0)
item.delete.when.called_with().should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_item_with_attribute_response():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="LOLCat Forum", attrs=item_data)
item.put()
table.refresh()
table.item_count.should.equal(1)
response = item.delete(return_values="ALL_OLD")
response.should.equal(
{
"Attributes": {
"Body": "http://url_to_lolcat.gif",
"forum_name": "LOLCat Forum",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"SentBy": "User A",
},
"ConsumedCapacityUnits": 0.5,
}
)
table.refresh()
table.item_count.should.equal(0)
item.delete.when.called_with().should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_delete_item_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.delete_item.when.called_with(
table_name="undeclared-table", key={"HashKeyElement": {"S": "tester"}}
).should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_query():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="the-key", attrs=item_data)
item.put()
results = table.query(hash_key="the-key")
results.response["Items"].should.have.length_of(1)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_query_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.query.when.called_with(
table_name="undeclared-table", hash_key_value={"S": "the-key"}
).should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_scan():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="the-key", attrs=item_data)
item.put()
item = table.new_item(hash_key="the-key2", attrs=item_data)
item.put()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item = table.new_item(hash_key="the-key3", attrs=item_data)
item.put()
results = table.scan()
results.response["Items"].should.have.length_of(3)
results = table.scan(scan_filter={"SentBy": condition.EQ("User B")})
results.response["Items"].should.have.length_of(1)
results = table.scan(scan_filter={"Body": condition.BEGINS_WITH("http")})
results.response["Items"].should.have.length_of(3)
results = table.scan(scan_filter={"Ids": condition.CONTAINS(2)})
results.response["Items"].should.have.length_of(1)
results = table.scan(scan_filter={"Ids": condition.NOT_NULL()})
results.response["Items"].should.have.length_of(1)
results = table.scan(scan_filter={"Ids": condition.NULL()})
results.response["Items"].should.have.length_of(2)
results = table.scan(scan_filter={"PK": condition.BETWEEN(8, 9)})
results.response["Items"].should.have.length_of(0)
results = table.scan(scan_filter={"PK": condition.BETWEEN(5, 8)})
results.response["Items"].should.have.length_of(1)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_scan_with_undeclared_table():
conn = boto.connect_dynamodb()
conn.layer1.scan.when.called_with(
table_name="undeclared-table",
scan_filter={
"SentBy": {
"AttributeValueList": [{"S": "User B"}],
"ComparisonOperator": "EQ",
}
},
).should.throw(DynamoDBResponseError)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_scan_after_has_item():
conn = boto.connect_dynamodb()
table = create_table(conn)
list(table.scan()).should.equal([])
table.has_item("the-key")
list(table.scan()).should.equal([])
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_write_batch():
conn = boto.connect_dynamodb()
table = create_table(conn)
batch_list = conn.new_batch_write_list()
items = []
items.append(
table.new_item(
hash_key="the-key",
attrs={
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
},
)
)
items.append(
table.new_item(
hash_key="the-key2",
attrs={
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
},
)
)
batch_list.add_batch(table, puts=items)
conn.batch_write_item(batch_list)
table.refresh()
table.item_count.should.equal(2)
batch_list = conn.new_batch_write_list()
batch_list.add_batch(table, deletes=[("the-key")])
conn.batch_write_item(batch_list)
table.refresh()
table.item_count.should.equal(1)
# Has boto3 equivalent
@mock_dynamodb_deprecated
def test_batch_read():
conn = boto.connect_dynamodb()
table = create_table(conn)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = table.new_item(hash_key="the-key1", attrs=item_data)
item.put()
item = table.new_item(hash_key="the-key2", attrs=item_data)
item.put()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item = table.new_item(hash_key="another-key", attrs=item_data)
item.put()
items = table.batch_get_item([("the-key1"), ("another-key")])
# Iterate through so that batch_item gets called
count = len([x for x in items])
count.should.have.equal(2)

View File

@ -1,53 +1,20 @@
from __future__ import print_function
import uuid
from datetime import datetime
from decimal import Decimal
import boto
import boto3
from boto3.dynamodb.conditions import Attr, Key
import re
import sure # noqa # pylint: disable=unused-import
from moto import mock_dynamodb2, mock_dynamodb2_deprecated
from moto.dynamodb2 import dynamodb_backend2, dynamodb_backends2
from boto.exception import JSONResponseError
from moto import mock_dynamodb2
from moto.dynamodb2 import dynamodb_backends2
from botocore.exceptions import ClientError
from tests.helpers import requires_boto_gte
import moto.dynamodb2.comparisons
import moto.dynamodb2.models
import pytest
try:
import boto.dynamodb2
except ImportError:
print("This boto version is not supported")
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_list_tables():
name = "TestTable"
# Should make tables properly with boto
dynamodb_backend2.create_table(
name,
attr=[
{"AttributeType": "S", "AttributeName": "forum_name"},
{"AttributeType": "S", "AttributeName": "subject"},
],
schema=[
{"KeyType": "HASH", "AttributeName": "forum_name"},
{"KeyType": "RANGE", "AttributeName": "subject"},
],
)
conn = boto.dynamodb2.connect_to_region(
"us-east-1", aws_access_key_id="ak", aws_secret_access_key="sk"
)
assert conn.list_tables()["TableNames"] == [name]
@mock_dynamodb2
@pytest.mark.parametrize(
@ -67,34 +34,6 @@ def test_list_tables_boto3(names):
conn.list_tables()["TableNames"].should.equal(names)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_list_tables_layer_1():
# Should make tables properly with boto
dynamodb_backend2.create_table(
"test_1",
attr=[{"AttributeType": "S", "AttributeName": "name"},],
schema=[{"KeyType": "HASH", "AttributeName": "name"}],
)
dynamodb_backend2.create_table(
"test_2",
attr=[{"AttributeType": "S", "AttributeName": "name"}],
schema=[{"KeyType": "HASH", "AttributeName": "name"}],
)
conn = boto.dynamodb2.connect_to_region(
"us-east-1", aws_access_key_id="ak", aws_secret_access_key="sk"
)
res = conn.list_tables(limit=1)
expected = {"TableNames": ["test_1"], "LastEvaluatedTableName": "test_1"}
res.should.equal(expected)
res = conn.list_tables(limit=1, exclusive_start_table_name="test_1")
expected = {"TableNames": ["test_2"]}
res.should.equal(expected)
@mock_dynamodb2
def test_list_tables_paginated():
conn = boto3.client("dynamodb", region_name="us-west-2")
@ -119,17 +58,6 @@ def test_list_tables_paginated():
res.shouldnt.have.key("LastEvaluatedTableName")
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_describe_missing_table():
conn = boto.dynamodb2.connect_to_region(
"us-west-2", aws_access_key_id="ak", aws_secret_access_key="sk"
)
with pytest.raises(JSONResponseError):
conn.describe_table("messages")
@mock_dynamodb2
def test_describe_missing_table_boto3():
conn = boto3.client("dynamodb", region_name="us-west-2")
@ -140,7 +68,6 @@ def test_describe_missing_table_boto3():
ex.value.response["Error"]["Message"].should.equal("Requested resource not found")
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_list_table_tags():
name = "TestTable"
@ -178,7 +105,6 @@ def test_list_table_tags():
assert resp["Tags"] == [{"Key": "TestTag2", "Value": "TestValue2"}]
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_list_table_tags_empty():
name = "TestTable"
@ -200,7 +126,6 @@ def test_list_table_tags_empty():
assert resp["Tags"] == []
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_list_table_tags_paginated():
name = "TestTable"
@ -229,7 +154,6 @@ def test_list_table_tags_paginated():
assert "NextToken" not in resp2.keys()
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_list_not_found_table_tags():
conn = boto3.client(
@ -384,7 +308,6 @@ def test_update_item_with_empty_string_attr_no_exception():
)
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_query_invalid_table():
conn = boto3.client(
@ -403,7 +326,6 @@ def test_query_invalid_table():
assert exception.response["Error"]["Code"] == "ResourceNotFoundException"
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_put_item_with_special_chars():
name = "TestTable"
@ -434,7 +356,6 @@ def test_put_item_with_special_chars():
)
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_put_item_with_streams():
name = "TestTable"
@ -3513,7 +3434,6 @@ def test_update_supports_list_append_maps():
)
@requires_boto_gte("2.9")
@mock_dynamodb2
def test_update_supports_nested_update_if_nested_value_not_exists():
dynamodb = boto3.resource("dynamodb", region_name="us-east-1")

View File

@ -1,94 +1,15 @@
from decimal import Decimal
import boto
import boto3
from boto3.dynamodb.conditions import Key
from botocore.exceptions import ClientError
import sure # noqa # pylint: disable=unused-import
from datetime import datetime
from freezegun import freeze_time
import pytest
from moto import mock_dynamodb2, mock_dynamodb2_deprecated
from boto.exception import JSONResponseError
from tests.helpers import requires_boto_gte
from moto import mock_dynamodb2
from uuid import uuid4
try:
from boto.dynamodb2.fields import GlobalAllIndex, HashKey, RangeKey, AllIndex
from boto.dynamodb2.table import Item, Table
from boto.dynamodb2.types import STRING, NUMBER
from boto.dynamodb2.exceptions import ValidationException
from boto.dynamodb2.exceptions import ConditionalCheckFailedException
except ImportError:
pass
def create_table():
table = Table.create(
"messages",
schema=[HashKey("forum_name"), RangeKey("subject")],
throughput={"read": 10, "write": 10},
)
return table
def create_table_with_local_indexes():
table = Table.create(
"messages",
schema=[HashKey("forum_name"), RangeKey("subject")],
throughput={"read": 10, "write": 10},
indexes=[
AllIndex(
"threads_index",
parts=[
HashKey("forum_name", data_type=STRING),
RangeKey("threads", data_type=NUMBER),
],
)
],
)
return table
def iterate_results(res):
for _ in res:
pass
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
@freeze_time("2012-01-14")
def test_create_table():
table = create_table()
expected = {
"Table": {
"AttributeDefinitions": [
{"AttributeName": "forum_name", "AttributeType": "S"},
{"AttributeName": "subject", "AttributeType": "S"},
],
"ProvisionedThroughput": {
"NumberOfDecreasesToday": 0,
"WriteCapacityUnits": 10,
"ReadCapacityUnits": 10,
},
"TableSizeBytes": 0,
"TableName": "messages",
"TableStatus": "ACTIVE",
"TableArn": "arn:aws:dynamodb:us-east-1:123456789011:table/messages",
"KeySchema": [
{"KeyType": "HASH", "AttributeName": "forum_name"},
{"KeyType": "RANGE", "AttributeName": "subject"},
],
"LocalSecondaryIndexes": [],
"ItemCount": 0,
"CreationDateTime": 1326499200.0,
"GlobalSecondaryIndexes": [],
}
}
table.describe().should.equal(expected)
@mock_dynamodb2
def test_create_table_boto3():
@ -134,50 +55,6 @@ def test_create_table_boto3():
actual.should.have.key("ItemCount").equal(0)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
@freeze_time("2012-01-14")
def test_create_table_with_local_index():
table = create_table_with_local_indexes()
expected = {
"Table": {
"AttributeDefinitions": [
{"AttributeName": "forum_name", "AttributeType": "S"},
{"AttributeName": "subject", "AttributeType": "S"},
{"AttributeName": "threads", "AttributeType": "N"},
],
"ProvisionedThroughput": {
"NumberOfDecreasesToday": 0,
"WriteCapacityUnits": 10,
"ReadCapacityUnits": 10,
},
"TableSizeBytes": 0,
"TableName": "messages",
"TableStatus": "ACTIVE",
"TableArn": "arn:aws:dynamodb:us-east-1:123456789011:table/messages",
"KeySchema": [
{"KeyType": "HASH", "AttributeName": "forum_name"},
{"KeyType": "RANGE", "AttributeName": "subject"},
],
"LocalSecondaryIndexes": [
{
"IndexName": "threads_index",
"KeySchema": [
{"AttributeName": "forum_name", "KeyType": "HASH"},
{"AttributeName": "threads", "KeyType": "RANGE"},
],
"Projection": {"ProjectionType": "ALL"},
}
],
"ItemCount": 0,
"CreationDateTime": 1326499200.0,
"GlobalSecondaryIndexes": [],
}
}
table.describe().should.equal(expected)
@mock_dynamodb2
def test_create_table_with_local_index_boto3():
client = boto3.client("dynamodb", region_name="us-east-1")
@ -245,169 +122,6 @@ def test_create_table_with_local_index_boto3():
actual.should.have.key("ItemCount").equal(0)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_delete_table():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
table = create_table()
conn.list_tables()["TableNames"].should.have.length_of(1)
table.delete()
conn.list_tables()["TableNames"].should.have.length_of(0)
conn.delete_table.when.called_with("messages").should.throw(JSONResponseError)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_update_table_throughput():
table = create_table()
table.throughput["read"].should.equal(10)
table.throughput["write"].should.equal(10)
table.update(throughput={"read": 5, "write": 15})
table.throughput["read"].should.equal(5)
table.throughput["write"].should.equal(15)
table.update(throughput={"read": 5, "write": 6})
table.describe()
table.throughput["read"].should.equal(5)
table.throughput["write"].should.equal(6)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_item_add_and_describe_and_update():
table = create_table()
ok = table.put_item(
data={
"forum_name": "LOLCat Forum",
"subject": "Check this out!",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
)
ok.should.equal(True)
table.get_item(
forum_name="LOLCat Forum", subject="Check this out!"
).should_not.be.none
returned_item = table.get_item(forum_name="LOLCat Forum", subject="Check this out!")
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"subject": "Check this out!",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
)
returned_item["SentBy"] = "User B"
returned_item.save(overwrite=True)
returned_item = table.get_item(forum_name="LOLCat Forum", subject="Check this out!")
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"subject": "Check this out!",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_item_partial_save():
table = create_table()
data = {
"forum_name": "LOLCat Forum",
"subject": "The LOLz",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
}
table.put_item(data=data)
returned_item = table.get_item(forum_name="LOLCat Forum", subject="The LOLz")
returned_item["SentBy"] = "User B"
returned_item.partial_save()
returned_item = table.get_item(forum_name="LOLCat Forum", subject="The LOLz")
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"subject": "The LOLz",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
}
)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_item_put_without_table():
table = Table("undeclared-table")
item_data = {
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = Item(table, item_data)
item.save.when.called_with().should.throw(JSONResponseError)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_missing_item():
table = create_table()
table.get_item.when.called_with(hash_key="tester", range_key="other").should.throw(
ValidationException
)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_item_with_undeclared_table():
table = Table("undeclared-table")
table.get_item.when.called_with(test_hash=3241526475).should.throw(
JSONResponseError
)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_item_without_range_key():
table = Table.create(
"messages",
schema=[HashKey("test_hash"), RangeKey("test_range")],
throughput={"read": 10, "write": 10},
)
hash_key = "3241526475"
range_key = "1234567890987"
table.put_item(data={"test_hash": hash_key, "test_range": range_key})
table.get_item.when.called_with(test_hash=hash_key).should.throw(
ValidationException
)
@mock_dynamodb2
def test_get_item_without_range_key_boto3():
client = boto3.resource("dynamodb", region_name="us-east-1")
@ -435,544 +149,6 @@ def test_get_item_without_range_key_boto3():
ex.value.response["Error"]["Message"].should.equal("Validation Exception")
@requires_boto_gte("2.30.0")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_delete_item():
table = create_table()
item_data = {
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = Item(table, item_data)
item["subject"] = "Check this out!"
item.save()
table.count().should.equal(1)
response = item.delete()
response.should.equal(True)
table.count().should.equal(0)
# Deletes are idempotent
item.delete().should.equal(True)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_delete_item_with_undeclared_table():
table = Table("undeclared-table")
item_data = {
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = Item(table, item_data)
item.delete.when.called_with().should.throw(JSONResponseError)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query():
table = create_table()
item_data = {
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"subject": "Check this out!",
}
item = Item(table, item_data)
item.save(overwrite=True)
item["forum_name"] = "the-key"
item["subject"] = "456"
item.save(overwrite=True)
item["forum_name"] = "the-key"
item["subject"] = "123"
item.save(overwrite=True)
item["forum_name"] = "the-key"
item["subject"] = "789"
item.save(overwrite=True)
table.count().should.equal(4)
results = table.query_2(forum_name__eq="the-key", subject__gt="1", consistent=True)
expected = ["123", "456", "789"]
for index, item in enumerate(results):
item["subject"].should.equal(expected[index])
results = table.query_2(forum_name__eq="the-key", subject__gt="1", reverse=True)
for index, item in enumerate(results):
item["subject"].should.equal(expected[len(expected) - 1 - index])
results = table.query_2(forum_name__eq="the-key", subject__gt="1", consistent=True)
sum(1 for _ in results).should.equal(3)
results = table.query_2(
forum_name__eq="the-key", subject__gt="234", consistent=True
)
sum(1 for _ in results).should.equal(2)
results = table.query_2(forum_name__eq="the-key", subject__gt="9999")
sum(1 for _ in results).should.equal(0)
results = table.query_2(forum_name__eq="the-key", subject__beginswith="12")
sum(1 for _ in results).should.equal(1)
results = table.query_2(forum_name__eq="the-key", subject__beginswith="7")
sum(1 for _ in results).should.equal(1)
results = table.query_2(forum_name__eq="the-key", subject__between=["567", "890"])
sum(1 for _ in results).should.equal(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_with_undeclared_table():
table = Table("undeclared")
results = table.query(
forum_name__eq="Amazon DynamoDB", subject__beginswith="DynamoDB", limit=1
)
iterate_results.when.called_with(results).should.throw(JSONResponseError)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_scan():
table = create_table()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item_data["forum_name"] = "the-key"
item_data["subject"] = "456"
item = Item(table, item_data)
item.save()
item["forum_name"] = "the-key"
item["subject"] = "123"
item.save()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:09 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item_data["forum_name"] = "the-key"
item_data["subject"] = "789"
item = Item(table, item_data)
item.save()
results = table.scan()
sum(1 for _ in results).should.equal(3)
results = table.scan(SentBy__eq="User B")
sum(1 for _ in results).should.equal(1)
results = table.scan(Body__beginswith="http")
sum(1 for _ in results).should.equal(3)
results = table.scan(Ids__null=False)
sum(1 for _ in results).should.equal(1)
results = table.scan(Ids__null=True)
sum(1 for _ in results).should.equal(2)
results = table.scan(PK__between=[8, 9])
sum(1 for _ in results).should.equal(0)
results = table.scan(PK__between=[5, 8])
sum(1 for _ in results).should.equal(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_scan_with_undeclared_table():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
conn.scan.when.called_with(
table_name="undeclared-table",
scan_filter={
"SentBy": {
"AttributeValueList": [{"S": "User B"}],
"ComparisonOperator": "EQ",
}
},
).should.throw(JSONResponseError)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_write_batch():
table = create_table()
with table.batch_write() as batch:
batch.put_item(
data={
"forum_name": "the-key",
"subject": "123",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
)
batch.put_item(
data={
"forum_name": "the-key",
"subject": "789",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
)
table.count().should.equal(2)
with table.batch_write() as batch:
batch.delete_item(forum_name="the-key", subject="789")
table.count().should.equal(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_batch_read():
table = create_table()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item_data["forum_name"] = "the-key"
item_data["subject"] = "456"
item = Item(table, item_data)
item.save()
item = Item(table, item_data)
item_data["forum_name"] = "the-key"
item_data["subject"] = "123"
item.save()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item = Item(table, item_data)
item_data["forum_name"] = "another-key"
item_data["subject"] = "789"
item.save()
results = table.batch_get(
keys=[
{"forum_name": "the-key", "subject": "123"},
{"forum_name": "another-key", "subject": "789"},
]
)
# Iterate through so that batch_item gets called
count = len([x for x in results])
count.should.equal(2)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_key_fields():
table = create_table()
kf = table.get_key_fields()
kf.should.equal(["forum_name", "subject"])
@mock_dynamodb2_deprecated
# Has boto3 equivalent
def test_create_with_global_indexes():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
Table.create(
"messages",
schema=[HashKey("subject"), RangeKey("version")],
global_indexes=[
GlobalAllIndex(
"topic-created_at-index",
parts=[HashKey("topic"), RangeKey("created_at", data_type="N")],
throughput={"read": 6, "write": 1},
)
],
)
table_description = conn.describe_table("messages")
table_description["Table"]["GlobalSecondaryIndexes"].should.equal(
[
{
"IndexName": "topic-created_at-index",
"KeySchema": [
{"AttributeName": "topic", "KeyType": "HASH"},
{"AttributeName": "created_at", "KeyType": "RANGE"},
],
"Projection": {"ProjectionType": "ALL"},
"ProvisionedThroughput": {
"ReadCapacityUnits": 6,
"WriteCapacityUnits": 1,
},
"IndexStatus": "ACTIVE",
}
]
)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_with_global_indexes():
table = Table.create(
"messages",
schema=[HashKey("subject"), RangeKey("version")],
global_indexes=[
GlobalAllIndex(
"topic-created_at-index",
parts=[HashKey("topic"), RangeKey("created_at", data_type="N")],
throughput={"read": 6, "write": 1},
),
GlobalAllIndex(
"status-created_at-index",
parts=[HashKey("status"), RangeKey("created_at", data_type="N")],
throughput={"read": 2, "write": 1},
),
],
)
item_data = {
"subject": "Check this out!",
"version": "1",
"created_at": 0,
"status": "inactive",
}
item = Item(table, item_data)
item.save(overwrite=True)
item["version"] = "2"
item.save(overwrite=True)
results = table.query(status__eq="active")
list(results).should.have.length_of(0)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_with_local_indexes():
table = create_table_with_local_indexes()
item_data = {
"forum_name": "Cool Forum",
"subject": "Check this out!",
"version": "1",
"threads": 1,
"status": "inactive",
}
item = Item(table, item_data)
item.save(overwrite=True)
item["version"] = "2"
item.save(overwrite=True)
results = table.query(
forum_name__eq="Cool Forum", index="threads_index", threads__eq=1
)
list(results).should.have.length_of(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_filter_eq():
table = create_table_with_local_indexes()
item_data = [
{
"forum_name": "Cool Forum",
"subject": "Check this out!",
"version": "1",
"threads": 1,
},
{
"forum_name": "Cool Forum",
"subject": "Read this now!",
"version": "1",
"threads": 5,
},
{
"forum_name": "Cool Forum",
"subject": "Please read this... please",
"version": "1",
"threads": 0,
},
]
for data in item_data:
item = Item(table, data)
item.save(overwrite=True)
results = table.query_2(
forum_name__eq="Cool Forum", index="threads_index", threads__eq=5
)
list(results).should.have.length_of(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_filter_lt():
table = create_table_with_local_indexes()
item_data = [
{
"forum_name": "Cool Forum",
"subject": "Check this out!",
"version": "1",
"threads": 1,
},
{
"forum_name": "Cool Forum",
"subject": "Read this now!",
"version": "1",
"threads": 5,
},
{
"forum_name": "Cool Forum",
"subject": "Please read this... please",
"version": "1",
"threads": 0,
},
]
for data in item_data:
item = Item(table, data)
item.save(overwrite=True)
results = table.query(
forum_name__eq="Cool Forum", index="threads_index", threads__lt=5
)
results = list(results)
results.should.have.length_of(2)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_filter_gt():
table = create_table_with_local_indexes()
item_data = [
{
"forum_name": "Cool Forum",
"subject": "Check this out!",
"version": "1",
"threads": 1,
},
{
"forum_name": "Cool Forum",
"subject": "Read this now!",
"version": "1",
"threads": 5,
},
{
"forum_name": "Cool Forum",
"subject": "Please read this... please",
"version": "1",
"threads": 0,
},
]
for data in item_data:
item = Item(table, data)
item.save(overwrite=True)
results = table.query(
forum_name__eq="Cool Forum", index="threads_index", threads__gt=1
)
list(results).should.have.length_of(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_filter_lte():
table = create_table_with_local_indexes()
item_data = [
{
"forum_name": "Cool Forum",
"subject": "Check this out!",
"version": "1",
"threads": 1,
},
{
"forum_name": "Cool Forum",
"subject": "Read this now!",
"version": "1",
"threads": 5,
},
{
"forum_name": "Cool Forum",
"subject": "Please read this... please",
"version": "1",
"threads": 0,
},
]
for data in item_data:
item = Item(table, data)
item.save(overwrite=True)
results = table.query(
forum_name__eq="Cool Forum", index="threads_index", threads__lte=5
)
list(results).should.have.length_of(3)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_filter_gte():
table = create_table_with_local_indexes()
item_data = [
{
"forum_name": "Cool Forum",
"subject": "Check this out!",
"version": "1",
"threads": 1,
},
{
"forum_name": "Cool Forum",
"subject": "Read this now!",
"version": "1",
"threads": 5,
},
{
"forum_name": "Cool Forum",
"subject": "Please read this... please",
"version": "1",
"threads": 0,
},
]
for data in item_data:
item = Item(table, data)
item.save(overwrite=True)
results = table.query(
forum_name__eq="Cool Forum", index="threads_index", threads__gte=1
)
list(results).should.have.length_of(2)
@mock_dynamodb2
def test_query_filter_boto3():
table_schema = {
@ -1016,135 +192,6 @@ def test_query_filter_boto3():
res["Items"].should.equal([{"pk": "pk", "sk": "sk-1"}, {"pk": "pk", "sk": "sk-2"}])
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_non_hash_range_key():
table = create_table_with_local_indexes()
item_data = [
{
"forum_name": "Cool Forum",
"subject": "Check this out!",
"version": "1",
"threads": 1,
},
{
"forum_name": "Cool Forum",
"subject": "Read this now!",
"version": "3",
"threads": 5,
},
{
"forum_name": "Cool Forum",
"subject": "Please read this... please",
"version": "2",
"threads": 0,
},
]
for data in item_data:
item = Item(table, data)
item.save(overwrite=True)
results = table.query(forum_name__eq="Cool Forum", version__gt="2")
results = list(results)
results.should.have.length_of(1)
results = table.query(forum_name__eq="Cool Forum", version__lt="3")
results = list(results)
results.should.have.length_of(2)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_reverse_query():
boto.dynamodb2.layer1.DynamoDBConnection()
table = Table.create(
"messages", schema=[HashKey("subject"), RangeKey("created_at", data_type="N")]
)
for i in range(10):
table.put_item({"subject": "Hi", "created_at": i})
results = table.query_2(subject__eq="Hi", created_at__lt=6, limit=4, reverse=True)
expected = [Decimal(5), Decimal(4), Decimal(3), Decimal(2)]
[r["created_at"] for r in results].should.equal(expected)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_lookup():
table = Table.create(
"messages",
schema=[
HashKey("test_hash", data_type=NUMBER),
RangeKey("test_range", data_type=NUMBER),
],
throughput={"read": 10, "write": 10},
)
hash_key = 3241526475
range_key = 1234567890987
data = {"test_hash": hash_key, "test_range": range_key}
table.put_item(data=data)
message = table.lookup(hash_key, range_key)
message.get("test_hash").should.equal(Decimal(hash_key))
message.get("test_range").should.equal(Decimal(range_key))
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_failed_overwrite():
table = Table.create(
"messages",
schema=[HashKey("id"), RangeKey("range")],
throughput={"read": 7, "write": 3},
)
data1 = {"id": "123", "range": "abc", "data": "678"}
table.put_item(data=data1)
data2 = {"id": "123", "range": "abc", "data": "345"}
table.put_item(data=data2, overwrite=True)
data3 = {"id": "123", "range": "abc", "data": "812"}
table.put_item.when.called_with(data=data3).should.throw(
ConditionalCheckFailedException
)
returned_item = table.lookup("123", "abc")
dict(returned_item).should.equal(data2)
data4 = {"id": "123", "range": "ghi", "data": 812}
table.put_item(data=data4)
returned_item = table.lookup("123", "ghi")
dict(returned_item).should.equal(data4)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_conflicting_writes():
table = Table.create("messages", schema=[HashKey("id"), RangeKey("range")])
item_data = {"id": "123", "range": "abc", "data": "678"}
item1 = Item(table, item_data)
item2 = Item(table, item_data)
item1.save()
item1["data"] = "579"
item2["data"] = "912"
item1.save()
item2.save.when.called_with().should.throw(ConditionalCheckFailedException)
"""
boto3
"""
@mock_dynamodb2
def test_boto3_create_table_with_gsi():
dynamodb = boto3.client("dynamodb", region_name="us-east-1")

View File

@ -1,66 +1,12 @@
import boto
import boto3
from boto3.dynamodb.conditions import Key
import sure # noqa # pylint: disable=unused-import
import pytest
from datetime import datetime
from freezegun import freeze_time
from boto.exception import JSONResponseError
from botocore.exceptions import ClientError
from moto import mock_dynamodb2, mock_dynamodb2_deprecated
from tests.helpers import requires_boto_gte
from moto import mock_dynamodb2
import botocore
try:
from boto.dynamodb2.types import NUMBER
from boto.dynamodb2.fields import HashKey
from boto.dynamodb2.table import Table
from boto.dynamodb2.table import Item
from boto.dynamodb2.exceptions import ConditionalCheckFailedException, ItemNotFound
except ImportError:
pass
def create_table():
table = Table.create(
"messages", schema=[HashKey("forum_name")], throughput={"read": 10, "write": 10}
)
return table
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
@freeze_time("2012-01-14")
def test_create_table():
create_table()
expected = {
"Table": {
"AttributeDefinitions": [
{"AttributeName": "forum_name", "AttributeType": "S"}
],
"ProvisionedThroughput": {
"NumberOfDecreasesToday": 0,
"WriteCapacityUnits": 10,
"ReadCapacityUnits": 10,
},
"TableSizeBytes": 0,
"TableName": "messages",
"TableStatus": "ACTIVE",
"TableArn": "arn:aws:dynamodb:us-east-1:123456789011:table/messages",
"KeySchema": [{"KeyType": "HASH", "AttributeName": "forum_name"}],
"ItemCount": 0,
"CreationDateTime": 1326499200.0,
"GlobalSecondaryIndexes": [],
"LocalSecondaryIndexes": [],
}
}
conn = boto.dynamodb2.connect_to_region(
"us-east-1", aws_access_key_id="ak", aws_secret_access_key="sk"
)
conn.describe_table("messages").should.equal(expected)
@mock_dynamodb2
def test_create_table_boto3():
@ -125,20 +71,6 @@ def test_create_table_boto3():
actual.should.have.key("ItemCount").equal(0)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_delete_table():
create_table()
conn = boto.dynamodb2.layer1.DynamoDBConnection()
conn.list_tables()["TableNames"].should.have.length_of(1)
conn.delete_table("messages")
conn.list_tables()["TableNames"].should.have.length_of(0)
conn.delete_table.when.called_with("messages").should.throw(JSONResponseError)
@mock_dynamodb2
def test_delete_table_boto3():
conn = boto3.client("dynamodb", region_name="us-west-2")
@ -161,20 +93,6 @@ def test_delete_table_boto3():
ex.value.response["Error"]["Message"].should.equal("Requested resource not found")
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_update_table_throughput():
table = create_table()
table.throughput["read"].should.equal(10)
table.throughput["write"].should.equal(10)
table.update(throughput={"read": 5, "write": 6})
table.throughput["read"].should.equal(5)
table.throughput["write"].should.equal(6)
@mock_dynamodb2
def test_update_table_throughput_boto3():
conn = boto3.resource("dynamodb", region_name="us-west-2")
@ -195,43 +113,6 @@ def test_update_table_throughput_boto3():
table.provisioned_throughput["WriteCapacityUnits"].should.equal(6)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_item_add_and_describe_and_update():
table = create_table()
data = {
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
}
table.put_item(data=data)
returned_item = table.get_item(forum_name="LOLCat Forum")
returned_item.should_not.be.none
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
}
)
returned_item["SentBy"] = "User B"
returned_item.save(overwrite=True)
returned_item = table.get_item(forum_name="LOLCat Forum")
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
}
)
@mock_dynamodb2
def test_item_add_and_describe_and_update_boto3():
conn = boto3.resource("dynamodb", region_name="us-west-2")
@ -268,50 +149,6 @@ def test_item_add_and_describe_and_update_boto3():
)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_item_partial_save():
table = create_table()
data = {
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
}
table.put_item(data=data)
returned_item = table.get_item(forum_name="LOLCat Forum")
returned_item["SentBy"] = "User B"
returned_item.partial_save()
returned_item = table.get_item(forum_name="LOLCat Forum")
dict(returned_item).should.equal(
{
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
}
)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_item_put_without_table():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
conn.put_item.when.called_with(
table_name="undeclared-table",
item={
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
},
).should.throw(JSONResponseError)
@mock_dynamodb2
def test_item_put_without_table_boto3():
conn = boto3.client("dynamodb", region_name="us-west-2")
@ -331,17 +168,6 @@ def test_item_put_without_table_boto3():
ex.value.response["Error"]["Message"].should.equal("Requested resource not found")
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_item_with_undeclared_table():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
conn.get_item.when.called_with(
table_name="undeclared-table", key={"forum_name": {"S": "LOLCat Forum"}}
).should.throw(JSONResponseError)
@mock_dynamodb2
def test_get_item_with_undeclared_table_boto3():
conn = boto3.client("dynamodb", region_name="us-west-2")
@ -354,32 +180,6 @@ def test_get_item_with_undeclared_table_boto3():
ex.value.response["Error"]["Message"].should.equal("Requested resource not found")
@requires_boto_gte("2.30.0")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_delete_item():
table = create_table()
item_data = {
"forum_name": "LOLCat Forum",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = Item(table, item_data)
item.save()
table.count().should.equal(1)
response = item.delete()
response.should.equal(True)
table.count().should.equal(0)
# Deletes are idempotent and 'False' here would imply an error condition
item.delete().should.equal(True)
@mock_dynamodb2
def test_delete_item_boto3():
conn = boto3.resource("dynamodb", region_name="us-west-2")
@ -407,17 +207,6 @@ def test_delete_item_boto3():
table.delete_item(Key={"id": "LOLCat Forum"})
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_delete_item_with_undeclared_table():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
conn.delete_item.when.called_with(
table_name="undeclared-table", key={"forum_name": {"S": "LOLCat Forum"}}
).should.throw(JSONResponseError)
@mock_dynamodb2
def test_delete_item_with_undeclared_table_boto3():
conn = boto3.client("dynamodb", region_name="us-west-2")
@ -434,113 +223,6 @@ def test_delete_item_with_undeclared_table_boto3():
)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query():
table = create_table()
item_data = {
"forum_name": "the-key",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item = Item(table, item_data)
item.save(overwrite=True)
table.count().should.equal(1)
table = Table("messages")
results = table.query(forum_name__eq="the-key")
sum(1 for _ in results).should.equal(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_query_with_undeclared_table():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
conn.query.when.called_with(
table_name="undeclared-table",
key_conditions={
"forum_name": {
"ComparisonOperator": "EQ",
"AttributeValueList": [{"S": "the-key"}],
}
},
).should.throw(JSONResponseError)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_scan():
table = create_table()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item_data["forum_name"] = "the-key"
item = Item(table, item_data)
item.save()
item["forum_name"] = "the-key2"
item.save(overwrite=True)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item_data["forum_name"] = "the-key3"
item = Item(table, item_data)
item.save()
results = table.scan()
sum(1 for _ in results).should.equal(3)
results = table.scan(SentBy__eq="User B")
sum(1 for _ in results).should.equal(1)
results = table.scan(Body__beginswith="http")
sum(1 for _ in results).should.equal(3)
results = table.scan(Ids__null=False)
sum(1 for _ in results).should.equal(1)
results = table.scan(Ids__null=True)
sum(1 for _ in results).should.equal(2)
results = table.scan(PK__between=[8, 9])
sum(1 for _ in results).should.equal(0)
results = table.scan(PK__between=[5, 8])
sum(1 for _ in results).should.equal(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_scan_with_undeclared_table():
conn = boto.dynamodb2.layer1.DynamoDBConnection()
conn.scan.when.called_with(
table_name="undeclared-table",
scan_filter={
"SentBy": {
"AttributeValueList": [{"S": "User B"}],
"ComparisonOperator": "EQ",
}
},
).should.throw(JSONResponseError)
@mock_dynamodb2
def test_scan_with_undeclared_table_boto3():
conn = boto3.client("dynamodb", region_name="us-west-2")
@ -553,87 +235,6 @@ def test_scan_with_undeclared_table_boto3():
ex.value.response["Error"]["Message"].should.equal("Requested resource not found")
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_write_batch():
table = create_table()
with table.batch_write() as batch:
batch.put_item(
data={
"forum_name": "the-key",
"subject": "123",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
)
batch.put_item(
data={
"forum_name": "the-key2",
"subject": "789",
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
)
table.count().should.equal(2)
with table.batch_write() as batch:
batch.delete_item(forum_name="the-key", subject="789")
table.count().should.equal(1)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_batch_read():
table = create_table()
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User A",
"ReceivedTime": "12/9/2011 11:36:03 PM",
}
item_data["forum_name"] = "the-key1"
item = Item(table, item_data)
item.save()
item = Item(table, item_data)
item_data["forum_name"] = "the-key2"
item.save(overwrite=True)
item_data = {
"Body": "http://url_to_lolcat.gif",
"SentBy": "User B",
"ReceivedTime": "12/9/2011 11:36:03 PM",
"Ids": set([1, 2, 3]),
"PK": 7,
}
item = Item(table, item_data)
item_data["forum_name"] = "another-key"
item.save(overwrite=True)
results = table.batch_get(
keys=[{"forum_name": "the-key1"}, {"forum_name": "another-key"}]
)
# Iterate through so that batch_item gets called
count = len([x for x in results])
count.should.equal(2)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_key_fields():
table = create_table()
kf = table.get_key_fields()
kf[0].should.equal("forum_name")
@mock_dynamodb2
def test_get_key_schema():
conn = boto3.resource("dynamodb", region_name="us-west-2")
@ -647,64 +248,6 @@ def test_get_key_schema():
table.key_schema.should.equal([{"AttributeName": "id", "KeyType": "HASH"}])
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_missing_item():
table = create_table()
table.get_item.when.called_with(forum_name="missing").should.throw(ItemNotFound)
@requires_boto_gte("2.9")
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_get_special_item():
table = Table.create(
"messages",
schema=[HashKey("date-joined", data_type=NUMBER)],
throughput={"read": 10, "write": 10},
)
data = {"date-joined": 127549192, "SentBy": "User A"}
table.put_item(data=data)
returned_item = table.get_item(**{"date-joined": 127549192})
dict(returned_item).should.equal(data)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_update_item_remove():
conn = boto.dynamodb2.connect_to_region("us-east-1")
table = Table.create("messages", schema=[HashKey("username")])
data = {"username": "steve", "SentBy": "User A", "SentTo": "User B"}
table.put_item(data=data)
key_map = {"username": {"S": "steve"}}
# Then remove the SentBy field
conn.update_item("messages", key_map, update_expression="REMOVE SentBy, SentTo")
returned_item = table.get_item(username="steve")
dict(returned_item).should.equal({"username": "steve"})
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_update_item_nested_remove():
conn = boto.dynamodb2.connect_to_region("us-east-1")
table = Table.create("messages", schema=[HashKey("username")])
data = {"username": "steve", "Meta": {"FullName": "Steve Urkel"}}
table.put_item(data=data)
key_map = {"username": {"S": "steve"}}
# Then remove the Meta.FullName field
conn.update_item("messages", key_map, update_expression="REMOVE Meta.FullName")
returned_item = table.get_item(username="steve")
dict(returned_item).should.equal({"username": "steve", "Meta": {}})
@mock_dynamodb2
def test_update_item_double_nested_remove():
conn = boto3.client("dynamodb", region_name="us-east-1")
@ -740,27 +283,6 @@ def test_update_item_double_nested_remove():
dict(returned_item["Item"]).should.equal(expected_item)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_update_item_set():
conn = boto.dynamodb2.connect_to_region("us-east-1")
table = Table.create("messages", schema=[HashKey("username")])
data = {"username": "steve", "SentBy": "User A"}
table.put_item(data=data)
key_map = {"username": {"S": "steve"}}
conn.update_item(
"messages",
key_map,
update_expression="SET foo=:bar, blah=:baz REMOVE SentBy",
expression_attribute_values={":bar": {"S": "bar"}, ":baz": {"S": "baz"}},
)
returned_item = table.get_item(username="steve")
dict(returned_item).should.equal({"username": "steve", "foo": "bar", "blah": "baz"})
@mock_dynamodb2
def test_update_item_set_boto3():
conn = boto3.resource("dynamodb", region_name="us-east-1")
@ -785,56 +307,6 @@ def test_update_item_set_boto3():
dict(returned_item).should.equal({"username": "steve", "foo": "bar", "blah": "baz"})
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_failed_overwrite():
table = Table.create(
"messages", schema=[HashKey("id")], throughput={"read": 7, "write": 3}
)
data1 = {"id": "123", "data": "678"}
table.put_item(data=data1)
data2 = {"id": "123", "data": "345"}
table.put_item(data=data2, overwrite=True)
data3 = {"id": "123", "data": "812"}
table.put_item.when.called_with(data=data3).should.throw(
ConditionalCheckFailedException
)
returned_item = table.lookup("123")
dict(returned_item).should.equal(data2)
data4 = {"id": "124", "data": 812}
table.put_item(data=data4)
returned_item = table.lookup("124")
dict(returned_item).should.equal(data4)
# Has boto3 equivalent
@mock_dynamodb2_deprecated
def test_conflicting_writes():
table = Table.create("messages", schema=[HashKey("id")])
item_data = {"id": "123", "data": "678"}
item1 = Item(table, item_data)
item2 = Item(table, item_data)
item1.save()
item1["data"] = "579"
item2["data"] = "912"
item1.save()
item2.save.when.called_with().should.throw(ConditionalCheckFailedException)
"""
boto3
"""
@mock_dynamodb2
def test_boto3_create_table():
dynamodb = boto3.resource("dynamodb", region_name="us-east-1")

View File

@ -1,96 +1,17 @@
import boto
import boto.ec2
import boto3
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
import pytest
import sure # noqa # pylint: disable=unused-import
import random
from moto import mock_ec2_deprecated, mock_ec2
from moto import mock_ec2
from moto.ec2.models import AMIS, OWNER_ID
from moto.core import ACCOUNT_ID
from tests import EXAMPLE_AMI_ID, EXAMPLE_AMI_PARAVIRTUAL
from tests.helpers import requires_boto_gte
from uuid import uuid4
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_create_and_delete():
conn = boto.connect_ec2("the_key", "the_secret")
initial_ami_count = len(AMIS)
conn.get_all_volumes().should.have.length_of(0)
conn.get_all_snapshots().should.have.length_of(initial_ami_count)
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
with pytest.raises(EC2ResponseError) as ex:
conn.create_image(instance.id, "test-ami", "this is a test ami", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateImage operation: Request would have succeeded, but DryRun flag is set"
)
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
all_images = conn.get_all_images()
set([i.id for i in all_images]).should.contain(image_id)
retrieved_image = [i for i in all_images if i.id == image_id][0]
retrieved_image.id.should.equal(image_id)
retrieved_image.virtualization_type.should.equal(instance.virtualization_type)
retrieved_image.architecture.should.equal(instance.architecture)
retrieved_image.kernel_id.should.equal(instance.kernel)
retrieved_image.platform.should.equal(instance.platform)
retrieved_image.creationDate.should_not.be.none
instance.terminate()
# Ensure we're no longer creating a volume
volumes = conn.get_all_volumes()
volumes.should.have.length_of(0)
# Validate auto-created snapshot
snapshots = conn.get_all_snapshots()
snapshots.should.have.length_of(initial_ami_count + 1)
retrieved_image_snapshot_id = (
retrieved_image.block_device_mapping.current_value.snapshot_id
)
[s.id for s in snapshots].should.contain(retrieved_image_snapshot_id)
snapshot = [s for s in snapshots if s.id == retrieved_image_snapshot_id][0]
snapshot.description.should.match("Created by CreateImage")
# root device should be in AMI's block device mappings
root_mapping = retrieved_image.block_device_mapping.get(
retrieved_image.root_device_name
)
root_mapping.should_not.be.none
# Deregister
with pytest.raises(EC2ResponseError) as ex:
success = conn.deregister_image(image_id, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DeregisterImage operation: Request would have succeeded, but DryRun flag is set"
)
success = conn.deregister_image(image_id)
success.should.be.true
with pytest.raises(EC2ResponseError) as cm:
conn.deregister_image(image_id)
cm.value.code.should.equal("InvalidAMIID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_snapshots_for_initial_amis():
ec2 = boto3.client("ec2", region_name="us-east-1")
@ -199,89 +120,6 @@ def test_ami_create_and_delete_boto3():
ex.value.response["ResponseMetadata"]["RequestId"].should_not.be.none
# Has boto3 equivalent
@requires_boto_gte("2.14.0")
@mock_ec2_deprecated
def test_ami_copy():
conn = boto.ec2.connect_to_region("us-west-1")
initial_ami_count = len(AMIS)
conn.get_all_volumes().should.have.length_of(0)
conn.get_all_snapshots().should.have.length_of(initial_ami_count)
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
source_image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
instance.terminate()
source_image = conn.get_all_images(image_ids=[source_image_id])[0]
# Boto returns a 'CopyImage' object with an image_id attribute here. Use
# the image_id to fetch the full info.
with pytest.raises(EC2ResponseError) as ex:
copy_image_ref = conn.copy_image(
source_image.region.name,
source_image.id,
"test-copy-ami",
"this is a test copy ami",
dry_run=True,
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CopyImage operation: Request would have succeeded, but DryRun flag is set"
)
copy_image_ref = conn.copy_image(
source_image.region.name,
source_image.id,
"test-copy-ami",
"this is a test copy ami",
)
copy_image_id = copy_image_ref.image_id
copy_image = conn.get_all_images(image_ids=[copy_image_id])[0]
copy_image.id.should.equal(copy_image_id)
copy_image.virtualization_type.should.equal(source_image.virtualization_type)
copy_image.architecture.should.equal(source_image.architecture)
copy_image.kernel_id.should.equal(source_image.kernel_id)
copy_image.platform.should.equal(source_image.platform)
# Ensure we're no longer creating a volume
conn.get_all_volumes().should.have.length_of(0)
# Validate auto-created snapshot
conn.get_all_snapshots().should.have.length_of(initial_ami_count + 2)
copy_image.block_device_mapping.current_value.snapshot_id.should_not.equal(
source_image.block_device_mapping.current_value.snapshot_id
)
# Copy from non-existent source ID.
with pytest.raises(EC2ResponseError) as cm:
conn.copy_image(
source_image.region.name,
"ami-abcd1234",
"test-copy-ami",
"this is a test copy ami",
)
cm.value.code.should.equal("InvalidAMIID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Copy from non-existent source region.
with pytest.raises(EC2ResponseError) as cm:
invalid_region = (
"us-east-1" if (source_image.region.name != "us-east-1") else "us-west-1"
)
conn.copy_image(
invalid_region, source_image.id, "test-copy-ami", "this is a test copy ami"
)
cm.value.code.should.equal("InvalidAMIID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_ami_copy_boto3_dryrun():
ec2 = boto3.client("ec2", region_name="us-west-1")
@ -430,35 +268,6 @@ def test_copy_image_changes_owner_id():
describe_resp[0]["ImageId"].should.equal(copy_resp["ImageId"])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_tagging():
conn = boto.connect_vpc("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_all_images()[0]
with pytest.raises(EC2ResponseError) as ex:
image.add_tag("a key", "some value", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateTags operation: Request would have succeeded, but DryRun flag is set"
)
image.add_tag("a key", "some value")
tag = conn.get_all_tags()[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
# Refresh the DHCP options
image = conn.get_all_images()[0]
image.tags.should.have.length_of(1)
image.tags["a key"].should.equal("some value")
@mock_ec2
def test_ami_tagging_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")
@ -488,19 +297,6 @@ def test_ami_tagging_boto3():
image["Tags"].should.equal([{"Value": "some value", "Key": "a key"}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_create_from_missing_instance():
conn = boto.connect_ec2("the_key", "the_secret")
args = ["i-abcdefg", "test-ami", "this is a test ami"]
with pytest.raises(EC2ResponseError) as cm:
conn.create_image(*args)
cm.value.code.should.equal("InvalidInstanceID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_ami_create_from_missing_instance_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")
@ -514,19 +310,6 @@ def test_ami_create_from_missing_instance_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidInstanceID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_pulls_attributes_from_instance():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.modify_attribute("kernel", "test-kernel")
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
image.kernel_id.should.equal("test-kernel")
@mock_ec2
def test_ami_pulls_attributes_from_instance_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")
@ -543,20 +326,6 @@ def test_ami_pulls_attributes_from_instance_boto3():
image.kernel_id.should.equal("test-kernel")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_uses_account_id_if_valid_access_key_is_supplied():
access_key = "AKIAXXXXXXXXXXXXXXXX"
conn = boto.connect_ec2(access_key, "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.modify_attribute("kernel", "test-kernel")
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
images = conn.get_all_images(owners=["self"])
[(ami.id, ami.owner_id) for ami in images].should.equal([(image_id, ACCOUNT_ID)])
@mock_ec2
def test_ami_uses_account_id_if_valid_access_key_is_supplied_boto3():
# The boto-equivalent required an access_key to be passed in, but Moto will always mock this in boto3
@ -575,68 +344,6 @@ def test_ami_uses_account_id_if_valid_access_key_is_supplied_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_filters():
conn = boto.connect_ec2("the_key", "the_secret")
reservationA = conn.run_instances(EXAMPLE_AMI_ID)
instanceA = reservationA.instances[0]
instanceA.modify_attribute("architecture", "i386")
instanceA.modify_attribute("kernel", "k-1234abcd")
instanceA.modify_attribute("platform", "windows")
instanceA.modify_attribute("virtualization_type", "hvm")
imageA_id = conn.create_image(instanceA.id, "test-ami-A", "this is a test ami")
imageA = conn.get_image(imageA_id)
reservationB = conn.run_instances(EXAMPLE_AMI_ID)
instanceB = reservationB.instances[0]
instanceB.modify_attribute("architecture", "x86_64")
instanceB.modify_attribute("kernel", "k-abcd1234")
instanceB.modify_attribute("platform", "linux")
instanceB.modify_attribute("virtualization_type", "paravirtual")
imageB_id = conn.create_image(instanceB.id, "test-ami-B", "this is a test ami")
imageB = conn.get_image(imageB_id)
imageB.set_launch_permissions(group_names=("all"))
amis_by_architecture = conn.get_all_images(filters={"architecture": "x86_64"})
set([ami.id for ami in amis_by_architecture]).should.contain(imageB.id)
len(amis_by_architecture).should.equal(39)
amis_by_kernel = conn.get_all_images(filters={"kernel-id": "k-abcd1234"})
set([ami.id for ami in amis_by_kernel]).should.equal(set([imageB.id]))
amis_by_virtualization = conn.get_all_images(
filters={"virtualization-type": "paravirtual"}
)
set([ami.id for ami in amis_by_virtualization]).should.contain(imageB.id)
len(amis_by_virtualization).should.equal(3)
amis_by_platform = conn.get_all_images(filters={"platform": "windows"})
set([ami.id for ami in amis_by_platform]).should.contain(imageA.id)
len(amis_by_platform).should.equal(25)
amis_by_id = conn.get_all_images(filters={"image-id": imageA.id})
set([ami.id for ami in amis_by_id]).should.equal(set([imageA.id]))
amis_by_state = conn.get_all_images(filters={"state": "available"})
ami_ids_by_state = [ami.id for ami in amis_by_state]
ami_ids_by_state.should.contain(imageA.id)
ami_ids_by_state.should.contain(imageB.id)
len(amis_by_state).should.equal(40)
amis_by_name = conn.get_all_images(filters={"name": imageA.name})
set([ami.id for ami in amis_by_name]).should.equal(set([imageA.id]))
amis_by_public = conn.get_all_images(filters={"is-public": "true"})
set([ami.id for ami in amis_by_public]).should.contain(imageB.id)
len(amis_by_public).should.equal(39)
amis_by_nonpublic = conn.get_all_images(filters={"is-public": "false"})
set([ami.id for ami in amis_by_nonpublic]).should.contain(imageA.id)
len(amis_by_nonpublic).should.equal(1)
@mock_ec2
def test_ami_filters_boto3():
image_name_A = f"test-ami-{str(uuid4())[0:6]}"
@ -723,30 +430,6 @@ def test_ami_filters_boto3():
assert len(amis_by_nonpublic) >= 2, "Should have at least 2 non-public images"
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_filtering_via_tag():
conn = boto.connect_vpc("the_key", "the_secret")
reservationA = conn.run_instances(EXAMPLE_AMI_ID)
instanceA = reservationA.instances[0]
imageA_id = conn.create_image(instanceA.id, "test-ami-A", "this is a test ami")
imageA = conn.get_image(imageA_id)
imageA.add_tag("a key", "some value")
reservationB = conn.run_instances(EXAMPLE_AMI_ID)
instanceB = reservationB.instances[0]
imageB_id = conn.create_image(instanceB.id, "test-ami-B", "this is a test ami")
imageB = conn.get_image(imageB_id)
imageB.add_tag("another key", "some other value")
amis_by_tagA = conn.get_all_images(filters={"tag:a key": "some value"})
set([ami.id for ami in amis_by_tagA]).should.equal(set([imageA.id]))
amis_by_tagB = conn.get_all_images(filters={"tag:another key": "some other value"})
set([ami.id for ami in amis_by_tagB]).should.equal(set([imageB.id]))
@mock_ec2
def test_ami_filtering_via_tag_boto3():
tag_value = f"value {str(uuid4())}"
@ -780,18 +463,6 @@ def test_ami_filtering_via_tag_boto3():
[ami["ImageId"] for ami in amis_by_tagB].should.equal([imageB_id])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_getting_missing_ami():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.get_image("ami-missing")
cm.value.code.should.equal("InvalidAMIID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_getting_missing_ami_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -803,18 +474,6 @@ def test_getting_missing_ami_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidAMIID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_getting_malformed_ami():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.get_image("foo-missing")
cm.value.code.should.equal("InvalidAMIID.Malformed")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_getting_malformed_ami_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -826,70 +485,6 @@ def test_getting_malformed_ami_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidAMIID.Malformed")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_attribute_group_permissions():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
# Baseline
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.name.should.equal("launch_permission")
attributes.attrs.should.have.length_of(0)
ADD_GROUP_ARGS = {
"image_id": image.id,
"attribute": "launchPermission",
"operation": "add",
"groups": "all",
}
REMOVE_GROUP_ARGS = {
"image_id": image.id,
"attribute": "launchPermission",
"operation": "remove",
"groups": "all",
}
# Add 'all' group and confirm
with pytest.raises(EC2ResponseError) as ex:
conn.modify_image_attribute(**dict(ADD_GROUP_ARGS, **{"dry_run": True}))
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ModifyImageAttribute operation: Request would have succeeded, but DryRun flag is set"
)
conn.modify_image_attribute(**ADD_GROUP_ARGS)
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs["groups"].should.have.length_of(1)
attributes.attrs["groups"].should.equal(["all"])
image = conn.get_image(image_id)
image.is_public.should.equal(True)
# Add is idempotent
conn.modify_image_attribute.when.called_with(**ADD_GROUP_ARGS).should_not.throw(
EC2ResponseError
)
# Remove 'all' group and confirm
conn.modify_image_attribute(**REMOVE_GROUP_ARGS)
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs.should.have.length_of(0)
image = conn.get_image(image_id)
image.is_public.should.equal(False)
# Remove is idempotent
conn.modify_image_attribute.when.called_with(**REMOVE_GROUP_ARGS).should_not.throw(
EC2ResponseError
)
@mock_ec2
def test_ami_attribute_group_permissions_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")
@ -956,82 +551,6 @@ def test_ami_attribute_group_permissions_boto3():
image.modify_attribute(**REMOVE_GROUP_ARGS)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_attribute_user_permissions():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
# Baseline
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.name.should.equal("launch_permission")
attributes.attrs.should.have.length_of(0)
# Both str and int values should work.
USER1 = "123456789011"
USER2 = 123456789022
ADD_USERS_ARGS = {
"image_id": image.id,
"attribute": "launchPermission",
"operation": "add",
"user_ids": [USER1, USER2],
}
REMOVE_USERS_ARGS = {
"image_id": image.id,
"attribute": "launchPermission",
"operation": "remove",
"user_ids": [USER1, USER2],
}
REMOVE_SINGLE_USER_ARGS = {
"image_id": image.id,
"attribute": "launchPermission",
"operation": "remove",
"user_ids": [USER1],
}
# Add multiple users and confirm
conn.modify_image_attribute(**ADD_USERS_ARGS)
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs["user_ids"].should.have.length_of(2)
set(attributes.attrs["user_ids"]).should.equal(set([str(USER1), str(USER2)]))
image = conn.get_image(image_id)
image.is_public.should.equal(False)
# Add is idempotent
conn.modify_image_attribute.when.called_with(**ADD_USERS_ARGS).should_not.throw(
EC2ResponseError
)
# Remove single user and confirm
conn.modify_image_attribute(**REMOVE_SINGLE_USER_ARGS)
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs["user_ids"].should.have.length_of(1)
set(attributes.attrs["user_ids"]).should.equal(set([str(USER2)]))
image = conn.get_image(image_id)
image.is_public.should.equal(False)
# Remove multiple users and confirm
conn.modify_image_attribute(**REMOVE_USERS_ARGS)
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs.should.have.length_of(0)
image = conn.get_image(image_id)
image.is_public.should.equal(False)
# Remove is idempotent
conn.modify_image_attribute.when.called_with(**REMOVE_USERS_ARGS).should_not.throw(
EC2ResponseError
)
@mock_ec2
def test_ami_attribute_user_permissions_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")
@ -1216,63 +735,6 @@ def test_ami_describe_executable_users_and_filter():
images[0]["ImageId"].should.equal(image_id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_attribute_user_and_group_permissions():
"""
Boto supports adding/removing both users and groups at the same time.
Just spot-check this -- input variations, idempotency, etc are validated
via user-specific and group-specific tests above.
"""
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
# Baseline
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.name.should.equal("launch_permission")
attributes.attrs.should.have.length_of(0)
USER1 = "123456789011"
USER2 = "123456789022"
ADD_ARGS = {
"image_id": image.id,
"attribute": "launchPermission",
"operation": "add",
"groups": ["all"],
"user_ids": [USER1, USER2],
}
REMOVE_ARGS = {
"image_id": image.id,
"attribute": "launchPermission",
"operation": "remove",
"groups": ["all"],
"user_ids": [USER1, USER2],
}
# Add and confirm
conn.modify_image_attribute(**ADD_ARGS)
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs["user_ids"].should.have.length_of(2)
set(attributes.attrs["user_ids"]).should.equal(set([USER1, USER2]))
set(attributes.attrs["groups"]).should.equal(set(["all"]))
image = conn.get_image(image_id)
image.is_public.should.equal(True)
# Remove and confirm
conn.modify_image_attribute(**REMOVE_ARGS)
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs.should.have.length_of(0)
image = conn.get_image(image_id)
image.is_public.should.equal(False)
@mock_ec2
def test_ami_attribute_user_and_group_permissions_boto3():
"""
@ -1363,98 +825,6 @@ def test_filter_description():
resp.should.have.length_of(1)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_ami_attribute_error_cases():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
# Error: Add with group != 'all'
with pytest.raises(EC2ResponseError) as cm:
conn.modify_image_attribute(
image.id, attribute="launchPermission", operation="add", groups="everyone"
)
cm.value.code.should.equal("InvalidAMIAttributeItemValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Add with user ID that isn't an integer.
with pytest.raises(EC2ResponseError) as cm:
conn.modify_image_attribute(
image.id,
attribute="launchPermission",
operation="add",
user_ids="12345678901A",
)
cm.value.code.should.equal("InvalidAMIAttributeItemValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Add with user ID that is > length 12.
with pytest.raises(EC2ResponseError) as cm:
conn.modify_image_attribute(
image.id,
attribute="launchPermission",
operation="add",
user_ids="1234567890123",
)
cm.value.code.should.equal("InvalidAMIAttributeItemValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Add with user ID that is < length 12.
with pytest.raises(EC2ResponseError) as cm:
conn.modify_image_attribute(
image.id,
attribute="launchPermission",
operation="add",
user_ids="12345678901",
)
cm.value.code.should.equal("InvalidAMIAttributeItemValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Add with one invalid user ID among other valid IDs, ensure no
# partial changes.
with pytest.raises(EC2ResponseError) as cm:
conn.modify_image_attribute(
image.id,
attribute="launchPermission",
operation="add",
user_ids=["123456789011", "foo", "123456789022"],
)
cm.value.code.should.equal("InvalidAMIAttributeItemValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
attributes = conn.get_image_attribute(image.id, attribute="launchPermission")
attributes.attrs.should.have.length_of(0)
# Error: Add with invalid image ID
with pytest.raises(EC2ResponseError) as cm:
conn.modify_image_attribute(
"ami-abcd1234", attribute="launchPermission", operation="add", groups="all"
)
cm.value.code.should.equal("InvalidAMIID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Remove with invalid image ID
with pytest.raises(EC2ResponseError) as cm:
conn.modify_image_attribute(
"ami-abcd1234",
attribute="launchPermission",
operation="remove",
groups="all",
)
cm.value.code.should.equal("InvalidAMIID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_ami_attribute_error_cases_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")

View File

@ -1,34 +1,9 @@
import boto
import boto.ec2
import boto3
import sure # noqa # pylint: disable=unused-import
import pytest
from botocore.exceptions import ClientError
from moto import mock_ec2, mock_ec2_deprecated
# Has boto3 equivalent
@mock_ec2_deprecated
def test_describe_regions():
conn = boto.connect_ec2("the_key", "the_secret")
regions = conn.get_all_regions()
len(regions).should.be.greater_than(1)
for region in regions:
region.endpoint.should.contain(region.name)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_availability_zones():
conn = boto.connect_ec2("the_key", "the_secret")
regions = conn.get_all_regions()
for region in regions:
conn = boto.ec2.connect_to_region(region.name)
if conn is None:
continue
for zone in conn.get_all_zones():
zone.name.should.contain(region.name)
from moto import mock_ec2
@mock_ec2

View File

@ -1,24 +1,9 @@
import boto
import sure # noqa # pylint: disable=unused-import
import boto3
import pytest
from boto.exception import EC2ResponseError
import sure # noqa # pylint: disable=unused-import
from botocore.exceptions import ClientError
from moto import mock_ec2_deprecated, mock_ec2
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_customer_gateways():
conn = boto.connect_vpc("the_key", "the_secret")
customer_gateway = conn.create_customer_gateway("ipsec.1", "205.251.242.54", 65534)
customer_gateway.should_not.be.none
customer_gateway.id.should.match(r"cgw-\w+")
customer_gateway.type.should.equal("ipsec.1")
customer_gateway.bgp_asn.should.equal(65534)
customer_gateway.ip_address.should.equal("205.251.242.54")
from moto import mock_ec2
@mock_ec2
@ -32,16 +17,6 @@ def test_create_customer_gateways_boto3():
customer_gateway.should.have.key("IpAddress").equal("205.251.242.54")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_describe_customer_gateways():
conn = boto.connect_vpc("the_key", "the_secret")
customer_gateway = conn.create_customer_gateway("ipsec.1", "205.251.242.54", 65534)
cgws = conn.get_all_customer_gateways()
cgws.should.have.length_of(1)
cgws[0].id.should.match(customer_gateway.id)
@mock_ec2
def test_describe_customer_gateways_dryrun():
client = boto3.client("ec2", region_name="us-east-1")
@ -81,21 +56,6 @@ def test_describe_customer_gateways_boto3():
), "Should have at least the one CustomerGateway we just created"
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_customer_gateways():
conn = boto.connect_vpc("the_key", "the_secret")
customer_gateway = conn.create_customer_gateway("ipsec.1", "205.251.242.54", 65534)
customer_gateway.should_not.be.none
cgws = conn.get_all_customer_gateways()
cgws[0].id.should.match(customer_gateway.id)
conn.delete_customer_gateway(customer_gateway.id)
cgws = conn.get_all_customer_gateways()
cgws[0].state.should.equal("deleted")
cgws.should.have.length_of(1)
@mock_ec2
def test_delete_customer_gateways_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")
@ -118,14 +78,6 @@ def test_delete_customer_gateways_boto3():
cgws[0].should.have.key("State").equal("deleted")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_customer_gateways_bad_id():
conn = boto.connect_vpc("the_key", "the_secret")
with pytest.raises(EC2ResponseError):
conn.delete_customer_gateway("cgw-0123abcd")
@mock_ec2
def test_delete_customer_gateways_bad_id_boto3():
ec2 = boto3.client("ec2", region_name="us-east-1")

View File

@ -1,33 +1,19 @@
import pytest
import boto3
import boto
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
import sure # noqa # pylint: disable=unused-import
import random
import uuid
from moto import mock_ec2, mock_ec2_deprecated, settings
from moto import mock_ec2, settings
from unittest import SkipTest
SAMPLE_DOMAIN_NAME = "example.com"
SAMPLE_NAME_SERVERS = ["10.0.0.6", "10.0.0.7"]
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_options_associate():
"""associate dhcp option"""
conn = boto.connect_vpc("the_key", "the_secret")
dhcp_options = conn.create_dhcp_options(SAMPLE_DOMAIN_NAME, SAMPLE_NAME_SERVERS)
vpc = conn.create_vpc("10.0.0.0/16")
rval = conn.associate_dhcp_options(dhcp_options.id, vpc.id)
rval.should.be.equal(True)
@mock_ec2
def test_dhcp_options_associate_boto3():
""" associate dhcp option """
@ -48,20 +34,6 @@ def test_dhcp_options_associate_boto3():
vpc.dhcp_options_id.should.equal(dhcp_options.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_options_associate_invalid_dhcp_id():
"""associate dhcp option bad dhcp options id"""
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
with pytest.raises(EC2ResponseError) as cm:
conn.associate_dhcp_options("foo", vpc.id)
cm.value.code.should.equal("InvalidDhcpOptionID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_dhcp_options_associate_invalid_dhcp_id_boto3():
""" associate dhcp option bad dhcp options id """
@ -76,20 +48,6 @@ def test_dhcp_options_associate_invalid_dhcp_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidDhcpOptionID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_options_associate_invalid_vpc_id():
"""associate dhcp option invalid vpc id"""
conn = boto.connect_vpc("the_key", "the_secret")
dhcp_options = conn.create_dhcp_options(SAMPLE_DOMAIN_NAME, SAMPLE_NAME_SERVERS)
with pytest.raises(EC2ResponseError) as cm:
conn.associate_dhcp_options(dhcp_options.id, "foo")
cm.value.code.should.equal("InvalidVpcID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_dhcp_options_associate_invalid_vpc_id_boto3():
""" associate dhcp option invalid vpc id """
@ -109,33 +67,6 @@ def test_dhcp_options_associate_invalid_vpc_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidVpcID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_options_delete_with_vpc():
"""Test deletion of dhcp options with vpc"""
conn = boto.connect_vpc("the_key", "the_secret")
dhcp_options = conn.create_dhcp_options(SAMPLE_DOMAIN_NAME, SAMPLE_NAME_SERVERS)
dhcp_options_id = dhcp_options.id
vpc = conn.create_vpc("10.0.0.0/16")
rval = conn.associate_dhcp_options(dhcp_options_id, vpc.id)
rval.should.be.equal(True)
with pytest.raises(EC2ResponseError) as cm:
conn.delete_dhcp_options(dhcp_options_id)
cm.value.code.should.equal("DependencyViolation")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
vpc.delete()
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_dhcp_options([dhcp_options_id])
cm.value.code.should.equal("InvalidDhcpOptionID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_dhcp_options_delete_with_vpc_boto3():
"""Test deletion of dhcp options with vpc"""
@ -166,22 +97,6 @@ def test_dhcp_options_delete_with_vpc_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidDhcpOptionID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_dhcp_options():
"""Create most basic dhcp option"""
conn = boto.connect_vpc("the_key", "the_secret")
dhcp_option = conn.create_dhcp_options(SAMPLE_DOMAIN_NAME, SAMPLE_NAME_SERVERS)
dhcp_option.options["domain-name"][0].should.be.equal(SAMPLE_DOMAIN_NAME)
dhcp_option.options["domain-name-servers"][0].should.be.equal(
SAMPLE_NAME_SERVERS[0]
)
dhcp_option.options["domain-name-servers"][1].should.be.equal(
SAMPLE_NAME_SERVERS[1]
)
@mock_ec2
def test_create_dhcp_options_boto3():
"""Create most basic dhcp option"""
@ -206,26 +121,6 @@ def test_create_dhcp_options_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_dhcp_options_invalid_options():
"""Create invalid dhcp options"""
conn = boto.connect_vpc("the_key", "the_secret")
servers = ["f", "f", "f", "f", "f"]
with pytest.raises(EC2ResponseError) as cm:
conn.create_dhcp_options(ntp_servers=servers)
cm.value.code.should.equal("InvalidParameterValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
with pytest.raises(EC2ResponseError) as cm:
conn.create_dhcp_options(netbios_node_type="0")
cm.value.code.should.equal("InvalidParameterValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_create_dhcp_options_invalid_options_boto3():
"""Create invalid dhcp options"""
@ -249,20 +144,6 @@ def test_create_dhcp_options_invalid_options_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidParameterValue")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_describe_dhcp_options():
"""Test dhcp options lookup by id"""
conn = boto.connect_vpc("the_key", "the_secret")
dhcp_option = conn.create_dhcp_options()
dhcp_options = conn.get_all_dhcp_options([dhcp_option.id])
dhcp_options.should.be.length_of(1)
dhcp_options = conn.get_all_dhcp_options()
dhcp_options.should.be.length_of(1)
@mock_ec2
def test_describe_dhcp_options_boto3():
"""Test dhcp options lookup by id"""
@ -299,19 +180,6 @@ def test_describe_dhcp_options_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_describe_dhcp_options_invalid_id():
"""get error on invalid dhcp_option_id lookup"""
conn = boto.connect_vpc("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_dhcp_options(["1"])
cm.value.code.should.equal("InvalidDhcpOptionID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_describe_dhcp_options_invalid_id_boto3():
"""get error on invalid dhcp_option_id lookup"""
@ -324,25 +192,6 @@ def test_describe_dhcp_options_invalid_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidDhcpOptionID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_dhcp_options():
"""delete dhcp option"""
conn = boto.connect_vpc("the_key", "the_secret")
dhcp_option = conn.create_dhcp_options()
dhcp_options = conn.get_all_dhcp_options([dhcp_option.id])
dhcp_options.should.be.length_of(1)
conn.delete_dhcp_options(dhcp_option.id) # .should.be.equal(True)
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_dhcp_options([dhcp_option.id])
cm.value.code.should.equal("InvalidDhcpOptionID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_delete_dhcp_options_boto3():
"""delete dhcp option"""
@ -365,20 +214,6 @@ def test_delete_dhcp_options_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidDhcpOptionID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_dhcp_options_invalid_id():
conn = boto.connect_vpc("the_key", "the_secret")
conn.create_dhcp_options()
with pytest.raises(EC2ResponseError) as cm:
conn.delete_dhcp_options("dopt-abcd1234")
cm.value.code.should.equal("InvalidDhcpOptionID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_delete_dhcp_options_invalid_id_boto3():
client = boto3.client("ec2", region_name="us-west-1")
@ -390,20 +225,6 @@ def test_delete_dhcp_options_invalid_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidDhcpOptionID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_dhcp_options_malformed_id():
conn = boto.connect_vpc("the_key", "the_secret")
conn.create_dhcp_options()
with pytest.raises(EC2ResponseError) as cm:
conn.delete_dhcp_options("foo-abcd1234")
cm.value.code.should.equal("InvalidDhcpOptionsId.Malformed")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_delete_dhcp_options_malformed_id_boto3():
client = boto3.client("ec2", region_name="us-west-1")
@ -415,24 +236,6 @@ def test_delete_dhcp_options_malformed_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidDhcpOptionsId.Malformed")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_tagging():
conn = boto.connect_vpc("the_key", "the_secret")
dhcp_option = conn.create_dhcp_options()
dhcp_option.add_tag("a key", "some value")
tag = conn.get_all_tags()[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
# Refresh the DHCP options
dhcp_option = conn.get_all_dhcp_options()[0]
dhcp_option.tags.should.have.length_of(1)
dhcp_option.tags["a key"].should.equal("some value")
@mock_ec2
def test_dhcp_tagging_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -463,43 +266,6 @@ def test_dhcp_tagging_boto3():
dhcp_option["Tags"].should.equal([{"Key": "a tag", "Value": tag_value}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_options_get_by_tag():
conn = boto.connect_vpc("the_key", "the_secret")
dhcp1 = conn.create_dhcp_options("example.com", ["10.0.10.2"])
dhcp1.add_tag("Name", "TestDhcpOptions1")
dhcp1.add_tag("test-tag", "test-value")
dhcp2 = conn.create_dhcp_options("example.com", ["10.0.20.2"])
dhcp2.add_tag("Name", "TestDhcpOptions2")
dhcp2.add_tag("test-tag", "test-value")
filters = {"tag:Name": "TestDhcpOptions1", "tag:test-tag": "test-value"}
dhcp_options_sets = conn.get_all_dhcp_options(filters=filters)
dhcp_options_sets.should.have.length_of(1)
dhcp_options_sets[0].options["domain-name"][0].should.be.equal("example.com")
dhcp_options_sets[0].options["domain-name-servers"][0].should.be.equal("10.0.10.2")
dhcp_options_sets[0].tags["Name"].should.equal("TestDhcpOptions1")
dhcp_options_sets[0].tags["test-tag"].should.equal("test-value")
filters = {"tag:Name": "TestDhcpOptions2", "tag:test-tag": "test-value"}
dhcp_options_sets = conn.get_all_dhcp_options(filters=filters)
dhcp_options_sets.should.have.length_of(1)
dhcp_options_sets[0].options["domain-name"][0].should.be.equal("example.com")
dhcp_options_sets[0].options["domain-name-servers"][0].should.be.equal("10.0.20.2")
dhcp_options_sets[0].tags["Name"].should.equal("TestDhcpOptions2")
dhcp_options_sets[0].tags["test-tag"].should.equal("test-value")
filters = {"tag:test-tag": "test-value"}
dhcp_options_sets = conn.get_all_dhcp_options(filters=filters)
dhcp_options_sets.should.have.length_of(2)
@mock_ec2
def test_dhcp_options_get_by_tag_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -580,37 +346,6 @@ def test_dhcp_options_get_by_tag_boto3():
dhcp_options_sets.should.have.length_of(2)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_options_get_by_id():
conn = boto.connect_vpc("the_key", "the_secret")
dhcp1 = conn.create_dhcp_options("test1.com", ["10.0.10.2"])
dhcp1.add_tag("Name", "TestDhcpOptions1")
dhcp1.add_tag("test-tag", "test-value")
dhcp1_id = dhcp1.id
dhcp2 = conn.create_dhcp_options("test2.com", ["10.0.20.2"])
dhcp2.add_tag("Name", "TestDhcpOptions2")
dhcp2.add_tag("test-tag", "test-value")
dhcp2_id = dhcp2.id
dhcp_options_sets = conn.get_all_dhcp_options()
dhcp_options_sets.should.have.length_of(2)
dhcp_options_sets = conn.get_all_dhcp_options(filters={"dhcp-options-id": dhcp1_id})
dhcp_options_sets.should.have.length_of(1)
dhcp_options_sets[0].options["domain-name"][0].should.be.equal("test1.com")
dhcp_options_sets[0].options["domain-name-servers"][0].should.be.equal("10.0.10.2")
dhcp_options_sets = conn.get_all_dhcp_options(filters={"dhcp-options-id": dhcp2_id})
dhcp_options_sets.should.have.length_of(1)
dhcp_options_sets[0].options["domain-name"][0].should.be.equal("test2.com")
dhcp_options_sets[0].options["domain-name-servers"][0].should.be.equal("10.0.20.2")
@mock_ec2
def test_dhcp_options_get_by_id_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -724,19 +459,6 @@ def test_dhcp_options_get_by_key_filter():
servers.should.contain({"Value": "example.com"})
# Has boto3 equivalent
@mock_ec2_deprecated
def test_dhcp_options_get_by_invalid_filter():
conn = boto.connect_vpc("the_key", "the_secret")
conn.create_dhcp_options(SAMPLE_DOMAIN_NAME, SAMPLE_NAME_SERVERS)
filters = {"invalid-filter": "invalid-value"}
conn.get_all_dhcp_options.when.called_with(filters=filters).should.throw(
NotImplementedError
)
@mock_ec2
def test_dhcp_options_get_by_invalid_filter_boto3():
if settings.TEST_SERVER_MODE:

View File

@ -1,5 +1,4 @@
from botocore.exceptions import ClientError
from moto import mock_cloudformation_deprecated, mock_ec2_deprecated
from moto import mock_cloudformation, mock_ec2
from tests import EXAMPLE_AMI_ID
from tests.test_cloudformation.fixtures import ec2_classic_eip
@ -8,10 +7,6 @@ from tests.test_cloudformation.fixtures import vpc_eip
from tests.test_cloudformation.fixtures import vpc_eni
from tests.test_cloudformation.fixtures import vpc_single_instance_in_subnet
from uuid import uuid4
import boto
import boto.ec2
import boto.cloudformation
import boto.vpc
import boto3
import json
import sure # noqa # pylint: disable=unused-import
@ -113,31 +108,6 @@ def test_delete_stack_with_resource_missing_delete_attr():
ec2.describe_vpcs(VpcIds=[vpc_id])["Vpcs"].should.have.length_of(1)
# Has boto3 equivalent
@mock_ec2_deprecated
@mock_cloudformation_deprecated
def test_elastic_network_interfaces_cloudformation():
template = vpc_eni.template
template_json = json.dumps(template)
conn = boto.cloudformation.connect_to_region("us-west-1")
conn.create_stack("test_stack", template_body=template_json)
ec2_conn = boto.ec2.connect_to_region("us-west-1")
eni = ec2_conn.get_all_network_interfaces()[0]
eni.private_ip_addresses.should.have.length_of(1)
stack = conn.describe_stacks()[0]
resources = stack.describe_resources()
cfn_eni = [
resource
for resource in resources
if resource.resource_type == "AWS::EC2::NetworkInterface"
][0]
cfn_eni.physical_resource_id.should.equal(eni.id)
outputs = {output.key: output.value for output in stack.outputs}
outputs["ENIIpAddress"].should.equal(eni.private_ip_addresses[0].private_ip_address)
@mock_ec2
@mock_cloudformation
def test_elastic_network_interfaces_cloudformation_boto3():

View File

@ -1,57 +1,15 @@
import boto
import boto.ec2
import boto3
import pytest
import sure # noqa # pylint: disable=unused-import
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
from moto import mock_ec2, mock_ec2_deprecated
from moto.ec2 import ec2_backends
from moto import mock_ec2
from moto.ec2.models import OWNER_ID
from moto.kms import mock_kms
from tests import EXAMPLE_AMI_ID
from uuid import uuid4
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_and_delete_volume():
conn = boto.ec2.connect_to_region("us-east-1")
volume = conn.create_volume(80, "us-east-1a")
all_volumes = conn.get_all_volumes()
current_volume = [item for item in all_volumes if item.id == volume.id]
current_volume.should.have.length_of(1)
current_volume[0].size.should.equal(80)
current_volume[0].zone.should.equal("us-east-1a")
current_volume[0].encrypted.should.be(False)
volume = current_volume[0]
with pytest.raises(EC2ResponseError) as ex:
volume.delete(dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DeleteVolume operation: Request would have succeeded, but DryRun flag is set"
)
volume.delete()
all_volumes = conn.get_all_volumes()
my_volume = [item for item in all_volumes if item.id == volume.id]
my_volume.should.have.length_of(0)
# Deleting something that was already deleted should throw an error
with pytest.raises(EC2ResponseError) as cm:
volume.delete()
cm.value.code.should.equal("InvalidVolume.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_create_and_delete_volume_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -88,46 +46,6 @@ def test_create_and_delete_volume_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidVolume.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_attached_volume():
conn = boto.ec2.connect_to_region("us-east-1")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
# create an instance
instance = reservation.instances[0]
# create a volume
volume = conn.create_volume(80, "us-east-1a")
# attach volume to instance
volume.attach(instance.id, "/dev/sdh")
volume.update()
volume.volume_state().should.equal("in-use")
volume.attachment_state().should.equal("attached")
volume.attach_data.instance_id.should.equal(instance.id)
# attempt to delete volume
# assert raises VolumeInUseError
with pytest.raises(EC2ResponseError) as ex:
volume.delete()
ex.value.error_code.should.equal("VolumeInUse")
ex.value.status.should.equal(400)
ex.value.message.should.equal(
"Volume {0} is currently attached to {1}".format(volume.id, instance.id)
)
volume.detach()
volume.update()
volume.volume_state().should.equal("available")
volume.delete()
all_volumes = conn.get_all_volumes()
my_volume = [item for item in all_volumes if item.id == volume.id]
my_volume.should.have.length_of(0)
@mock_ec2
def test_delete_attached_volume_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -168,19 +86,6 @@ def test_delete_attached_volume_boto3():
[v["VolumeId"] for v in all_volumes].shouldnt.contain(volume.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_encrypted_volume_dryrun():
conn = boto.ec2.connect_to_region("us-east-1")
with pytest.raises(EC2ResponseError) as ex:
conn.create_volume(80, "us-east-1a", encrypted=True, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateVolume operation: Request would have succeeded, but DryRun flag is set"
)
@mock_ec2
def test_create_encrypted_volume_dryrun_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -193,24 +98,6 @@ def test_create_encrypted_volume_dryrun_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_encrypted_volume():
conn = boto.ec2.connect_to_region("us-east-1")
volume = conn.create_volume(80, "us-east-1a", encrypted=True)
with pytest.raises(EC2ResponseError) as ex:
conn.create_volume(80, "us-east-1a", encrypted=True, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateVolume operation: Request would have succeeded, but DryRun flag is set"
)
all_volumes = [vol for vol in conn.get_all_volumes() if vol.id == volume.id]
all_volumes[0].encrypted.should.be(True)
@mock_ec2
def test_create_encrypted_volume_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -221,27 +108,6 @@ def test_create_encrypted_volume_boto3():
all_volumes[0]["Encrypted"].should.be(True)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_filter_volume_by_id():
conn = boto.ec2.connect_to_region("us-east-1")
volume1 = conn.create_volume(80, "us-east-1a")
volume2 = conn.create_volume(36, "us-east-1b")
volume3 = conn.create_volume(20, "us-east-1c")
vol1 = conn.get_all_volumes(volume_ids=volume3.id)
vol1.should.have.length_of(1)
vol1[0].size.should.equal(20)
vol1[0].zone.should.equal("us-east-1c")
vol2 = conn.get_all_volumes(volume_ids=[volume1.id, volume2.id])
vol2.should.have.length_of(2)
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_volumes(volume_ids=["vol-does_not_exist"])
cm.value.code.should.equal("InvalidVolume.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_filter_volume_by_id_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -264,115 +130,6 @@ def test_filter_volume_by_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidVolume.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_volume_filters():
conn = boto.ec2.connect_to_region("us-east-1")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.update()
volume1 = conn.create_volume(80, "us-east-1a", encrypted=True)
volume2 = conn.create_volume(36, "us-east-1b", encrypted=False)
volume3 = conn.create_volume(20, "us-east-1c", encrypted=True)
snapshot = volume3.create_snapshot(description="testsnap")
volume4 = conn.create_volume(25, "us-east-1a", snapshot=snapshot)
conn.create_tags([volume1.id], {"testkey1": "testvalue1"})
conn.create_tags([volume2.id], {"testkey2": "testvalue2"})
volume1.update()
volume2.update()
volume3.update()
volume4.update()
block_mapping = instance.block_device_mapping["/dev/sda1"]
volume_ids = (
volume1.id,
volume2.id,
volume3.id,
volume4.id,
block_mapping.volume_id,
)
volumes_by_attach_time = conn.get_all_volumes(
filters={"attachment.attach-time": block_mapping.attach_time}
)
set([vol.id for vol in volumes_by_attach_time]).should.equal(
{block_mapping.volume_id}
)
volumes_by_attach_device = conn.get_all_volumes(
filters={"attachment.device": "/dev/sda1"}
)
set([vol.id for vol in volumes_by_attach_device]).should.equal(
{block_mapping.volume_id}
)
volumes_by_attach_instance_id = conn.get_all_volumes(
filters={"attachment.instance-id": instance.id}
)
set([vol.id for vol in volumes_by_attach_instance_id]).should.equal(
{block_mapping.volume_id}
)
volumes_by_attach_status = conn.get_all_volumes(
filters={"attachment.status": "attached"}
)
set([vol.id for vol in volumes_by_attach_status]).should.equal(
{block_mapping.volume_id}
)
volumes_by_create_time = conn.get_all_volumes(
filters={"create-time": volume4.create_time}
)
set([vol.create_time for vol in volumes_by_create_time]).should.equal(
{volume4.create_time}
)
volumes_by_size = conn.get_all_volumes(filters={"size": volume2.size})
set([vol.id for vol in volumes_by_size]).should.equal({volume2.id})
volumes_by_snapshot_id = conn.get_all_volumes(filters={"snapshot-id": snapshot.id})
set([vol.id for vol in volumes_by_snapshot_id]).should.equal({volume4.id})
volumes_by_status = conn.get_all_volumes(filters={"status": "in-use"})
set([vol.id for vol in volumes_by_status]).should.equal({block_mapping.volume_id})
volumes_by_id = conn.get_all_volumes(filters={"volume-id": volume1.id})
set([vol.id for vol in volumes_by_id]).should.equal({volume1.id})
volumes_by_tag_key = conn.get_all_volumes(filters={"tag-key": "testkey1"})
set([vol.id for vol in volumes_by_tag_key]).should.equal({volume1.id})
volumes_by_tag_value = conn.get_all_volumes(filters={"tag-value": "testvalue1"})
set([vol.id for vol in volumes_by_tag_value]).should.equal({volume1.id})
volumes_by_tag = conn.get_all_volumes(filters={"tag:testkey1": "testvalue1"})
set([vol.id for vol in volumes_by_tag]).should.equal({volume1.id})
volumes_by_unencrypted = conn.get_all_volumes(filters={"encrypted": "false"})
set(
[vol.id for vol in volumes_by_unencrypted if vol.id in volume_ids]
).should.equal({block_mapping.volume_id, volume2.id})
volumes_by_encrypted = conn.get_all_volumes(filters={"encrypted": "true"})
set([vol.id for vol in volumes_by_encrypted if vol.id in volume_ids]).should.equal(
{volume1.id, volume3.id, volume4.id}
)
volumes_by_availability_zone = conn.get_all_volumes(
filters={"availability-zone": "us-east-1b"}
)
set(
[vol.id for vol in volumes_by_availability_zone if vol.id in volume_ids]
).should.equal({volume2.id})
@mock_ec2
def test_volume_filters_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -496,65 +253,6 @@ def test_volume_filters_boto3():
[vol["VolumeId"] for vol in volumes_by_attach_device].should.contain(volume4.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_volume_attach_and_detach():
conn = boto.ec2.connect_to_region("us-east-1")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
volume = conn.create_volume(80, "us-east-1a")
volume.update()
volume.volume_state().should.equal("available")
with pytest.raises(EC2ResponseError) as ex:
volume.attach(instance.id, "/dev/sdh", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the AttachVolume operation: Request would have succeeded, but DryRun flag is set"
)
volume.attach(instance.id, "/dev/sdh")
volume.update()
volume.volume_state().should.equal("in-use")
volume.attachment_state().should.equal("attached")
volume.attach_data.instance_id.should.equal(instance.id)
with pytest.raises(EC2ResponseError) as ex:
volume.detach(dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DetachVolume operation: Request would have succeeded, but DryRun flag is set"
)
volume.detach()
volume.update()
volume.volume_state().should.equal("available")
with pytest.raises(EC2ResponseError) as cm1:
volume.attach("i-1234abcd", "/dev/sdh")
cm1.value.code.should.equal("InvalidInstanceID.NotFound")
cm1.value.status.should.equal(400)
cm1.value.request_id.should_not.be.none
with pytest.raises(EC2ResponseError) as cm2:
conn.detach_volume(volume.id, instance.id, "/dev/sdh")
cm2.value.code.should.equal("InvalidAttachment.NotFound")
cm2.value.status.should.equal(400)
cm2.value.request_id.should_not.be.none
with pytest.raises(EC2ResponseError) as cm3:
conn.detach_volume(volume.id, "i-1234abcd", "/dev/sdh")
cm3.value.code.should.equal("InvalidInstanceID.NotFound")
cm3.value.status.should.equal(400)
cm3.value.request_id.should_not.be.none
@mock_ec2
def test_volume_attach_and_detach_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -621,47 +319,6 @@ def test_volume_attach_and_detach_boto3():
ex3.value.response["Error"]["Code"].should.equal("InvalidInstanceID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_snapshot():
conn = boto.ec2.connect_to_region("us-east-1")
volume = conn.create_volume(80, "us-east-1a")
with pytest.raises(EC2ResponseError) as ex:
snapshot = volume.create_snapshot("a dryrun snapshot", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateSnapshot operation: Request would have succeeded, but DryRun flag is set"
)
snapshot = volume.create_snapshot("a test snapshot")
snapshot.update()
snapshot.status.should.equal("completed")
snapshots = [snap for snap in conn.get_all_snapshots() if snap.id == snapshot.id]
snapshots.should.have.length_of(1)
snapshots[0].description.should.equal("a test snapshot")
snapshots[0].start_time.should_not.be.none
snapshots[0].encrypted.should.be(False)
# Create snapshot without description
num_snapshots = len(conn.get_all_snapshots())
snapshot = volume.create_snapshot()
conn.get_all_snapshots().should.have.length_of(num_snapshots + 1)
snapshot.delete()
conn.get_all_snapshots().should.have.length_of(num_snapshots)
# Deleting something that was already deleted should throw an error
with pytest.raises(EC2ResponseError) as cm:
snapshot.delete()
cm.value.code.should.equal("InvalidSnapshot.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_create_snapshot_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -706,22 +363,6 @@ def test_create_snapshot_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidSnapshot.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_encrypted_snapshot():
conn = boto.ec2.connect_to_region("us-east-1")
volume = conn.create_volume(80, "us-east-1a", encrypted=True)
snapshot = volume.create_snapshot("a test snapshot")
snapshot.update()
snapshot.status.should.equal("completed")
snapshots = [snap for snap in conn.get_all_snapshots() if snap.id == snapshot.id]
snapshots.should.have.length_of(1)
snapshots[0].description.should.equal("a test snapshot")
snapshots[0].start_time.should_not.be.none
snapshots[0].encrypted.should.be(True)
@mock_ec2
@pytest.mark.parametrize("encrypted", [True, False])
def test_create_encrypted_snapshot_boto3(encrypted):
@ -746,34 +387,6 @@ def test_create_encrypted_snapshot_boto3(encrypted):
snapshots[0]["Encrypted"].should.be(encrypted)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_filter_snapshot_by_id():
conn = boto.ec2.connect_to_region("us-east-1")
volume1 = conn.create_volume(36, "us-east-1a")
volume1.create_snapshot("a test snapshot 1")
volume2 = conn.create_volume(42, "us-east-1a")
snap2 = volume2.create_snapshot("a test snapshot 2")
volume3 = conn.create_volume(84, "us-east-1a")
snap3 = volume3.create_snapshot("a test snapshot 3")
snapshots1 = conn.get_all_snapshots(snapshot_ids=snap2.id)
snapshots1.should.have.length_of(1)
snapshots1[0].volume_id.should.equal(volume2.id)
snapshots1[0].region.name.should.equal(conn.region.name)
snapshots2 = conn.get_all_snapshots(snapshot_ids=[snap2.id, snap3.id])
snapshots2.should.have.length_of(2)
for s in snapshots2:
s.start_time.should_not.be.none
s.volume_id.should.be.within([volume2.id, volume3.id])
s.region.name.should.equal(conn.region.name)
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_snapshots(snapshot_ids=["snap-does_not_exist"])
cm.value.code.should.equal("InvalidSnapshot.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_filter_snapshot_by_id_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -802,71 +415,6 @@ def test_filter_snapshot_by_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidSnapshot.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_snapshot_filters():
conn = boto.ec2.connect_to_region("us-east-1")
volume1 = conn.create_volume(20, "us-east-1a", encrypted=False)
volume2 = conn.create_volume(25, "us-east-1a", encrypted=True)
snapshot1 = volume1.create_snapshot(description="testsnapshot1")
snapshot2 = volume1.create_snapshot(description="testsnapshot2")
snapshot3 = volume2.create_snapshot(description="testsnapshot3")
conn.create_tags([snapshot1.id], {"testkey1": "testvalue1"})
conn.create_tags([snapshot2.id], {"testkey2": "testvalue2"})
snapshots_by_description = conn.get_all_snapshots(
filters={"description": "testsnapshot1"}
)
set([snap.id for snap in snapshots_by_description]).should.equal({snapshot1.id})
snapshots_by_id = conn.get_all_snapshots(filters={"snapshot-id": snapshot1.id})
set([snap.id for snap in snapshots_by_id]).should.equal({snapshot1.id})
snapshots_by_start_time = conn.get_all_snapshots(
filters={"start-time": snapshot1.start_time}
)
set([snap.start_time for snap in snapshots_by_start_time]).should.equal(
{snapshot1.start_time}
)
snapshots_by_volume_id = conn.get_all_snapshots(filters={"volume-id": volume1.id})
set([snap.id for snap in snapshots_by_volume_id]).should.equal(
{snapshot1.id, snapshot2.id}
)
snapshots_by_status = conn.get_all_snapshots(filters={"status": "completed"})
(
{snapshot1.id, snapshot2.id, snapshot3.id}
- {snap.id for snap in snapshots_by_status}
).should.have.length_of(0)
snapshots_by_volume_size = conn.get_all_snapshots(
filters={"volume-size": volume1.size}
)
set([snap.id for snap in snapshots_by_volume_size]).should.equal(
{snapshot1.id, snapshot2.id}
)
snapshots_by_tag_key = conn.get_all_snapshots(filters={"tag-key": "testkey1"})
set([snap.id for snap in snapshots_by_tag_key]).should.equal({snapshot1.id})
snapshots_by_tag_value = conn.get_all_snapshots(filters={"tag-value": "testvalue1"})
set([snap.id for snap in snapshots_by_tag_value]).should.equal({snapshot1.id})
snapshots_by_tag = conn.get_all_snapshots(filters={"tag:testkey1": "testvalue1"})
set([snap.id for snap in snapshots_by_tag]).should.equal({snapshot1.id})
snapshots_by_encrypted = conn.get_all_snapshots(filters={"encrypted": "true"})
set([snap.id for snap in snapshots_by_encrypted]).should.equal({snapshot3.id})
snapshots_by_owner_id = conn.get_all_snapshots(filters={"owner-id": OWNER_ID})
set([snap.id for snap in snapshots_by_owner_id]).should.equal(
{snapshot1.id, snapshot2.id, snapshot3.id}
)
@mock_ec2
def test_snapshot_filters_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -937,115 +485,6 @@ def test_snapshot_filters_boto3():
[s["SnapshotId"] for s in snapshots].should.contain(snapshot3.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_snapshot_attribute():
conn = boto.ec2.connect_to_region("us-east-1")
volume = conn.create_volume(80, "us-east-1a")
snapshot = volume.create_snapshot()
# Baseline
attributes = conn.get_snapshot_attribute(
snapshot.id, attribute="createVolumePermission"
)
attributes.name.should.equal("create_volume_permission")
attributes.attrs.should.have.length_of(0)
ADD_GROUP_ARGS = {
"snapshot_id": snapshot.id,
"attribute": "createVolumePermission",
"operation": "add",
"groups": "all",
}
REMOVE_GROUP_ARGS = {
"snapshot_id": snapshot.id,
"attribute": "createVolumePermission",
"operation": "remove",
"groups": "all",
}
# Add 'all' group and confirm
with pytest.raises(EC2ResponseError) as ex:
conn.modify_snapshot_attribute(**dict(ADD_GROUP_ARGS, **{"dry_run": True}))
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ModifySnapshotAttribute operation: Request would have succeeded, but DryRun flag is set"
)
conn.modify_snapshot_attribute(**ADD_GROUP_ARGS)
attributes = conn.get_snapshot_attribute(
snapshot.id, attribute="createVolumePermission"
)
attributes.attrs["groups"].should.have.length_of(1)
attributes.attrs["groups"].should.equal(["all"])
# Add is idempotent
conn.modify_snapshot_attribute.when.called_with(**ADD_GROUP_ARGS).should_not.throw(
EC2ResponseError
)
# Remove 'all' group and confirm
with pytest.raises(EC2ResponseError) as ex:
conn.modify_snapshot_attribute(**dict(REMOVE_GROUP_ARGS, **{"dry_run": True}))
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ModifySnapshotAttribute operation: Request would have succeeded, but DryRun flag is set"
)
conn.modify_snapshot_attribute(**REMOVE_GROUP_ARGS)
attributes = conn.get_snapshot_attribute(
snapshot.id, attribute="createVolumePermission"
)
attributes.attrs.should.have.length_of(0)
# Remove is idempotent
conn.modify_snapshot_attribute.when.called_with(
**REMOVE_GROUP_ARGS
).should_not.throw(EC2ResponseError)
# Error: Add with group != 'all'
with pytest.raises(EC2ResponseError) as cm:
conn.modify_snapshot_attribute(
snapshot.id,
attribute="createVolumePermission",
operation="add",
groups="everyone",
)
cm.value.code.should.equal("InvalidAMIAttributeItemValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Add with invalid snapshot ID
with pytest.raises(EC2ResponseError) as cm:
conn.modify_snapshot_attribute(
"snapshot-abcd1234",
attribute="createVolumePermission",
operation="add",
groups="all",
)
cm.value.code.should.equal("InvalidSnapshot.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Remove with invalid snapshot ID
with pytest.raises(EC2ResponseError) as cm:
conn.modify_snapshot_attribute(
"snapshot-abcd1234",
attribute="createVolumePermission",
operation="remove",
groups="all",
)
cm.value.code.should.equal("InvalidSnapshot.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_modify_snapshot_attribute():
ec2_client = boto3.client("ec2", region_name="us-east-1")
@ -1215,46 +654,6 @@ def test_modify_snapshot_attribute():
assert len(attributes["CreateVolumePermissions"]) == 0
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_volume_from_snapshot():
conn = boto.ec2.connect_to_region("us-east-1")
volume = conn.create_volume(80, "us-east-1a")
snapshot = volume.create_snapshot("a test snapshot")
with pytest.raises(EC2ResponseError) as ex:
snapshot = volume.create_snapshot("a test snapshot", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateSnapshot operation: Request would have succeeded, but DryRun flag is set"
)
snapshot = volume.create_snapshot("a test snapshot")
snapshot.update()
snapshot.status.should.equal("completed")
new_volume = snapshot.create_volume("us-east-1a")
new_volume.size.should.equal(80)
new_volume.snapshot_id.should.equal(snapshot.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_volume_from_encrypted_snapshot():
conn = boto.ec2.connect_to_region("us-east-1")
volume = conn.create_volume(80, "us-east-1a", encrypted=True)
snapshot = volume.create_snapshot("a test snapshot")
snapshot.update()
snapshot.status.should.equal("completed")
new_volume = snapshot.create_volume("us-east-1a")
new_volume.size.should.equal(80)
new_volume.snapshot_id.should.equal(snapshot.id)
new_volume.encrypted.should.be(True)
@mock_ec2
@pytest.mark.parametrize("encrypted", [True, False])
def test_create_volume_from_snapshot_boto3(encrypted):
@ -1275,38 +674,6 @@ def test_create_volume_from_snapshot_boto3(encrypted):
new_volume["Encrypted"].should.equal(encrypted)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_modify_attribute_blockDeviceMapping():
"""
Reproduces the missing feature explained at [0], where we want to mock a
call to modify an instance attribute of type: blockDeviceMapping.
[0] https://github.com/spulec/moto/issues/160
"""
conn = boto.ec2.connect_to_region("us-east-1")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
with pytest.raises(EC2ResponseError) as ex:
instance.modify_attribute(
"blockDeviceMapping", {"/dev/sda1": True}, dry_run=True
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ModifyInstanceAttribute operation: Request would have succeeded, but DryRun flag is set"
)
instance.modify_attribute("blockDeviceMapping", {"/dev/sda1": True})
instance = ec2_backends[conn.region.name].get_instance(instance.id)
instance.block_device_mapping.should.have.key("/dev/sda1")
instance.block_device_mapping["/dev/sda1"].delete_on_termination.should.be(True)
@mock_ec2
def test_modify_attribute_blockDeviceMapping_boto3():
"""
@ -1346,29 +713,6 @@ def test_modify_attribute_blockDeviceMapping_boto3():
mapping["Ebs"]["DeleteOnTermination"].should.be(True)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_volume_tag_escaping():
conn = boto.ec2.connect_to_region("us-east-1")
vol = conn.create_volume(10, "us-east-1a")
snapshot = conn.create_snapshot(vol.id, "Desc")
with pytest.raises(EC2ResponseError) as ex:
snapshot.add_tags({"key": "</closed>"}, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateTags operation: Request would have succeeded, but DryRun flag is set"
)
snaps = [snap for snap in conn.get_all_snapshots() if snap.id == snapshot.id]
dict(snaps[0].tags).should_not.be.equal({"key": "</closed>"})
snapshot.add_tags({"key": "</closed>"})
snaps = [snap for snap in conn.get_all_snapshots() if snap.id == snapshot.id]
dict(snaps[0].tags).should.equal({"key": "</closed>"})
@mock_ec2
def test_volume_tag_escaping_boto3():
client = boto3.client("ec2", region_name="us-east-1")

View File

@ -1,51 +1,17 @@
import pytest
import boto
import boto3
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
from uuid import uuid4
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2, mock_ec2_deprecated
from moto import mock_ec2
from tests import EXAMPLE_AMI_ID
import logging
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_allocate_classic():
"""Allocate/release Classic EIP"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as ex:
standard = conn.allocate_address(dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the AllocateAddress operation: Request would have succeeded, but DryRun flag is set"
)
standard = conn.allocate_address()
standard.should.be.a(boto.ec2.address.Address)
standard.public_ip.should.be.a(str)
standard.instance_id.should.be.none
standard.domain.should.be.equal("standard")
with pytest.raises(EC2ResponseError) as ex:
standard.release(dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ReleaseAddress operation: Request would have succeeded, but DryRun flag is set"
)
standard.release()
standard.should_not.be.within(conn.get_all_addresses())
@mock_ec2
def test_eip_allocate_classic_boto3():
"""Allocate/release Classic EIP"""
@ -83,27 +49,6 @@ def test_eip_allocate_classic_boto3():
[a["PublicIp"] for a in all_addresses].shouldnt.contain(public_ip)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_allocate_vpc():
"""Allocate/release VPC EIP"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as ex:
vpc = conn.allocate_address(domain="vpc", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the AllocateAddress operation: Request would have succeeded, but DryRun flag is set"
)
vpc = conn.allocate_address(domain="vpc")
vpc.should.be.a(boto.ec2.address.Address)
vpc.domain.should.be.equal("vpc")
logging.debug("vpc alloc_id:".format(vpc.allocation_id))
vpc.release()
@mock_ec2
def test_describe_addresses_dryrun():
client = boto3.client("ec2", region_name="us-east-1")
@ -162,19 +107,6 @@ def test_specific_eip_allocate_vpc():
logging.debug("vpc alloc_id:".format(vpc["AllocationId"]))
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_allocate_invalid_domain():
"""Allocate EIP invalid domain"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.allocate_address(domain="bogus")
cm.value.code.should.equal("InvalidParameterValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_eip_allocate_invalid_domain_boto3():
"""Allocate EIP invalid domain"""
@ -187,58 +119,6 @@ def test_eip_allocate_invalid_domain_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidParameterValue")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_associate_classic():
"""Associate/Disassociate EIP to classic instance"""
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
eip = conn.allocate_address()
eip.instance_id.should.be.none
with pytest.raises(EC2ResponseError) as cm:
conn.associate_address(public_ip=eip.public_ip)
cm.value.code.should.equal("MissingParameter")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
with pytest.raises(EC2ResponseError) as ex:
conn.associate_address(
instance_id=instance.id, public_ip=eip.public_ip, dry_run=True
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the AssociateAddress operation: Request would have succeeded, but DryRun flag is set"
)
conn.associate_address(instance_id=instance.id, public_ip=eip.public_ip)
# no .update() on address ):
eip = conn.get_all_addresses(addresses=[eip.public_ip])[0]
eip.instance_id.should.be.equal(instance.id)
with pytest.raises(EC2ResponseError) as ex:
conn.disassociate_address(public_ip=eip.public_ip, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DisAssociateAddress operation: Request would have succeeded, but DryRun flag is set"
)
conn.disassociate_address(public_ip=eip.public_ip)
# no .update() on address ):
eip = conn.get_all_addresses(addresses=[eip.public_ip])[0]
eip.instance_id.should.be.equal("")
eip.release()
eip.should_not.be.within(conn.get_all_addresses())
eip = None
instance.terminate()
@mock_ec2
def test_eip_associate_classic_boto3():
"""Associate/Disassociate EIP to classic instance"""
@ -297,48 +177,6 @@ def test_eip_associate_classic_boto3():
instance.terminate()
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_associate_vpc():
"""Associate/Disassociate EIP to VPC instance"""
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
eip = conn.allocate_address(domain="vpc")
eip.instance_id.should.be.none
with pytest.raises(EC2ResponseError) as cm:
conn.associate_address(allocation_id=eip.allocation_id)
cm.value.code.should.equal("MissingParameter")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
conn.associate_address(instance_id=instance.id, allocation_id=eip.allocation_id)
# no .update() on address ):
eip = conn.get_all_addresses(addresses=[eip.public_ip])[0]
eip.instance_id.should.be.equal(instance.id)
conn.disassociate_address(association_id=eip.association_id)
# no .update() on address ):
eip = conn.get_all_addresses(addresses=[eip.public_ip])[0]
eip.instance_id.should.be.equal("")
eip.association_id.should.be.none
with pytest.raises(EC2ResponseError) as ex:
eip.release(dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ReleaseAddress operation: Request would have succeeded, but DryRun flag is set"
)
eip.release()
eip = None
instance.terminate()
@mock_ec2
def test_eip_associate_vpc_boto3():
"""Associate/Disassociate EIP to VPC instance"""
@ -430,38 +268,6 @@ def test_eip_boto3_vpc_association():
address.instance_id.should.be.empty
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_associate_network_interface():
"""Associate/Disassociate EIP to NIC"""
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
eni = conn.create_network_interface(subnet.id)
eip = conn.allocate_address(domain="vpc")
eip.network_interface_id.should.be.none
with pytest.raises(EC2ResponseError) as cm:
conn.associate_address(network_interface_id=eni.id)
cm.value.code.should.equal("MissingParameter")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
conn.associate_address(network_interface_id=eni.id, allocation_id=eip.allocation_id)
# no .update() on address ):
eip = conn.get_all_addresses(addresses=[eip.public_ip])[0]
eip.network_interface_id.should.be.equal(eni.id)
conn.disassociate_address(association_id=eip.association_id)
# no .update() on address ):
eip = conn.get_all_addresses(addresses=[eip.public_ip])[0]
eip.network_interface_id.should.be.equal("")
eip.association_id.should.be.none
eip.release()
eip = None
@mock_ec2
def test_eip_associate_network_interface_boto3():
"""Associate/Disassociate EIP to NIC"""
@ -497,40 +303,6 @@ def test_eip_associate_network_interface_boto3():
eip.release()
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_reassociate():
"""reassociate EIP"""
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID, min_count=2)
instance1, instance2 = reservation.instances
eip = conn.allocate_address()
conn.associate_address(instance_id=instance1.id, public_ip=eip.public_ip)
# Same ID is idempotent
conn.associate_address(instance_id=instance1.id, public_ip=eip.public_ip)
# Different ID detects resource association
with pytest.raises(EC2ResponseError) as cm:
conn.associate_address(
instance_id=instance2.id, public_ip=eip.public_ip, allow_reassociation=False
)
cm.value.code.should.equal("Resource.AlreadyAssociated")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
conn.associate_address.when.called_with(
instance_id=instance2.id, public_ip=eip.public_ip, allow_reassociation=True
).should_not.throw(EC2ResponseError)
eip.release()
instance1.terminate()
instance2.terminate()
@mock_ec2
def test_eip_reassociate_boto3():
"""reassociate EIP"""
@ -572,38 +344,6 @@ def test_eip_reassociate_boto3():
instance2.terminate()
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_reassociate_nic():
"""reassociate EIP"""
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
eni1 = conn.create_network_interface(subnet.id)
eni2 = conn.create_network_interface(subnet.id)
eip = conn.allocate_address()
conn.associate_address(network_interface_id=eni1.id, public_ip=eip.public_ip)
# Same ID is idempotent
conn.associate_address(network_interface_id=eni1.id, public_ip=eip.public_ip)
# Different ID detects resource association
with pytest.raises(EC2ResponseError) as cm:
conn.associate_address(network_interface_id=eni2.id, public_ip=eip.public_ip)
cm.value.code.should.equal("Resource.AlreadyAssociated")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
conn.associate_address.when.called_with(
network_interface_id=eni2.id, public_ip=eip.public_ip, allow_reassociation=True
).should_not.throw(EC2ResponseError)
eip.release()
eip = None
@mock_ec2
def test_eip_reassociate_nic_boto3():
"""reassociate EIP"""
@ -641,26 +381,6 @@ def test_eip_reassociate_nic_boto3():
eip.release()
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_associate_invalid_args():
"""Associate EIP, invalid args"""
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
conn.allocate_address()
with pytest.raises(EC2ResponseError) as cm:
conn.associate_address(instance_id=instance.id)
cm.value.code.should.equal("MissingParameter")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
instance.terminate()
@mock_ec2
def test_eip_associate_invalid_args_boto3():
"""Associate EIP, invalid args """
@ -681,19 +401,6 @@ def test_eip_associate_invalid_args_boto3():
instance.terminate()
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_disassociate_bogus_association():
"""Disassociate bogus EIP"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.disassociate_address(association_id="bogus")
cm.value.code.should.equal("InvalidAssociationID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_eip_disassociate_bogus_association_boto3():
"""Disassociate bogus EIP"""
@ -706,19 +413,6 @@ def test_eip_disassociate_bogus_association_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidAssociationID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_release_bogus_eip():
"""Release bogus EIP"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.release_address(allocation_id="bogus")
cm.value.code.should.equal("InvalidAllocationID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_eip_release_bogus_eip_boto3():
"""Release bogus EIP"""
@ -731,19 +425,6 @@ def test_eip_release_bogus_eip_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidAllocationID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_disassociate_arg_error():
"""Invalid arguments disassociate address"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.disassociate_address()
cm.value.code.should.equal("MissingParameter")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_eip_disassociate_arg_error_boto3():
"""Invalid arguments disassociate address"""
@ -756,19 +437,6 @@ def test_eip_disassociate_arg_error_boto3():
ex.value.response["Error"]["Code"].should.equal("MissingParameter")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_release_arg_error():
"""Invalid arguments release address"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.release_address()
cm.value.code.should.equal("MissingParameter")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_eip_release_arg_error_boto3():
"""Invalid arguments release address"""
@ -781,47 +449,6 @@ def test_eip_release_arg_error_boto3():
ex.value.response["Error"]["Code"].should.equal("MissingParameter")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_describe():
"""Listing of allocated Elastic IP Addresses."""
conn = boto.connect_ec2("the_key", "the_secret")
eips = []
number_of_classic_ips = 2
number_of_vpc_ips = 2
# allocate some IPs
for _ in range(number_of_classic_ips):
eips.append(conn.allocate_address())
for _ in range(number_of_vpc_ips):
eips.append(conn.allocate_address(domain="vpc"))
len(eips).should.be.equal(number_of_classic_ips + number_of_vpc_ips)
# Can we find each one individually?
for eip in eips:
if eip.allocation_id:
lookup_addresses = conn.get_all_addresses(
allocation_ids=[eip.allocation_id]
)
else:
lookup_addresses = conn.get_all_addresses(addresses=[eip.public_ip])
len(lookup_addresses).should.be.equal(1)
lookup_addresses[0].public_ip.should.be.equal(eip.public_ip)
# Can we find first two when we search for them?
lookup_addresses = conn.get_all_addresses(
addresses=[eips[0].public_ip, eips[1].public_ip]
)
len(lookup_addresses).should.be.equal(2)
lookup_addresses[0].public_ip.should.be.equal(eips[0].public_ip)
lookup_addresses[1].public_ip.should.be.equal(eips[1].public_ip)
# Release all IPs
for eip in eips:
eip.release()
len(conn.get_all_addresses()).should.be.equal(0)
@mock_ec2
def test_eip_describe_boto3():
"""Listing of allocated Elastic IP Addresses."""
@ -868,19 +495,6 @@ def test_eip_describe_boto3():
[a["PublicIp"] for a in all_addresses].shouldnt.contain(eips[1].public_ip)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_eip_describe_none():
"""Error when search for bogus IP"""
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_addresses(addresses=["256.256.256.256"])
cm.value.code.should.equal("InvalidAddress.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_eip_describe_none_boto3():
"""Error when search for bogus IP"""

View File

@ -3,62 +3,14 @@ import random
import boto3
from botocore.exceptions import ClientError
import boto
import boto.ec2
from boto.exception import EC2ResponseError
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2, mock_ec2_deprecated, settings
from moto import mock_ec2, settings
from moto.ec2.utils import random_private_ip
from tests import EXAMPLE_AMI_ID
from tests.helpers import requires_boto_gte
from uuid import uuid4
# Has boto3 equivalent
@mock_ec2_deprecated
def test_elastic_network_interfaces():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
with pytest.raises(EC2ResponseError) as ex:
eni = conn.create_network_interface(subnet.id, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateNetworkInterface operation: Request would have succeeded, but DryRun flag is set"
)
conn.create_network_interface(subnet.id)
all_enis = conn.get_all_network_interfaces()
all_enis.should.have.length_of(1)
eni = all_enis[0]
eni.groups.should.have.length_of(1)
eni.private_ip_addresses.should.have.length_of(1)
eni.private_ip_addresses[0].private_ip_address.startswith("10.").should.be.true
with pytest.raises(EC2ResponseError) as ex:
conn.delete_network_interface(eni.id, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DeleteNetworkInterface operation: Request would have succeeded, but DryRun flag is set"
)
conn.delete_network_interface(eni.id)
all_enis = conn.get_all_network_interfaces()
all_enis.should.have.length_of(0)
with pytest.raises(EC2ResponseError) as cm:
conn.delete_network_interface(eni.id)
cm.value.error_code.should.equal("InvalidNetworkInterfaceID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_elastic_network_interfaces_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -116,18 +68,6 @@ def test_elastic_network_interfaces_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_elastic_network_interfaces_subnet_validation():
conn = boto.connect_vpc("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.create_network_interface("subnet-abcd1234")
cm.value.error_code.should.equal("InvalidSubnetID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_elastic_network_interfaces_subnet_validation_boto3():
client = boto3.client("ec2", "us-east-1")
@ -139,25 +79,6 @@ def test_elastic_network_interfaces_subnet_validation_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidSubnetID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_elastic_network_interfaces_with_private_ip():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
private_ip = "54.0.0.1"
eni = conn.create_network_interface(subnet.id, private_ip)
all_enis = conn.get_all_network_interfaces()
all_enis.should.have.length_of(1)
eni = all_enis[0]
eni.groups.should.have.length_of(1)
eni.private_ip_addresses.should.have.length_of(1)
eni.private_ip_addresses[0].private_ip_address.should.equal(private_ip)
@mock_ec2
def test_elastic_network_interfaces_with_private_ip_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -183,32 +104,6 @@ def test_elastic_network_interfaces_with_private_ip_boto3():
eni["PrivateIpAddresses"][0]["PrivateIpAddress"].should.equal(private_ip)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_elastic_network_interfaces_with_groups():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
security_group1 = conn.create_security_group(
"test security group #1", "this is a test security group"
)
security_group2 = conn.create_security_group(
"test security group #2", "this is a test security group"
)
conn.create_network_interface(
subnet.id, groups=[security_group1.id, security_group2.id]
)
all_enis = conn.get_all_network_interfaces()
all_enis.should.have.length_of(1)
eni = all_enis[0]
eni.groups.should.have.length_of(2)
set([group.id for group in eni.groups]).should.equal(
set([security_group1.id, security_group2.id])
)
@mock_ec2
def test_elastic_network_interfaces_with_groups_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -250,51 +145,6 @@ def test_elastic_network_interfaces_without_group():
my_eni["Groups"][0]["GroupName"].should.equal("default")
# Has boto3 equivalent
@requires_boto_gte("2.12.0")
@mock_ec2_deprecated
def test_elastic_network_interfaces_modify_attribute():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
security_group1 = conn.create_security_group(
"test security group #1", "this is a test security group"
)
security_group2 = conn.create_security_group(
"test security group #2", "this is a test security group"
)
conn.create_network_interface(subnet.id, groups=[security_group1.id])
all_enis = conn.get_all_network_interfaces()
all_enis.should.have.length_of(1)
eni = all_enis[0]
eni.groups.should.have.length_of(1)
eni.groups[0].id.should.equal(security_group1.id)
with pytest.raises(EC2ResponseError) as ex:
conn.modify_network_interface_attribute(
eni.id, "groupset", [security_group1.id, security_group2.id], dry_run=True
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ModifyNetworkInterface operation: Request would have succeeded, but DryRun flag is set"
)
conn.modify_network_interface_attribute(
eni.id, "groupset", [security_group1.id, security_group2.id]
)
all_enis = conn.get_all_network_interfaces()
all_enis.should.have.length_of(1)
eni = all_enis[0]
eni.groups.should.have.length_of(2)
eni.groups[0].id.should.equal(security_group1.id)
eni.groups[1].id.should.equal(security_group2.id)
@mock_ec2
def test_elastic_network_interfaces_modify_attribute_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -334,68 +184,6 @@ def test_elastic_network_interfaces_modify_attribute_boto3():
my_eni["Groups"][0]["GroupId"].should.equal(sec_group2.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_elastic_network_interfaces_filtering():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
security_group1 = conn.create_security_group(
"test security group #1", "this is a test security group"
)
security_group2 = conn.create_security_group(
"test security group #2", "this is a test security group"
)
eni1 = conn.create_network_interface(
subnet.id, groups=[security_group1.id, security_group2.id]
)
eni2 = conn.create_network_interface(subnet.id, groups=[security_group1.id])
eni3 = conn.create_network_interface(subnet.id, description="test description")
all_enis = conn.get_all_network_interfaces()
all_enis.should.have.length_of(3)
# Filter by NetworkInterfaceId
enis_by_id = conn.get_all_network_interfaces([eni1.id])
enis_by_id.should.have.length_of(1)
set([eni.id for eni in enis_by_id]).should.equal(set([eni1.id]))
# Filter by ENI ID
enis_by_id = conn.get_all_network_interfaces(
filters={"network-interface-id": eni1.id}
)
enis_by_id.should.have.length_of(1)
set([eni.id for eni in enis_by_id]).should.equal(set([eni1.id]))
# Filter by Security Group
enis_by_group = conn.get_all_network_interfaces(
filters={"group-id": security_group1.id}
)
enis_by_group.should.have.length_of(2)
set([eni.id for eni in enis_by_group]).should.equal(set([eni1.id, eni2.id]))
# Filter by ENI ID and Security Group
enis_by_group = conn.get_all_network_interfaces(
filters={"network-interface-id": eni1.id, "group-id": security_group1.id}
)
enis_by_group.should.have.length_of(1)
set([eni.id for eni in enis_by_group]).should.equal(set([eni1.id]))
# Filter by Description
enis_by_description = conn.get_all_network_interfaces(
filters={"description": eni3.description}
)
enis_by_description.should.have.length_of(1)
enis_by_description[0].description.should.equal(eni3.description)
# Unsupported filter
conn.get_all_network_interfaces.when.called_with(
filters={"not-implemented-filter": "foobar"}
).should.throw(NotImplementedError)
@mock_ec2
def test_elastic_network_interfaces_filtering_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")

View File

@ -1,37 +1,13 @@
import pytest
import boto
import boto3
from boto.exception import EC2ResponseError
import sure # noqa # pylint: disable=unused-import
from botocore.exceptions import ClientError
from moto import mock_ec2_deprecated, mock_ec2
from moto import mock_ec2
from tests import EXAMPLE_AMI_ID
# Has boto3 equivalent
@mock_ec2_deprecated
def test_console_output():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance_id = reservation.instances[0].id
output = conn.get_console_output(instance_id)
output.output.should_not.equal(None)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_console_output_without_instance():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.get_console_output("i-1234abcd")
cm.value.error_code.should.equal("InvalidInstanceID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_console_output_boto3():
conn = boto3.resource("ec2", "us-east-1")

File diff suppressed because it is too large Load Diff

View File

@ -1,14 +1,12 @@
import pytest
import boto
import boto3
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2_deprecated, mock_ec2
from moto import mock_ec2
from uuid import uuid4
@ -17,30 +15,6 @@ BAD_VPC = "vpc-deadbeef"
BAD_IGW = "igw-deadbeef"
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_create():
"""internet gateway create"""
conn = boto.connect_vpc("the_key", "the_secret")
conn.get_all_internet_gateways().should.have.length_of(0)
with pytest.raises(EC2ResponseError) as ex:
igw = conn.create_internet_gateway(dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateInternetGateway operation: Request would have succeeded, but DryRun flag is set"
)
igw = conn.create_internet_gateway()
conn.get_all_internet_gateways().should.have.length_of(1)
igw.id.should.match(r"igw-[0-9a-f]+")
igw = conn.get_all_internet_gateways()[0]
igw.attachments.should.have.length_of(0)
@mock_ec2
def test_igw_create_boto3():
""" internet gateway create """
@ -64,28 +38,6 @@ def test_igw_create_boto3():
igw["Attachments"].should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_attach():
"""internet gateway attach"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
vpc = conn.create_vpc(VPC_CIDR)
with pytest.raises(EC2ResponseError) as ex:
conn.attach_internet_gateway(igw.id, vpc.id, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the AttachInternetGateway operation: Request would have succeeded, but DryRun flag is set"
)
conn.attach_internet_gateway(igw.id, vpc.id)
igw = conn.get_all_internet_gateways()[0]
igw.attachments[0].vpc_id.should.be.equal(vpc.id)
@mock_ec2
def test_igw_attach_boto3():
""" internet gateway attach """
@ -111,20 +63,6 @@ def test_igw_attach_boto3():
igw["Attachments"].should.equal([{"State": "available", "VpcId": vpc.id}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_attach_bad_vpc():
"""internet gateway fail to attach w/ bad vpc"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
with pytest.raises(EC2ResponseError) as cm:
conn.attach_internet_gateway(igw.id, BAD_VPC)
cm.value.code.should.equal("InvalidVpcID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_igw_attach_bad_vpc_boto3():
""" internet gateway fail to attach w/ bad vpc """
@ -138,23 +76,6 @@ def test_igw_attach_bad_vpc_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidVpcID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_attach_twice():
"""internet gateway fail to attach twice"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
vpc1 = conn.create_vpc(VPC_CIDR)
vpc2 = conn.create_vpc(VPC_CIDR)
conn.attach_internet_gateway(igw.id, vpc1.id)
with pytest.raises(EC2ResponseError) as cm:
conn.attach_internet_gateway(igw.id, vpc2.id)
cm.value.code.should.equal("Resource.AlreadyAssociated")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_igw_attach_twice_boto3():
""" internet gateway fail to attach twice """
@ -172,28 +93,6 @@ def test_igw_attach_twice_boto3():
ex.value.response["Error"]["Code"].should.equal("Resource.AlreadyAssociated")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_detach():
"""internet gateway detach"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
vpc = conn.create_vpc(VPC_CIDR)
conn.attach_internet_gateway(igw.id, vpc.id)
with pytest.raises(EC2ResponseError) as ex:
conn.detach_internet_gateway(igw.id, vpc.id, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DetachInternetGateway operation: Request would have succeeded, but DryRun flag is set"
)
conn.detach_internet_gateway(igw.id, vpc.id)
igw = conn.get_all_internet_gateways()[0]
igw.attachments.should.have.length_of(0)
@mock_ec2
def test_igw_detach_boto3():
""" internet gateway detach"""
@ -220,23 +119,6 @@ def test_igw_detach_boto3():
igw["Attachments"].should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_detach_wrong_vpc():
"""internet gateway fail to detach w/ wrong vpc"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
vpc1 = conn.create_vpc(VPC_CIDR)
vpc2 = conn.create_vpc(VPC_CIDR)
conn.attach_internet_gateway(igw.id, vpc1.id)
with pytest.raises(EC2ResponseError) as cm:
conn.detach_internet_gateway(igw.id, vpc2.id)
cm.value.code.should.equal("Gateway.NotAttached")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_igw_detach_wrong_vpc_boto3():
""" internet gateway fail to detach w/ wrong vpc """
@ -254,22 +136,6 @@ def test_igw_detach_wrong_vpc_boto3():
ex.value.response["Error"]["Code"].should.equal("Gateway.NotAttached")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_detach_invalid_vpc():
"""internet gateway fail to detach w/ invalid vpc"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
vpc = conn.create_vpc(VPC_CIDR)
conn.attach_internet_gateway(igw.id, vpc.id)
with pytest.raises(EC2ResponseError) as cm:
conn.detach_internet_gateway(igw.id, BAD_VPC)
cm.value.code.should.equal("Gateway.NotAttached")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_igw_detach_invalid_vpc_boto3():
""" internet gateway fail to detach w/ invalid vpc """
@ -286,21 +152,6 @@ def test_igw_detach_invalid_vpc_boto3():
ex.value.response["Error"]["Code"].should.equal("Gateway.NotAttached")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_detach_unattached():
"""internet gateway fail to detach unattached"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
vpc = conn.create_vpc(VPC_CIDR)
with pytest.raises(EC2ResponseError) as cm:
conn.detach_internet_gateway(igw.id, vpc.id)
cm.value.code.should.equal("Gateway.NotAttached")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_igw_detach_unattached_boto3():
""" internet gateway fail to detach unattached """
@ -316,28 +167,6 @@ def test_igw_detach_unattached_boto3():
ex.value.response["Error"]["Code"].should.equal("Gateway.NotAttached")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_delete():
"""internet gateway delete"""
conn = boto.connect_vpc("the_key", "the_secret")
conn.create_vpc(VPC_CIDR)
conn.get_all_internet_gateways().should.have.length_of(0)
igw = conn.create_internet_gateway()
conn.get_all_internet_gateways().should.have.length_of(1)
with pytest.raises(EC2ResponseError) as ex:
conn.delete_internet_gateway(igw.id, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DeleteInternetGateway operation: Request would have succeeded, but DryRun flag is set"
)
conn.delete_internet_gateway(igw.id)
conn.get_all_internet_gateways().should.have.length_of(0)
@mock_ec2
def test_igw_delete_boto3():
""" internet gateway delete"""
@ -360,22 +189,6 @@ def test_igw_delete_boto3():
[i["InternetGatewayId"] for i in (retrieve_all(client))].shouldnt.contain(igw.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_delete_attached():
"""internet gateway fail to delete attached"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
vpc = conn.create_vpc(VPC_CIDR)
conn.attach_internet_gateway(igw.id, vpc.id)
with pytest.raises(EC2ResponseError) as cm:
conn.delete_internet_gateway(igw.id)
cm.value.code.should.equal("DependencyViolation")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_igw_delete_attached_boto3():
""" internet gateway fail to delete attached """
@ -392,16 +205,6 @@ def test_igw_delete_attached_boto3():
ex.value.response["Error"]["Code"].should.equal("DependencyViolation")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_desribe():
"""internet gateway fetch by id"""
conn = boto.connect_vpc("the_key", "the_secret")
igw = conn.create_internet_gateway()
igw_by_search = conn.get_all_internet_gateways([igw.id])[0]
igw.id.should.equal(igw_by_search.id)
@mock_ec2
def test_igw_describe_boto3():
""" internet gateway fetch by id """
@ -414,18 +217,6 @@ def test_igw_describe_boto3():
igw.id.should.equal(igw_by_search["InternetGatewayId"])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_describe_bad_id():
"""internet gateway fail to fetch by bad id"""
conn = boto.connect_vpc("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_internet_gateways([BAD_IGW])
cm.value.code.should.equal("InvalidInternetGatewayID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_igw_describe_bad_id_boto3():
""" internet gateway fail to fetch by bad id """
@ -437,22 +228,6 @@ def test_igw_describe_bad_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidInternetGatewayID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_filter_by_vpc_id():
"""internet gateway filter by vpc id"""
conn = boto.connect_vpc("the_key", "the_secret")
igw1 = conn.create_internet_gateway()
conn.create_internet_gateway()
vpc = conn.create_vpc(VPC_CIDR)
conn.attach_internet_gateway(igw1.id, vpc.id)
result = conn.get_all_internet_gateways(filters={"attachment.vpc-id": vpc.id})
result.should.have.length_of(1)
result[0].id.should.equal(igw1.id)
@mock_ec2
def test_igw_filter_by_vpc_id_boto3():
""" internet gateway filter by vpc id """
@ -471,21 +246,6 @@ def test_igw_filter_by_vpc_id_boto3():
result["InternetGateways"][0]["InternetGatewayId"].should.equal(igw1.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_filter_by_tags():
"""internet gateway filter by vpc id"""
conn = boto.connect_vpc("the_key", "the_secret")
igw1 = conn.create_internet_gateway()
conn.create_internet_gateway()
igw1.add_tag("tests", "yes")
result = conn.get_all_internet_gateways(filters={"tag:tests": "yes"})
result.should.have.length_of(1)
result[0].id.should.equal(igw1.id)
@mock_ec2
def test_igw_filter_by_tags_boto3():
""" internet gateway filter by vpc id """
@ -502,20 +262,6 @@ def test_igw_filter_by_tags_boto3():
result[0]["InternetGatewayId"].should.equal(igw1.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_filter_by_internet_gateway_id():
"""internet gateway filter by internet gateway id"""
conn = boto.connect_vpc("the_key", "the_secret")
igw1 = conn.create_internet_gateway()
conn.create_internet_gateway()
result = conn.get_all_internet_gateways(filters={"internet-gateway-id": igw1.id})
result.should.have.length_of(1)
result[0].id.should.equal(igw1.id)
@mock_ec2
def test_igw_filter_by_internet_gateway_id_boto3():
""" internet gateway filter by internet gateway id """
@ -532,22 +278,6 @@ def test_igw_filter_by_internet_gateway_id_boto3():
result["InternetGateways"][0]["InternetGatewayId"].should.equal(igw1.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_igw_filter_by_attachment_state():
"""internet gateway filter by attachment state"""
conn = boto.connect_vpc("the_key", "the_secret")
igw1 = conn.create_internet_gateway()
conn.create_internet_gateway()
vpc = conn.create_vpc(VPC_CIDR)
conn.attach_internet_gateway(igw1.id, vpc.id)
result = conn.get_all_internet_gateways(filters={"attachment.state": "available"})
result.should.have.length_of(1)
result[0].id.should.equal(igw1.id)
@mock_ec2
def test_igw_filter_by_attachment_state_boto3():
""" internet gateway filter by attachment state """

View File

@ -1,12 +1,10 @@
import pytest
import boto
import sure # noqa # pylint: disable=unused-import
import boto3
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
from moto import mock_ec2, mock_ec2_deprecated, settings
from moto import mock_ec2, settings
from uuid import uuid4
from unittest import SkipTest
@ -46,13 +44,6 @@ ffsm7UIHtCBYERr9Nx0u20ldfhkgB1lhaJb5o0ZJ3pmJ38KChfyHe5EUcqRdEFo89Mp72VI2Z6UHyL17
moto@github.com"""
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_empty():
conn = boto.connect_ec2("the_key", "the_secret")
assert len(conn.get_all_key_pairs()) == 0
@mock_ec2
def test_key_pairs_empty_boto3():
if settings.TEST_SERVER_MODE:
@ -61,18 +52,6 @@ def test_key_pairs_empty_boto3():
client.describe_key_pairs()["KeyPairs"].should.be.empty
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_invalid_id():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_key_pairs("foo")
cm.value.code.should.equal("InvalidKeyPair.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_key_pairs_invalid_id_boto3():
client = boto3.client("ec2", "us-west-1")
@ -84,49 +63,6 @@ def test_key_pairs_invalid_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidKeyPair.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_create():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as ex:
conn.create_key_pair("foo", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateKeyPair operation: Request would have succeeded, but DryRun flag is set"
)
kp = conn.create_key_pair("foo")
rsa_check_private_key(kp.material)
kps = conn.get_all_key_pairs()
assert len(kps) == 1
assert kps[0].name == "foo"
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_create_two():
conn = boto.connect_ec2("the_key", "the_secret")
kp1 = conn.create_key_pair("foo")
rsa_check_private_key(kp1.material)
kp2 = conn.create_key_pair("bar")
rsa_check_private_key(kp2.material)
assert kp1.material != kp2.material
kps = conn.get_all_key_pairs()
kps.should.have.length_of(2)
assert {i.name for i in kps} == {"foo", "bar"}
kps = conn.get_all_key_pairs("foo")
kps.should.have.length_of(1)
kps[0].name.should.equal("foo")
@mock_ec2
def test_key_pairs_create_dryrun_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -166,20 +102,6 @@ def test_key_pairs_create_boto3():
kps[0].should.have.key("KeyFingerprint")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_create_exist():
conn = boto.connect_ec2("the_key", "the_secret")
conn.create_key_pair("foo")
assert len(conn.get_all_key_pairs()) == 1
with pytest.raises(EC2ResponseError) as cm:
conn.create_key_pair("foo")
cm.value.code.should.equal("InvalidKeyPair.Duplicate")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_key_pairs_create_exist_boto3():
client = boto3.client("ec2", "us-west-1")
@ -193,40 +115,12 @@ def test_key_pairs_create_exist_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidKeyPair.Duplicate")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_delete_no_exist():
conn = boto.connect_ec2("the_key", "the_secret")
assert len(conn.get_all_key_pairs()) == 0
r = conn.delete_key_pair("foo")
r.should.be.ok
@mock_ec2
def test_key_pairs_delete_no_exist_boto3():
client = boto3.client("ec2", "us-west-1")
client.delete_key_pair(KeyName=str(uuid4())[0:6])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_delete_exist():
conn = boto.connect_ec2("the_key", "the_secret")
conn.create_key_pair("foo")
with pytest.raises(EC2ResponseError) as ex:
r = conn.delete_key_pair("foo", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DeleteKeyPair operation: Request would have succeeded, but DryRun flag is set"
)
r = conn.delete_key_pair("foo")
r.should.be.ok
assert len(conn.get_all_key_pairs()) == 0
@mock_ec2
def test_key_pairs_delete_exist_boto3():
client = boto3.client("ec2", "us-west-1")
@ -247,33 +141,6 @@ def test_key_pairs_delete_exist_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_import():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as ex:
conn.import_key_pair("foo", RSA_PUBLIC_KEY_OPENSSH, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the ImportKeyPair operation: Request would have succeeded, but DryRun flag is set"
)
kp1 = conn.import_key_pair("foo", RSA_PUBLIC_KEY_OPENSSH)
assert kp1.name == "foo"
assert kp1.fingerprint == RSA_PUBLIC_KEY_FINGERPRINT
kp2 = conn.import_key_pair("foo2", RSA_PUBLIC_KEY_RFC4716)
assert kp2.name == "foo2"
assert kp2.fingerprint == RSA_PUBLIC_KEY_FINGERPRINT
kps = conn.get_all_key_pairs()
assert len(kps) == 2
assert kps[0].name == kp1.name
assert kps[1].name == kp2.name
@mock_ec2
def test_key_pairs_import_boto3():
client = boto3.client("ec2", "us-west-1")
@ -309,21 +176,6 @@ def test_key_pairs_import_boto3():
all_names.should.contain(kp2["KeyName"])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_import_exist():
conn = boto.connect_ec2("the_key", "the_secret")
kp = conn.import_key_pair("foo", RSA_PUBLIC_KEY_OPENSSH)
assert kp.name == "foo"
assert len(conn.get_all_key_pairs()) == 1
with pytest.raises(EC2ResponseError) as cm:
conn.create_key_pair("foo")
cm.value.code.should.equal("InvalidKeyPair.Duplicate")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_key_pairs_import_exist_boto3():
client = boto3.client("ec2", "us-west-1")
@ -343,30 +195,6 @@ def test_key_pairs_import_exist_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidKeyPair.Duplicate")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pairs_invalid():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as ex:
conn.import_key_pair("foo", b"")
ex.value.error_code.should.equal("InvalidKeyPair.Format")
ex.value.status.should.equal(400)
ex.value.message.should.equal("Key is not in valid OpenSSH public key format")
with pytest.raises(EC2ResponseError) as ex:
conn.import_key_pair("foo", b"garbage")
ex.value.error_code.should.equal("InvalidKeyPair.Format")
ex.value.status.should.equal(400)
ex.value.message.should.equal("Key is not in valid OpenSSH public key format")
with pytest.raises(EC2ResponseError) as ex:
conn.import_key_pair("foo", DSA_PUBLIC_KEY_OPENSSH)
ex.value.error_code.should.equal("InvalidKeyPair.Format")
ex.value.status.should.equal(400)
ex.value.message.should.equal("Key is not in valid OpenSSH public key format")
@mock_ec2
def test_key_pairs_invalid_boto3():
client = boto3.client("ec2", "us-west-1")
@ -393,22 +221,6 @@ def test_key_pairs_invalid_boto3():
err["Message"].should.equal("Key is not in valid OpenSSH public key format")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_key_pair_filters():
conn = boto.connect_ec2("the_key", "the_secret")
_ = conn.create_key_pair("kpfltr1")
kp2 = conn.create_key_pair("kpfltr2")
kp3 = conn.create_key_pair("kpfltr3")
kp_by_name = conn.get_all_key_pairs(filters={"key-name": "kpfltr2"})
set([kp.name for kp in kp_by_name]).should.equal(set([kp2.name]))
kp_by_name = conn.get_all_key_pairs(filters={"fingerprint": kp3.fingerprint})
set([kp.name for kp in kp_by_name]).should.equal(set([kp3.name]))
@mock_ec2
def test_key_pair_filters_boto3():
ec2 = boto3.resource("ec2", "us-west-1")

View File

@ -1,24 +1,14 @@
import boto
import boto3
import sure # noqa # pylint: disable=unused-import
import pytest
from botocore.exceptions import ClientError
from moto import mock_ec2_deprecated, mock_ec2, settings
from moto import mock_ec2, settings
from moto.ec2.models import OWNER_ID
from random import randint
from unittest import SkipTest
# Has boto3 equivalent
@mock_ec2_deprecated
def test_default_network_acl_created_with_vpc():
conn = boto.connect_vpc("the_key", "the secret")
conn.create_vpc("10.0.0.0/16")
all_network_acls = conn.get_all_network_acls()
all_network_acls.should.have.length_of(2)
@mock_ec2
def test_default_network_acl_created_with_vpc_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -31,16 +21,6 @@ def test_default_network_acl_created_with_vpc_boto3():
our_acl[0].should.have.key("IsDefault").equals(True)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_network_acls():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
conn.create_network_acl(vpc.id)
all_network_acls = conn.get_all_network_acls()
all_network_acls.should.have.length_of(3)
@mock_ec2
def test_network_create_and_list_acls_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -58,21 +38,6 @@ def test_network_create_and_list_acls_boto3():
acl_found["IsDefault"].should.equal(False)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_new_subnet_associates_with_default_network_acl():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.get_all_vpcs()[0]
subnet = conn.create_subnet(vpc.id, "172.31.112.0/20")
all_network_acls = conn.get_all_network_acls()
all_network_acls.should.have.length_of(1)
acl = all_network_acls[0]
acl.associations.should.have.length_of(7)
[a.subnet_id for a in acl.associations].should.contain(subnet.id)
@mock_ec2
def test_new_subnet_associates_with_default_network_acl_boto3():
if settings.TEST_SERVER_MODE:
@ -90,36 +55,6 @@ def test_new_subnet_associates_with_default_network_acl_boto3():
[a["SubnetId"] for a in acl["Associations"]].should.contain(subnet.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_network_acl_entries():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
network_acl = conn.create_network_acl(vpc.id)
conn.create_network_acl_entry(
network_acl.id,
110,
6,
"ALLOW",
"0.0.0.0/0",
False,
port_range_from="443",
port_range_to="443",
)
all_network_acls = conn.get_all_network_acls()
all_network_acls.should.have.length_of(3)
test_network_acl = next(na for na in all_network_acls if na.id == network_acl.id)
entries = test_network_acl.network_acl_entries
entries.should.have.length_of(1)
entries[0].rule_number.should.equal("110")
entries[0].protocol.should.equal("6")
entries[0].rule_action.should.equal("ALLOW")
@mock_ec2
def test_network_acl_entries_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -155,33 +90,6 @@ def test_network_acl_entries_boto3():
entries[0]["CidrBlock"].should.equal("0.0.0.0/0")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_network_acl_entry():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
network_acl = conn.create_network_acl(vpc.id)
conn.create_network_acl_entry(
network_acl.id,
110,
6,
"ALLOW",
"0.0.0.0/0",
False,
port_range_from="443",
port_range_to="443",
)
conn.delete_network_acl_entry(network_acl.id, 110, False)
all_network_acls = conn.get_all_network_acls()
test_network_acl = next(na for na in all_network_acls if na.id == network_acl.id)
entries = test_network_acl.network_acl_entries
entries.should.have.length_of(0)
@mock_ec2
def test_delete_network_acl_entry_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -211,45 +119,6 @@ def test_delete_network_acl_entry_boto3():
test_network_acl["Entries"].should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_replace_network_acl_entry():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
network_acl = conn.create_network_acl(vpc.id)
conn.create_network_acl_entry(
network_acl.id,
110,
6,
"ALLOW",
"0.0.0.0/0",
False,
port_range_from="443",
port_range_to="443",
)
conn.replace_network_acl_entry(
network_acl.id,
110,
-1,
"DENY",
"0.0.0.0/0",
False,
port_range_from="22",
port_range_to="22",
)
all_network_acls = conn.get_all_network_acls()
test_network_acl = next(na for na in all_network_acls if na.id == network_acl.id)
entries = test_network_acl.network_acl_entries
entries.should.have.length_of(1)
entries[0].rule_number.should.equal("110")
entries[0].protocol.should.equal("-1")
entries[0].rule_action.should.equal("DENY")
@mock_ec2
def test_replace_network_acl_entry_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -290,46 +159,6 @@ def test_replace_network_acl_entry_boto3():
entries[0]["PortRange"].should.equal({"To": 22, "From": 22})
# TODO: How to convert 'associate_network_acl' to boto3?
@mock_ec2_deprecated
def test_associate_new_network_acl_with_subnet():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
network_acl = conn.create_network_acl(vpc.id)
conn.associate_network_acl(network_acl.id, subnet.id)
all_network_acls = conn.get_all_network_acls()
all_network_acls.should.have.length_of(3)
test_network_acl = next(na for na in all_network_acls if na.id == network_acl.id)
test_network_acl.associations.should.have.length_of(1)
test_network_acl.associations[0].subnet_id.should.equal(subnet.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_network_acl():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
conn.create_subnet(vpc.id, "10.0.0.0/18")
network_acl = conn.create_network_acl(vpc.id)
all_network_acls = conn.get_all_network_acls()
all_network_acls.should.have.length_of(3)
any(acl.id == network_acl.id for acl in all_network_acls).should.be.ok
conn.delete_network_acl(network_acl.id)
updated_network_acls = conn.get_all_network_acls()
updated_network_acls.should.have.length_of(2)
any(acl.id == network_acl.id for acl in updated_network_acls).shouldnt.be.ok
@mock_ec2
def test_delete_network_acl_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -350,25 +179,6 @@ def test_delete_network_acl_boto3():
).shouldnt.be.ok
# Has boto3 equivalent
@mock_ec2_deprecated
def test_network_acl_tagging():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
network_acl = conn.create_network_acl(vpc.id)
network_acl.add_tag("a key", "some value")
tag = conn.get_all_tags()[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
all_network_acls = conn.get_all_network_acls()
test_network_acl = next(na for na in all_network_acls if na.id == network_acl.id)
test_network_acl.tags.should.have.length_of(1)
test_network_acl.tags["a key"].should.equal("some value")
@mock_ec2
def test_network_acl_tagging_boto3():
client = boto3.client("ec2", region_name="us-east-1")

View File

@ -1,46 +1,20 @@
import boto.ec2
import boto.ec2.autoscale
import boto.ec2.elb
import boto3
import pytest
import sure # noqa # pylint: disable=unused-import
from botocore.exceptions import ClientError
from moto import mock_ec2_deprecated, mock_autoscaling_deprecated, mock_elb_deprecated
from moto import mock_autoscaling, mock_ec2, mock_elb
from moto.ec2 import ec2_backends
from tests import EXAMPLE_AMI_ID, EXAMPLE_AMI_ID2
from uuid import uuid4
from .test_instances import retrieve_all_instances
def add_servers_to_region(ami_id, count, region):
conn = boto.ec2.connect_to_region(region)
for _ in range(count):
conn.run_instances(ami_id)
def add_servers_to_region_boto3(ami_id, count, region):
ec2 = boto3.resource("ec2", region_name=region)
return ec2.create_instances(ImageId=ami_id, MinCount=count, MaxCount=count)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_add_servers_to_a_single_region():
region = "ap-northeast-1"
add_servers_to_region(EXAMPLE_AMI_ID, 1, region)
add_servers_to_region(EXAMPLE_AMI_ID2, 1, region)
conn = boto.ec2.connect_to_region(region)
reservations = conn.get_all_reservations()
len(reservations).should.equal(2)
image_ids = [r.instances[0].image_id for r in reservations]
image_ids.should.equal([EXAMPLE_AMI_ID, EXAMPLE_AMI_ID2])
@mock_ec2
def test_add_servers_to_a_single_region_boto3():
region = "ap-northeast-1"
@ -56,26 +30,6 @@ def test_add_servers_to_a_single_region_boto3():
instance2["ImageId"].should.equal(EXAMPLE_AMI_ID2)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_add_servers_to_multiple_regions():
region1 = "us-east-1"
region2 = "ap-northeast-1"
add_servers_to_region(EXAMPLE_AMI_ID, 1, region1)
add_servers_to_region(EXAMPLE_AMI_ID2, 1, region2)
us_conn = boto.ec2.connect_to_region(region1)
ap_conn = boto.ec2.connect_to_region(region2)
us_reservations = us_conn.get_all_reservations()
ap_reservations = ap_conn.get_all_reservations()
len(us_reservations).should.equal(1)
len(ap_reservations).should.equal(1)
us_reservations[0].instances[0].image_id.should.equal(EXAMPLE_AMI_ID)
ap_reservations[0].instances[0].image_id.should.equal(EXAMPLE_AMI_ID2)
@mock_ec2
def test_add_servers_to_multiple_regions_boto3():
region1 = "us-east-1"
@ -103,107 +57,6 @@ def test_add_servers_to_multiple_regions_boto3():
ap_instance["ImageId"].should.equal(EXAMPLE_AMI_ID2)
# Has boto3 equivalent
@mock_autoscaling_deprecated
@mock_elb_deprecated
def test_create_autoscaling_group():
elb_conn = boto.ec2.elb.connect_to_region("us-east-1")
elb_conn.create_load_balancer(
"us_test_lb", zones=[], listeners=[(80, 8080, "http")]
)
elb_conn = boto.ec2.elb.connect_to_region("ap-northeast-1")
elb_conn.create_load_balancer(
"ap_test_lb", zones=[], listeners=[(80, 8080, "http")]
)
us_conn = boto.ec2.autoscale.connect_to_region("us-east-1")
config = boto.ec2.autoscale.LaunchConfiguration(
name="us_tester", image_id=EXAMPLE_AMI_ID, instance_type="m1.small"
)
us_conn.create_launch_configuration(config)
us_subnet_id = list(ec2_backends["us-east-1"].subnets["us-east-1c"].keys())[0]
ap_subnet_id = list(
ec2_backends["ap-northeast-1"].subnets["ap-northeast-1a"].keys()
)[0]
group = boto.ec2.autoscale.AutoScalingGroup(
name="us_tester_group",
availability_zones=["us-east-1c"],
default_cooldown=60,
desired_capacity=2,
health_check_period=100,
health_check_type="EC2",
max_size=2,
min_size=2,
launch_config=config,
load_balancers=["us_test_lb"],
placement_group="us_test_placement",
vpc_zone_identifier=us_subnet_id,
termination_policies=["OldestInstance", "NewestInstance"],
)
us_conn.create_auto_scaling_group(group)
ap_conn = boto.ec2.autoscale.connect_to_region("ap-northeast-1")
config = boto.ec2.autoscale.LaunchConfiguration(
name="ap_tester", image_id=EXAMPLE_AMI_ID, instance_type="m1.small"
)
ap_conn.create_launch_configuration(config)
group = boto.ec2.autoscale.AutoScalingGroup(
name="ap_tester_group",
availability_zones=["ap-northeast-1a"],
default_cooldown=60,
desired_capacity=2,
health_check_period=100,
health_check_type="EC2",
max_size=2,
min_size=2,
launch_config=config,
load_balancers=["ap_test_lb"],
placement_group="ap_test_placement",
vpc_zone_identifier=ap_subnet_id,
termination_policies=["OldestInstance", "NewestInstance"],
)
ap_conn.create_auto_scaling_group(group)
len(us_conn.get_all_groups()).should.equal(1)
len(ap_conn.get_all_groups()).should.equal(1)
us_group = us_conn.get_all_groups()[0]
us_group.name.should.equal("us_tester_group")
list(us_group.availability_zones).should.equal(["us-east-1c"])
us_group.desired_capacity.should.equal(2)
us_group.max_size.should.equal(2)
us_group.min_size.should.equal(2)
us_group.vpc_zone_identifier.should.equal(us_subnet_id)
us_group.launch_config_name.should.equal("us_tester")
us_group.default_cooldown.should.equal(60)
us_group.health_check_period.should.equal(100)
us_group.health_check_type.should.equal("EC2")
list(us_group.load_balancers).should.equal(["us_test_lb"])
us_group.placement_group.should.equal("us_test_placement")
list(us_group.termination_policies).should.equal(
["OldestInstance", "NewestInstance"]
)
ap_group = ap_conn.get_all_groups()[0]
ap_group.name.should.equal("ap_tester_group")
list(ap_group.availability_zones).should.equal(["ap-northeast-1a"])
ap_group.desired_capacity.should.equal(2)
ap_group.max_size.should.equal(2)
ap_group.min_size.should.equal(2)
ap_group.vpc_zone_identifier.should.equal(ap_subnet_id)
ap_group.launch_config_name.should.equal("ap_tester")
ap_group.default_cooldown.should.equal(60)
ap_group.health_check_period.should.equal(100)
ap_group.health_check_type.should.equal("EC2")
list(ap_group.load_balancers).should.equal(["ap_test_lb"])
ap_group.placement_group.should.equal("ap_test_placement")
list(ap_group.termination_policies).should.equal(
["OldestInstance", "NewestInstance"]
)
@mock_autoscaling
@mock_elb
@mock_ec2

View File

@ -1,43 +1,14 @@
import pytest
import boto
import boto3
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2, mock_ec2_deprecated, settings
from moto import mock_ec2, settings
from tests import EXAMPLE_AMI_ID
from tests.helpers import requires_boto_gte
from uuid import uuid4
# Has boto3 equivalent
@mock_ec2_deprecated
def test_route_tables_defaults():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
all_route_tables = conn.get_all_route_tables(filters={"vpc-id": vpc.id})
all_route_tables.should.have.length_of(1)
main_route_table = all_route_tables[0]
main_route_table.vpc_id.should.equal(vpc.id)
routes = main_route_table.routes
routes.should.have.length_of(1)
local_route = routes[0]
local_route.gateway_id.should.equal("local")
local_route.state.should.equal("active")
local_route.destination_cidr_block.should.equal(vpc.cidr_block)
vpc.delete()
all_route_tables = conn.get_all_route_tables(filters={"vpc-id": vpc.id})
all_route_tables.should.have.length_of(0)
@mock_ec2
def test_route_tables_defaults_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -68,47 +39,6 @@ def test_route_tables_defaults_boto3():
all_route_tables.should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_route_tables_additional():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
route_table = conn.create_route_table(vpc.id)
all_route_tables = conn.get_all_route_tables(filters={"vpc-id": vpc.id})
all_route_tables.should.have.length_of(2)
all_route_tables[0].vpc_id.should.equal(vpc.id)
all_route_tables[1].vpc_id.should.equal(vpc.id)
all_route_table_ids = [route_table.id for route_table in all_route_tables]
all_route_table_ids.should.contain(route_table.id)
routes = route_table.routes
routes.should.have.length_of(1)
local_route = routes[0]
local_route.gateway_id.should.equal("local")
local_route.state.should.equal("active")
local_route.destination_cidr_block.should.equal(vpc.cidr_block)
with pytest.raises(EC2ResponseError) as cm:
conn.delete_vpc(vpc.id)
cm.value.code.should.equal("DependencyViolation")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
conn.delete_route_table(route_table.id)
all_route_tables = conn.get_all_route_tables(filters={"vpc-id": vpc.id})
all_route_tables.should.have.length_of(1)
with pytest.raises(EC2ResponseError) as cm:
conn.delete_route_table("rtb-1234abcd")
cm.value.code.should.equal("InvalidRouteTableID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_route_tables_additional_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -154,51 +84,6 @@ def test_route_tables_additional_boto3():
ex.value.response["ResponseMetadata"].should.have.key("RequestId")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_route_tables_filters_standard():
conn = boto.connect_vpc("the_key", "the_secret")
vpc1 = conn.create_vpc("10.0.0.0/16")
route_table1 = conn.create_route_table(vpc1.id)
vpc2 = conn.create_vpc("10.0.0.0/16")
route_table2 = conn.create_route_table(vpc2.id)
all_route_tables = conn.get_all_route_tables()
all_route_tables.should.have.length_of(5)
# Filter by main route table
main_route_tables = conn.get_all_route_tables(filters={"association.main": "true"})
main_route_tables.should.have.length_of(3)
main_route_table_ids = [route_table.id for route_table in main_route_tables]
main_route_table_ids.should_not.contain(route_table1.id)
main_route_table_ids.should_not.contain(route_table2.id)
# Filter by VPC
vpc1_route_tables = conn.get_all_route_tables(filters={"vpc-id": vpc1.id})
vpc1_route_tables.should.have.length_of(2)
vpc1_route_table_ids = [route_table.id for route_table in vpc1_route_tables]
vpc1_route_table_ids.should.contain(route_table1.id)
vpc1_route_table_ids.should_not.contain(route_table2.id)
# Filter by VPC and main route table
vpc2_main_route_tables = conn.get_all_route_tables(
filters={"association.main": "true", "vpc-id": vpc2.id}
)
vpc2_main_route_tables.should.have.length_of(1)
vpc2_main_route_table_ids = [
route_table.id for route_table in vpc2_main_route_tables
]
vpc2_main_route_table_ids.should_not.contain(route_table1.id)
vpc2_main_route_table_ids.should_not.contain(route_table2.id)
# Unsupported filter
conn.get_all_route_tables.when.called_with(
filters={"not-implemented-filter": "foobar"}
).should.throw(NotImplementedError)
@mock_ec2
def test_route_tables_filters_standard_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -259,50 +144,6 @@ def test_route_tables_filters_standard_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_route_tables_filters_associations():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet1 = conn.create_subnet(vpc.id, "10.0.0.0/24")
subnet2 = conn.create_subnet(vpc.id, "10.0.1.0/24")
subnet3 = conn.create_subnet(vpc.id, "10.0.2.0/24")
route_table1 = conn.create_route_table(vpc.id)
route_table2 = conn.create_route_table(vpc.id)
association_id1 = conn.associate_route_table(route_table1.id, subnet1.id)
conn.associate_route_table(route_table1.id, subnet2.id)
conn.associate_route_table(route_table2.id, subnet3.id)
all_route_tables = conn.get_all_route_tables()
all_route_tables.should.have.length_of(4)
# Filter by association ID
association1_route_tables = conn.get_all_route_tables(
filters={"association.route-table-association-id": association_id1}
)
association1_route_tables.should.have.length_of(1)
association1_route_tables[0].id.should.equal(route_table1.id)
association1_route_tables[0].associations.should.have.length_of(3)
# Filter by route table ID
route_table2_route_tables = conn.get_all_route_tables(
filters={"association.route-table-id": route_table2.id}
)
route_table2_route_tables.should.have.length_of(1)
route_table2_route_tables[0].id.should.equal(route_table2.id)
route_table2_route_tables[0].associations.should.have.length_of(2)
# Filter by subnet ID
subnet_route_tables = conn.get_all_route_tables(
filters={"association.subnet-id": subnet1.id}
)
subnet_route_tables.should.have.length_of(1)
subnet_route_tables[0].id.should.equal(route_table1.id)
association1_route_tables[0].associations.should.have.length_of(3)
@mock_ec2
def test_route_tables_filters_associations_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -351,73 +192,6 @@ def test_route_tables_filters_associations_boto3():
subnet_route_tables[0]["Associations"].should.have.length_of(3)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_route_table_associations():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
route_table = conn.create_route_table(vpc.id)
all_route_tables = conn.get_all_route_tables()
all_route_tables.should.have.length_of(3)
# Refresh
route_table = conn.get_all_route_tables(route_table.id)[0]
route_table.associations.should.have.length_of(1)
# Associate
association_id = conn.associate_route_table(route_table.id, subnet.id)
# Refresh
route_table = conn.get_all_route_tables(route_table.id)[0]
route_table.associations.should.have.length_of(2)
route_table.associations[1].id.should.equal(association_id)
route_table.associations[1].main.should.equal(False)
route_table.associations[1].route_table_id.should.equal(route_table.id)
route_table.associations[1].subnet_id.should.equal(subnet.id)
# Associate is idempotent
association_id_idempotent = conn.associate_route_table(route_table.id, subnet.id)
association_id_idempotent.should.equal(association_id)
# Error: Attempt delete associated route table.
with pytest.raises(EC2ResponseError) as cm:
conn.delete_route_table(route_table.id)
cm.value.code.should.equal("DependencyViolation")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Disassociate
conn.disassociate_route_table(association_id)
# Refresh
route_table = conn.get_all_route_tables(route_table.id)[0]
route_table.associations.should.have.length_of(1)
# Error: Disassociate with invalid association ID
with pytest.raises(EC2ResponseError) as cm:
conn.disassociate_route_table(association_id)
cm.value.code.should.equal("InvalidAssociationID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Associate with invalid subnet ID
with pytest.raises(EC2ResponseError) as cm:
conn.associate_route_table(route_table.id, "subnet-1234abcd")
cm.value.code.should.equal("InvalidSubnetID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Associate with invalid route table ID
with pytest.raises(EC2ResponseError) as cm:
conn.associate_route_table("rtb-1234abcd", subnet.id)
cm.value.code.should.equal("InvalidRouteTableID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_route_table_associations_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -497,84 +271,6 @@ def test_route_table_associations_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidRouteTableID.NotFound")
# Has boto3 equivalent
@requires_boto_gte("2.16.0")
@mock_ec2_deprecated
def test_route_table_replace_route_table_association():
"""
Note: Boto has deprecated replace_route_table_association (which returns status)
and now uses replace_route_table_association_with_assoc (which returns association ID).
"""
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
route_table1 = conn.create_route_table(vpc.id)
route_table2 = conn.create_route_table(vpc.id)
all_route_tables = conn.get_all_route_tables()
all_route_tables.should.have.length_of(4)
# Refresh
route_table1 = conn.get_all_route_tables(route_table1.id)[0]
route_table1.associations.should.have.length_of(1)
# Associate
association_id1 = conn.associate_route_table(route_table1.id, subnet.id)
# Refresh
route_table1 = conn.get_all_route_tables(route_table1.id)[0]
route_table2 = conn.get_all_route_tables(route_table2.id)[0]
# Validate
route_table1.associations.should.have.length_of(2)
route_table2.associations.should.have.length_of(1)
route_table1.associations[1].id.should.equal(association_id1)
route_table1.associations[1].main.should.equal(False)
route_table1.associations[1].route_table_id.should.equal(route_table1.id)
route_table1.associations[1].subnet_id.should.equal(subnet.id)
# Replace Association
association_id2 = conn.replace_route_table_association_with_assoc(
association_id1, route_table2.id
)
# Refresh
route_table1 = conn.get_all_route_tables(route_table1.id)[0]
route_table2 = conn.get_all_route_tables(route_table2.id)[0]
# Validate
route_table1.associations.should.have.length_of(1)
route_table2.associations.should.have.length_of(2)
route_table2.associations[1].id.should.equal(association_id2)
route_table2.associations[1].main.should.equal(False)
route_table2.associations[1].route_table_id.should.equal(route_table2.id)
route_table2.associations[1].subnet_id.should.equal(subnet.id)
# Replace Association is idempotent
association_id_idempotent = conn.replace_route_table_association_with_assoc(
association_id2, route_table2.id
)
association_id_idempotent.should.equal(association_id2)
# Error: Replace association with invalid association ID
with pytest.raises(EC2ResponseError) as cm:
conn.replace_route_table_association_with_assoc(
"rtbassoc-1234abcd", route_table1.id
)
cm.value.code.should.equal("InvalidAssociationID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Error: Replace association with invalid route table ID
with pytest.raises(EC2ResponseError) as cm:
conn.replace_route_table_association_with_assoc(association_id2, "rtb-1234abcd")
cm.value.code.should.equal("InvalidRouteTableID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_route_table_replace_route_table_association_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -669,25 +365,6 @@ def test_route_table_replace_route_table_association_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidRouteTableID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_route_table_get_by_tag():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
route_table = conn.create_route_table(vpc.id)
route_table.add_tag("Name", "TestRouteTable")
route_tables = conn.get_all_route_tables(filters={"tag:Name": "TestRouteTable"})
route_tables.should.have.length_of(1)
route_tables[0].vpc_id.should.equal(vpc.id)
route_tables[0].id.should.equal(route_table.id)
route_tables[0].tags.should.have.length_of(1)
route_tables[0].tags["Name"].should.equal("TestRouteTable")
@mock_ec2
def test_route_table_get_by_tag_boto3():
ec2 = boto3.resource("ec2", region_name="eu-central-1")
@ -708,57 +385,6 @@ def test_route_table_get_by_tag_boto3():
route_tables[0].tags[0].should.equal({"Key": "Name", "Value": tag_value})
# Has boto3 equivalent
@mock_ec2_deprecated
def test_routes_additional():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
main_route_table = conn.get_all_route_tables(filters={"vpc-id": vpc.id})[0]
igw = conn.create_internet_gateway()
ROUTE_CIDR = "10.0.0.4/24"
conn.create_route(main_route_table.id, ROUTE_CIDR, gateway_id=igw.id)
main_route_table = conn.get_all_route_tables(filters={"vpc-id": vpc.id})[
0
] # Refresh route table
main_route_table.routes.should.have.length_of(2)
new_routes = [
route
for route in main_route_table.routes
if route.destination_cidr_block != vpc.cidr_block
]
new_routes.should.have.length_of(1)
new_route = new_routes[0]
new_route.gateway_id.should.equal(igw.id)
new_route.instance_id.should.be.none
new_route.state.should.equal("active")
new_route.destination_cidr_block.should.equal(ROUTE_CIDR)
conn.delete_route(main_route_table.id, ROUTE_CIDR)
main_route_table = conn.get_all_route_tables(filters={"vpc-id": vpc.id})[
0
] # Refresh route table
main_route_table.routes.should.have.length_of(1)
new_routes = [
route
for route in main_route_table.routes
if route.destination_cidr_block != vpc.cidr_block
]
new_routes.should.have.length_of(0)
with pytest.raises(EC2ResponseError) as cm:
conn.delete_route(main_route_table.id, ROUTE_CIDR)
cm.value.code.should.equal("InvalidRoute.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_routes_additional_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -812,60 +438,6 @@ def test_routes_additional_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidRoute.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_routes_replace():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
main_route_table = conn.get_all_route_tables(
filters={"association.main": "true", "vpc-id": vpc.id}
)[0]
ROUTE_CIDR = "10.0.0.4/24"
# Various route targets
igw = conn.create_internet_gateway()
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
# Create initial route
conn.create_route(main_route_table.id, ROUTE_CIDR, gateway_id=igw.id)
# Replace...
def get_target_route():
route_table = conn.get_all_route_tables(main_route_table.id)[0]
routes = [
route
for route in route_table.routes
if route.destination_cidr_block != vpc.cidr_block
]
routes.should.have.length_of(1)
return routes[0]
conn.replace_route(main_route_table.id, ROUTE_CIDR, instance_id=instance.id)
target_route = get_target_route()
target_route.gateway_id.should.be.none
target_route.instance_id.should.equal(instance.id)
target_route.state.should.equal("active")
target_route.destination_cidr_block.should.equal(ROUTE_CIDR)
conn.replace_route(main_route_table.id, ROUTE_CIDR, gateway_id=igw.id)
target_route = get_target_route()
target_route.gateway_id.should.equal(igw.id)
target_route.instance_id.should.be.none
target_route.state.should.equal("active")
target_route.destination_cidr_block.should.equal(ROUTE_CIDR)
with pytest.raises(EC2ResponseError) as cm:
conn.replace_route("rtb-1234abcd", ROUTE_CIDR, gateway_id=igw.id)
cm.value.code.should.equal("InvalidRouteTableID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_routes_replace_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -937,30 +509,6 @@ def test_routes_replace_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidRouteTableID.NotFound")
# Has boto3 equivalent
@requires_boto_gte("2.19.0")
@mock_ec2_deprecated
def test_routes_not_supported():
conn = boto.connect_vpc("the_key", "the_secret")
conn.create_vpc("10.0.0.0/16")
main_route_table = conn.get_all_route_tables()[0]
conn.create_internet_gateway()
ROUTE_CIDR = "10.0.0.4/24"
# Create
conn.create_route.when.called_with(
main_route_table.id, ROUTE_CIDR, interface_id="eni-1234abcd"
).should.throw("InvalidNetworkInterfaceID.NotFound")
# Replace
igw = conn.create_internet_gateway()
conn.create_route(main_route_table.id, ROUTE_CIDR, gateway_id=igw.id)
conn.replace_route.when.called_with(
main_route_table.id, ROUTE_CIDR, interface_id="eni-1234abcd"
).should.throw(NotImplementedError)
@mock_ec2
def test_routes_not_supported_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -1002,42 +550,6 @@ def test_routes_not_supported_boto3():
client.replace_route.when.called_with(**args).should.throw(NotImplementedError)
# Has boto3 equivalent
@requires_boto_gte("2.34.0")
@mock_ec2_deprecated
def test_routes_vpc_peering_connection():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
main_route_table = conn.get_all_route_tables(
filters={"association.main": "true", "vpc-id": vpc.id}
)[0]
ROUTE_CIDR = "10.0.0.4/24"
peer_vpc = conn.create_vpc("11.0.0.0/16")
vpc_pcx = conn.create_vpc_peering_connection(vpc.id, peer_vpc.id)
conn.create_route(
main_route_table.id, ROUTE_CIDR, vpc_peering_connection_id=vpc_pcx.id
)
# Refresh route table
main_route_table = conn.get_all_route_tables(main_route_table.id)[0]
new_routes = [
route
for route in main_route_table.routes
if route.destination_cidr_block != vpc.cidr_block
]
new_routes.should.have.length_of(1)
new_route = new_routes[0]
new_route.gateway_id.should.be.none
new_route.instance_id.should.be.none
new_route.vpc_peering_connection_id.should.equal(vpc_pcx.id)
new_route.state.should.equal("active")
new_route.destination_cidr_block.should.equal(ROUTE_CIDR)
@mock_ec2
def test_routes_vpc_peering_connection_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -1076,36 +588,6 @@ def test_routes_vpc_peering_connection_boto3():
new_route.destination_cidr_block.should.equal(ROUTE_CIDR)
# Has boto3 equivalent
@requires_boto_gte("2.34.0")
@mock_ec2_deprecated
def test_routes_vpn_gateway():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
main_route_table = conn.get_all_route_tables(
filters={"association.main": "true", "vpc-id": vpc.id}
)[0]
ROUTE_CIDR = "10.0.0.4/24"
vpn_gw = conn.create_vpn_gateway(type="ipsec.1")
conn.create_route(main_route_table.id, ROUTE_CIDR, gateway_id=vpn_gw.id)
main_route_table = conn.get_all_route_tables(main_route_table.id)[0]
new_routes = [
route
for route in main_route_table.routes
if route.destination_cidr_block != vpc.cidr_block
]
new_routes.should.have.length_of(1)
new_route = new_routes[0]
new_route.gateway_id.should.equal(vpn_gw.id)
new_route.instance_id.should.be.none
new_route.vpc_peering_connection_id.should.be.none
@mock_ec2
def test_routes_vpn_gateway_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -1139,26 +621,6 @@ def test_routes_vpn_gateway_boto3():
new_route.vpc_peering_connection_id.should.be.none
# Has boto3 equivalent
@mock_ec2_deprecated
def test_network_acl_tagging():
conn = boto.connect_vpc("the_key", "the secret")
vpc = conn.create_vpc("10.0.0.0/16")
route_table = conn.create_route_table(vpc.id)
route_table.add_tag("a key", "some value")
tag = conn.get_all_tags()[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
all_route_tables = conn.get_all_route_tables()
test_route_table = next(na for na in all_route_tables if na.id == route_table.id)
test_route_table.tags.should.have.length_of(1)
test_route_table.tags["a key"].should.equal("some value")
@mock_ec2
def test_network_acl_tagging_boto3():
client = boto3.client("ec2", region_name="us-east-1")

View File

@ -5,57 +5,16 @@ import unittest
import pytest
import boto3
import boto
import boto.ec2
from botocore.exceptions import ClientError
from boto.exception import EC2ResponseError
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2, mock_ec2_deprecated, settings
from moto import mock_ec2, settings
from moto.ec2 import ec2_backend
from random import randint
from uuid import uuid4
from unittest import SkipTest
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_and_describe_security_group():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as ex:
security_group = conn.create_security_group(
"test security group", "this is a test security group", dry_run=True
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateSecurityGroup operation: Request would have succeeded, but DryRun flag is set"
)
security_group = conn.create_security_group(
"test security group", "this is a test security group"
)
security_group.name.should.equal("test security group")
security_group.description.should.equal("this is a test security group")
# Trying to create another group with the same name should throw an error
with pytest.raises(EC2ResponseError) as cm:
conn.create_security_group(
"test security group", "this is a test security group"
)
cm.value.code.should.equal("InvalidGroup.Duplicate")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
all_groups = conn.get_all_security_groups()
# The default group gets created automatically
all_groups.should.have.length_of(2)
group_names = [group.name for group in all_groups]
set(group_names).should.equal(set(["default", "test security group"]))
@mock_ec2
def test_create_and_describe_security_group_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -90,18 +49,6 @@ def test_create_and_describe_security_group_boto3():
group_names.should.contain(sec_name)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_security_group_without_description_raises_error():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.create_security_group("test security group", "")
cm.value.code.should.equal("MissingParameter")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_create_security_group_without_description_raises_error_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -113,15 +60,6 @@ def test_create_security_group_without_description_raises_error_boto3():
ex.value.response["Error"]["Code"].should.equal("MissingParameter")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_default_security_group():
conn = boto.ec2.connect_to_region("us-east-1")
groups = conn.get_all_security_groups()
groups.should.have.length_of(1)
groups[0].name.should.equal("default")
@mock_ec2
def test_default_security_group_boto3():
client = boto3.client("ec2", "us-west-1")
@ -129,38 +67,6 @@ def test_default_security_group_boto3():
[g["GroupName"] for g in groups].should.contain("default")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_and_describe_vpc_security_group():
conn = boto.connect_ec2("the_key", "the_secret")
vpc_id = "vpc-5300000c"
security_group = conn.create_security_group(
"test security group", "this is a test security group", vpc_id=vpc_id
)
security_group.vpc_id.should.equal(vpc_id)
security_group.name.should.equal("test security group")
security_group.description.should.equal("this is a test security group")
# Trying to create another group with the same name in the same VPC should
# throw an error
with pytest.raises(EC2ResponseError) as cm:
conn.create_security_group(
"test security group", "this is a test security group", vpc_id
)
cm.value.code.should.equal("InvalidGroup.Duplicate")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
all_groups = conn.get_all_security_groups(filters={"vpc-id": [vpc_id]})
all_groups[0].vpc_id.should.equal(vpc_id)
all_groups.should.have.length_of(1)
all_groups[0].name.should.equal("test security group")
@mock_ec2
def test_create_and_describe_vpc_security_group_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -203,28 +109,6 @@ def test_create_and_describe_vpc_security_group_boto3():
all_groups[0]["GroupName"].should.equal(name)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_two_security_groups_with_same_name_in_different_vpc():
conn = boto.connect_ec2("the_key", "the_secret")
vpc_id = "vpc-5300000c"
vpc_id2 = "vpc-5300000d"
conn.create_security_group(
"test security group", "this is a test security group", vpc_id
)
conn.create_security_group(
"test security group", "this is a test security group", vpc_id2
)
all_groups = conn.get_all_security_groups()
all_groups.should.have.length_of(3)
group_names = [group.name for group in all_groups]
# The default group is created automatically
set(group_names).should.equal(set(["default", "test security group"]))
@mock_ec2
def test_create_two_security_groups_with_same_name_in_different_vpc_boto3():
ec2 = boto3.resource("ec2", "us-east-1")
@ -259,39 +143,6 @@ def test_create_two_security_groups_in_vpc_with_ipv6_enabled():
security_group.ip_permissions_egress.should.have.length_of(2)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_deleting_security_groups():
conn = boto.connect_ec2("the_key", "the_secret")
security_group1 = conn.create_security_group("test1", "test1")
conn.create_security_group("test2", "test2")
conn.get_all_security_groups().should.have.length_of(3)
# Deleting a group that doesn't exist should throw an error
with pytest.raises(EC2ResponseError) as cm:
conn.delete_security_group("foobar")
cm.value.code.should.equal("InvalidGroup.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Delete by name
with pytest.raises(EC2ResponseError) as ex:
conn.delete_security_group("test2", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DeleteSecurityGroup operation: Request would have succeeded, but DryRun flag is set"
)
conn.delete_security_group("test2")
conn.get_all_security_groups().should.have.length_of(2)
# Delete by group id
conn.delete_security_group(group_id=security_group1.id)
conn.get_all_security_groups().should.have.length_of(1)
@mock_ec2
def test_deleting_security_groups_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -334,17 +185,6 @@ def test_deleting_security_groups_boto3():
[g["GroupId"] for g in all_groups].shouldnt.contain(group1.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_security_group_in_vpc():
conn = boto.connect_ec2("the_key", "the_secret")
vpc_id = "vpc-12345"
security_group1 = conn.create_security_group("test1", "test1", vpc_id)
# this should not throw an exception
conn.delete_security_group(group_id=security_group1.id)
@mock_ec2
def test_delete_security_group_in_vpc_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -364,144 +204,6 @@ def test_delete_security_group_in_vpc_boto3():
[g["GroupId"] for g in all_groups].shouldnt.contain(group.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_authorize_ip_range_and_revoke():
conn = boto.connect_ec2("the_key", "the_secret")
security_group = conn.create_security_group("test", "test")
with pytest.raises(EC2ResponseError) as ex:
success = security_group.authorize(
ip_protocol="tcp",
from_port="22",
to_port="2222",
cidr_ip="123.123.123.123/32",
dry_run=True,
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the GrantSecurityGroupIngress operation: Request would have succeeded, but DryRun flag is set"
)
success = security_group.authorize(
ip_protocol="tcp", from_port="22", to_port="2222", cidr_ip="123.123.123.123/32"
)
assert success.should.be.true
security_group = conn.get_all_security_groups(groupnames=["test"])[0]
int(security_group.rules[0].to_port).should.equal(2222)
security_group.rules[0].grants[0].cidr_ip.should.equal("123.123.123.123/32")
# Wrong Cidr should throw error
with pytest.raises(EC2ResponseError) as cm:
security_group.revoke(
ip_protocol="tcp",
from_port="22",
to_port="2222",
cidr_ip="123.123.123.122/32",
)
cm.value.code.should.equal("InvalidPermission.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Actually revoke
with pytest.raises(EC2ResponseError) as ex:
security_group.revoke(
ip_protocol="tcp",
from_port="22",
to_port="2222",
cidr_ip="123.123.123.123/32",
dry_run=True,
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the RevokeSecurityGroupIngress operation: Request would have succeeded, but DryRun flag is set"
)
security_group.revoke(
ip_protocol="tcp", from_port="22", to_port="2222", cidr_ip="123.123.123.123/32"
)
security_group = conn.get_all_security_groups()[0]
security_group.rules.should.have.length_of(0)
# Test for egress as well
vpc_conn = boto.connect_vpc()
vpc = vpc_conn.create_vpc("10.0.0.0/16")
egress_security_group = conn.create_security_group(
"testegress", "testegress", vpc_id=vpc.id
)
with pytest.raises(EC2ResponseError) as ex:
success = conn.authorize_security_group_egress(
egress_security_group.id,
"tcp",
from_port="22",
to_port="2222",
cidr_ip="123.123.123.123/32",
dry_run=True,
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the GrantSecurityGroupEgress operation: Request would have succeeded, but DryRun flag is set"
)
success = conn.authorize_security_group_egress(
egress_security_group.id,
"tcp",
from_port="22",
to_port="2222",
cidr_ip="123.123.123.123/32",
)
assert success.should.be.true
egress_security_group = conn.get_all_security_groups(groupnames="testegress")[0]
# There are two egress rules associated with the security group:
# the default outbound rule and the new one
int(egress_security_group.rules_egress[1].to_port).should.equal(2222)
actual_cidr = egress_security_group.rules_egress[1].grants[0].cidr_ip
actual_cidr.should.equal("123.123.123.123/32")
# Wrong Cidr should throw error
egress_security_group.revoke.when.called_with(
ip_protocol="tcp", from_port="22", to_port="2222", cidr_ip="123.123.123.122/32"
).should.throw(EC2ResponseError)
# Actually revoke
with pytest.raises(EC2ResponseError) as ex:
conn.revoke_security_group_egress(
egress_security_group.id,
"tcp",
from_port="22",
to_port="2222",
cidr_ip="123.123.123.123/32",
dry_run=True,
)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the RevokeSecurityGroupEgress operation: Request would have succeeded, but DryRun flag is set"
)
conn.revoke_security_group_egress(
egress_security_group.id,
"tcp",
from_port="22",
to_port="2222",
cidr_ip="123.123.123.123/32",
)
egress_security_group = [
group
for group in conn.get_all_security_groups()
if group.id == egress_security_group.id
][0]
# There is still the default outbound rule
egress_security_group.rules_egress.should.have.length_of(1)
@mock_ec2
def test_authorize_ip_range_and_revoke_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -623,51 +325,6 @@ def test_authorize_ip_range_and_revoke_boto3():
egress_security_group["IpPermissionsEgress"].should.have.length_of(1)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_authorize_other_group_and_revoke():
conn = boto.connect_ec2("the_key", "the_secret")
security_group = conn.create_security_group("test", "test")
other_security_group = conn.create_security_group("other", "other")
wrong_group = conn.create_security_group("wrong", "wrong")
success = security_group.authorize(
ip_protocol="tcp",
from_port="22",
to_port="2222",
src_group=other_security_group,
)
assert success.should.be.true
security_group = [
group for group in conn.get_all_security_groups() if group.name == "test"
][0]
int(security_group.rules[0].to_port).should.equal(2222)
security_group.rules[0].grants[0].group_id.should.equal(other_security_group.id)
# Wrong source group should throw error
with pytest.raises(EC2ResponseError) as cm:
security_group.revoke(
ip_protocol="tcp", from_port="22", to_port="2222", src_group=wrong_group
)
cm.value.code.should.equal("InvalidPermission.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Actually revoke
security_group.revoke(
ip_protocol="tcp",
from_port="22",
to_port="2222",
src_group=other_security_group,
)
security_group = [
group for group in conn.get_all_security_groups() if group.name == "test"
][0]
security_group.rules.should.have.length_of(0)
@mock_ec2
def test_authorize_other_group_and_revoke_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -759,47 +416,6 @@ def test_authorize_other_group_egress_and_revoke():
sg01.ip_permissions_egress.should.have.length_of(1)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_authorize_group_in_vpc():
conn = boto.connect_ec2("the_key", "the_secret")
vpc_id = "vpc-12345"
# create 2 groups in a vpc
security_group = conn.create_security_group("test1", "test1", vpc_id)
other_security_group = conn.create_security_group("test2", "test2", vpc_id)
success = security_group.authorize(
ip_protocol="tcp",
from_port="22",
to_port="2222",
src_group=other_security_group,
)
success.should.be.true
# Check that the rule is accurate
security_group = [
group for group in conn.get_all_security_groups() if group.name == "test1"
][0]
int(security_group.rules[0].to_port).should.equal(2222)
security_group.rules[0].grants[0].group_id.should.equal(other_security_group.id)
# Now remove the rule
success = security_group.revoke(
ip_protocol="tcp",
from_port="22",
to_port="2222",
src_group=other_security_group,
)
success.should.be.true
# And check that it gets revoked
security_group = [
group for group in conn.get_all_security_groups() if group.name == "test1"
][0]
security_group.rules.should.have.length_of(0)
@mock_ec2
def test_authorize_group_in_vpc_boto3():
ec2 = boto3.resource("ec2", "ap-south-1")
@ -851,44 +467,6 @@ def test_authorize_group_in_vpc_boto3():
found_sec_group["IpPermissions"].should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_security_groups():
conn = boto.connect_ec2()
sg1 = conn.create_security_group(
name="test1", description="test1", vpc_id="vpc-mjm05d27"
)
conn.create_security_group(name="test2", description="test2")
resp = conn.get_all_security_groups(groupnames=["test1"])
resp.should.have.length_of(1)
resp[0].id.should.equal(sg1.id)
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_security_groups(groupnames=["does_not_exist"])
cm.value.code.should.equal("InvalidGroup.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
resp.should.have.length_of(1)
resp[0].id.should.equal(sg1.id)
resp = conn.get_all_security_groups(filters={"vpc-id": ["vpc-mjm05d27"]})
resp.should.have.length_of(1)
resp[0].id.should.equal(sg1.id)
resp = conn.get_all_security_groups(filters={"vpc-id": ["vpc-mjm05d27"]})
resp.should.have.length_of(1)
resp[0].id.should.equal(sg1.id)
resp = conn.get_all_security_groups(filters={"description": ["test1"]})
resp.should.have.length_of(1)
resp[0].id.should.equal(sg1.id)
resp = conn.get_all_security_groups()
resp.should.have.length_of(3)
@mock_ec2
def test_describe_security_groups():
ec2 = boto3.resource("ec2", "us-west-1")
@ -927,20 +505,6 @@ def test_describe_security_groups():
sg_ids.should.contain(sg2.id)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_authorize_bad_cidr_throws_invalid_parameter_value():
conn = boto.connect_ec2("the_key", "the_secret")
security_group = conn.create_security_group("test", "test")
with pytest.raises(EC2ResponseError) as cm:
security_group.authorize(
ip_protocol="tcp", from_port="22", to_port="2222", cidr_ip="123.123.123.123"
)
cm.value.code.should.equal("InvalidParameterValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_authorize_bad_cidr_throws_invalid_parameter_value_boto3():
ec2 = boto3.resource("ec2", "us-west-1")
@ -960,44 +524,6 @@ def test_authorize_bad_cidr_throws_invalid_parameter_value_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidParameterValue")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_security_group_tagging():
conn = boto.connect_vpc()
vpc = conn.create_vpc("10.0.0.0/16")
sg = conn.create_security_group("test-sg", "Test SG", vpc.id)
with pytest.raises(EC2ResponseError) as ex:
sg.add_tag("Test", "Tag", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateTags operation: Request would have succeeded, but DryRun flag is set"
)
sg.add_tag("Test", "Tag")
tag = conn.get_all_tags()[0]
tag.name.should.equal("Test")
tag.value.should.equal("Tag")
group = conn.get_all_security_groups("test-sg")[0]
group.tags.should.have.length_of(1)
group.tags["Test"].should.equal("Tag")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_security_group_tag_filtering():
conn = boto.connect_ec2()
sg = conn.create_security_group("test-sg", "Test SG")
sg.add_tag("test-tag", "test-value")
groups = conn.get_all_security_groups(filters={"tag:test-tag": "test-value"})
groups.should.have.length_of(1)
@mock_ec2
def test_security_group_tag_filtering_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -1018,20 +544,6 @@ def test_security_group_tag_filtering_boto3():
groups.should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_authorize_all_protocols_with_no_port_specification():
conn = boto.connect_ec2()
sg = conn.create_security_group("test", "test")
success = sg.authorize(ip_protocol="-1", cidr_ip="0.0.0.0/0")
success.should.be.true
sg = conn.get_all_security_groups("test")[0]
sg.rules[0].from_port.should.equal(None)
sg.rules[0].to_port.should.equal(None)
@mock_ec2
def test_authorize_all_protocols_with_no_port_specification_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -1050,72 +562,6 @@ def test_authorize_all_protocols_with_no_port_specification_boto3():
permission.shouldnt.have.key("ToPort")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_sec_group_rule_limit():
ec2_conn = boto.connect_ec2()
sg = ec2_conn.create_security_group("test", "test")
other_sg = ec2_conn.create_security_group("test_2", "test_other")
# INGRESS
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group(
group_id=sg.id,
ip_protocol="-1",
cidr_ip=["{0}.0.0.0/0".format(i) for i in range(110)],
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
sg.rules.should.be.empty
# authorize a rule targeting a different sec group (because this count too)
success = ec2_conn.authorize_security_group(
group_id=sg.id, ip_protocol="-1", src_security_group_group_id=other_sg.id
)
success.should.be.true
# fill the rules up the limit
success = ec2_conn.authorize_security_group(
group_id=sg.id,
ip_protocol="-1",
cidr_ip=["{0}.0.0.0/0".format(i) for i in range(1, 60)],
)
success.should.be.true
# verify that we cannot authorize past the limit for a CIDR IP
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group(
group_id=sg.id, ip_protocol="-1", cidr_ip=["100.0.0.0/0"]
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
# verify that we cannot authorize past the limit for a different sec group
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group(
group_id=sg.id, ip_protocol="-1", src_security_group_group_id=other_sg.id
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
# EGRESS
# authorize a rule targeting a different sec group (because this count too)
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", src_group_id=other_sg.id
)
# fill the rules up the limit, 59 + 1 default rule
for i in range(1, 59):
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", cidr_ip="{0}.0.0.0/0".format(i)
)
# verify that we cannot authorize past the limit for a CIDR IP
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", cidr_ip="101.0.0.0/0"
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
# verify that we cannot authorize past the limit for a different sec group
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", src_group_id=other_sg.id
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
@mock_ec2
@pytest.mark.parametrize(
"use_vpc", [True, False], ids=["Use VPC", "Without VPC"],
@ -1232,83 +678,6 @@ def test_sec_group_rule_limit_boto3(use_vpc):
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_sec_group_rule_limit_vpc():
ec2_conn = boto.connect_ec2()
vpc_conn = boto.connect_vpc()
vpc = vpc_conn.create_vpc("10.0.0.0/16")
sg = ec2_conn.create_security_group("test", "test", vpc_id=vpc.id)
other_sg = ec2_conn.create_security_group("test_2", "test", vpc_id=vpc.id)
# INGRESS
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group(
group_id=sg.id,
ip_protocol="-1",
cidr_ip=["{0}.0.0.0/0".format(i) for i in range(110)],
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
sg.rules.should.be.empty
# authorize a rule targeting a different sec group (because this count too)
success = ec2_conn.authorize_security_group(
group_id=sg.id, ip_protocol="-1", src_security_group_group_id=other_sg.id
)
success.should.be.true
# fill the rules up the limit
success = ec2_conn.authorize_security_group(
group_id=sg.id,
ip_protocol="-1",
cidr_ip=["{0}.0.0.0/0".format(i) for i in range(59)],
)
# verify that we cannot authorize past the limit for a CIDR IP
success.should.be.true
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group(
group_id=sg.id, ip_protocol="-1", cidr_ip=["100.0.0.0/0"]
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
# verify that we cannot authorize past the limit for a different sec group
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group(
group_id=sg.id, ip_protocol="-1", src_security_group_group_id=other_sg.id
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
# EGRESS
# authorize a rule targeting a different sec group (because this count too)
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", src_group_id=other_sg.id
)
# fill the rules up the limit
# remember that by default, when created a sec group contains 1 egress rule
# so our other_sg rule + 48 CIDR IP rules + 1 by default == 50 the limit
for i in range(1, 59):
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", cidr_ip="{0}.0.0.0/0".format(i)
)
# verify that we cannot authorize past the limit for a CIDR IP
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", cidr_ip="50.0.0.0/0"
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
# verify that we cannot authorize past the limit for a different sec group
with pytest.raises(EC2ResponseError) as cm:
ec2_conn.authorize_security_group_egress(
group_id=sg.id, ip_protocol="-1", src_group_id=other_sg.id
)
cm.value.error_code.should.equal("RulesPerSecurityGroupLimitExceeded")
"""
Boto3
"""
@mock_ec2
def test_add_same_rule_twice_throws_error():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -1669,29 +1038,6 @@ def test_security_group_ingress_without_multirule_after_reload():
assert len(sg_after.ip_permissions) == 1
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_security_groups_filter_with_same_vpc_id():
conn = boto.connect_ec2("the_key", "the_secret")
vpc_id = "vpc-5300000c"
security_group = conn.create_security_group("test1", "test1", vpc_id=vpc_id)
security_group2 = conn.create_security_group("test2", "test2", vpc_id=vpc_id)
security_group.vpc_id.should.equal(vpc_id)
security_group2.vpc_id.should.equal(vpc_id)
security_groups = conn.get_all_security_groups(
group_ids=[security_group.id], filters={"vpc-id": [vpc_id]}
)
security_groups.should.have.length_of(1)
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_security_groups(group_ids=["does_not_exist"])
cm.value.code.should.equal("InvalidGroup.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_get_all_security_groups_filter_with_same_vpc_id_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")

View File

@ -1,15 +1,12 @@
import pytest
import datetime
import boto
import boto.ec2
import boto3
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
import pytz
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2, mock_ec2_deprecated, settings
from moto import mock_ec2, settings
from moto.ec2.models import ec2_backends
from moto.core.utils import iso_8601_datetime_with_milliseconds
from tests import EXAMPLE_AMI_ID
@ -155,30 +152,6 @@ def test_request_spot_instances_default_arguments():
request.shouldnt.contain("SubnetId")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_cancel_spot_instance_request():
conn = boto.connect_ec2()
conn.request_spot_instances(price=0.5, image_id=EXAMPLE_AMI_ID)
requests = conn.get_all_spot_instance_requests()
requests.should.have.length_of(1)
with pytest.raises(EC2ResponseError) as ex:
conn.cancel_spot_instance_requests([requests[0].id], dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CancelSpotInstance operation: Request would have succeeded, but DryRun flag is set"
)
conn.cancel_spot_instance_requests([requests[0].id])
requests = conn.get_all_spot_instance_requests()
requests.should.have.length_of(0)
@mock_ec2
def test_cancel_spot_instance_request_boto3():
client = boto3.client("ec2", region_name="us-west-1")
@ -219,32 +192,6 @@ def test_cancel_spot_instance_request_boto3():
requests.should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_request_spot_instances_fulfilled():
"""
Test that moto correctly fullfills a spot instance request
"""
conn = boto.ec2.connect_to_region("us-east-1")
request = conn.request_spot_instances(price=0.5, image_id=EXAMPLE_AMI_ID)
requests = conn.get_all_spot_instance_requests()
requests.should.have.length_of(1)
request = requests[0]
request.state.should.equal("open")
if not settings.TEST_SERVER_MODE:
ec2_backends["us-east-1"].spot_instance_requests[request.id].state = "active"
requests = conn.get_all_spot_instance_requests()
requests.should.have.length_of(1)
request = requests[0]
request.state.should.equal("active")
@mock_ec2
def test_request_spot_instances_fulfilled_boto3():
"""
@ -277,26 +224,6 @@ def test_request_spot_instances_fulfilled_boto3():
request["State"].should.equal("active")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_tag_spot_instance_request():
"""
Test that moto correctly tags a spot instance request
"""
conn = boto.connect_ec2()
request = conn.request_spot_instances(price=0.5, image_id=EXAMPLE_AMI_ID)
request[0].add_tag("tag1", "value1")
request[0].add_tag("tag2", "value2")
requests = conn.get_all_spot_instance_requests()
requests.should.have.length_of(1)
request = requests[0]
tag_dict = dict(request.tags)
tag_dict.should.equal({"tag1": "value1", "tag2": "value2"})
@mock_ec2
def test_tag_spot_instance_request_boto3():
"""
@ -324,37 +251,6 @@ def test_tag_spot_instance_request_boto3():
request["Tags"].should.contain({"Key": "tag2", "Value": "value2"})
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_spot_instance_requests_filtering():
"""
Test that moto correctly filters spot instance requests
"""
conn = boto.connect_ec2()
request1 = conn.request_spot_instances(price=0.5, image_id=EXAMPLE_AMI_ID)
request2 = conn.request_spot_instances(price=0.5, image_id=EXAMPLE_AMI_ID)
conn.request_spot_instances(price=0.5, image_id=EXAMPLE_AMI_ID)
request1[0].add_tag("tag1", "value1")
request1[0].add_tag("tag2", "value2")
request2[0].add_tag("tag1", "value1")
request2[0].add_tag("tag2", "wrong")
requests = conn.get_all_spot_instance_requests(filters={"state": "active"})
requests.should.have.length_of(0)
requests = conn.get_all_spot_instance_requests(filters={"state": "open"})
requests.should.have.length_of(3)
requests = conn.get_all_spot_instance_requests(filters={"tag:tag1": "value1"})
requests.should.have.length_of(2)
requests = conn.get_all_spot_instance_requests(
filters={"tag:tag1": "value1", "tag:tag2": "value2"}
)
requests.should.have.length_of(1)
@mock_ec2
def test_get_all_spot_instance_requests_filtering_boto3():
"""
@ -411,22 +307,6 @@ def test_get_all_spot_instance_requests_filtering_boto3():
requests.should.have.length_of(1)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_request_spot_instances_setting_instance_id():
conn = boto.ec2.connect_to_region("us-east-1")
request = conn.request_spot_instances(price=0.5, image_id=EXAMPLE_AMI_ID)
if not settings.TEST_SERVER_MODE:
req = ec2_backends["us-east-1"].spot_instance_requests[request[0].id]
req.state = "active"
req.instance_id = "i-12345678"
request = conn.get_all_spot_instance_requests()[0]
assert request.state == "active"
assert request.instance_id == "i-12345678"
@mock_ec2
def test_request_spot_instances_instance_lifecycle():
if settings.TEST_SERVER_MODE:

View File

@ -1,42 +1,16 @@
import random
import boto
import boto3
import boto.vpc
import pytest
import sure # noqa # pylint: disable=unused-import
from boto.exception import EC2ResponseError
from botocore.exceptions import ClientError
from moto import mock_ec2, mock_ec2_deprecated, settings
from moto import mock_ec2, settings
from tests import EXAMPLE_AMI_ID
from uuid import uuid4
from unittest import SkipTest
# Has boto3 equivalent
@mock_ec2_deprecated
def test_subnets():
ec2 = boto.connect_ec2("the_key", "the_secret")
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
all_subnets = conn.get_all_subnets()
all_subnets.should.have.length_of(1 + len(ec2.get_all_zones()))
conn.delete_subnet(subnet.id)
all_subnets = conn.get_all_subnets()
all_subnets.should.have.length_of(0 + len(ec2.get_all_zones()))
with pytest.raises(EC2ResponseError) as cm:
conn.delete_subnet(subnet.id)
cm.value.code.should.equal("InvalidSubnetID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_subnets_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -61,18 +35,6 @@ def test_subnets_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidSubnetID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_subnet_create_vpc_validation():
conn = boto.connect_vpc("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.create_subnet("vpc-abcd1234", "10.0.0.0/18")
cm.value.code.should.equal("InvalidVpcID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_subnet_create_vpc_validation_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -84,25 +46,6 @@ def test_subnet_create_vpc_validation_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidVpcID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_subnet_tagging():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
subnet = conn.create_subnet(vpc.id, "10.0.0.0/18")
subnet.add_tag("a key", "some value")
tag = conn.get_all_tags()[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
# Refresh the subnet
subnet = conn.get_all_subnets(subnet_ids=[subnet.id])[0]
subnet.tags.should.have.length_of(1)
subnet.tags["a key"].should.equal("some value")
@mock_ec2
def test_subnet_tagging_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -123,15 +66,6 @@ def test_subnet_tagging_boto3():
subnet["Tags"].should.equal([{"Key": "a key", "Value": "some value"}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_subnet_should_have_proper_availability_zone_set():
conn = boto.vpc.connect_to_region("us-west-1")
vpcA = conn.create_vpc("10.0.0.0/16")
subnetA = conn.create_subnet(vpcA.id, "10.0.0.0/24", availability_zone="us-west-1b")
subnetA.availability_zone.should.equal("us-west-1b")
@mock_ec2
def test_subnet_should_have_proper_availability_zone_set_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -172,20 +106,6 @@ def test_default_subnet():
subnet.map_public_ip_on_launch.shouldnt.be.ok
# Has boto3 equivalent
@mock_ec2_deprecated
def test_non_default_subnet():
vpc_cli = boto.vpc.connect_to_region("us-west-1")
# Create the non default VPC
vpc = vpc_cli.create_vpc("10.0.0.0/16")
vpc.is_default.shouldnt.be.ok
subnet = vpc_cli.create_subnet(vpc.id, "10.0.0.0/24")
subnet = vpc_cli.get_all_subnets(subnet_ids=[subnet.id])[0]
subnet.mapPublicIpOnLaunch.should.equal("false")
@mock_ec2
def test_boto3_non_default_subnet():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -279,31 +199,6 @@ def test_modify_subnet_attribute_validation():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_subnet_get_by_id():
conn = boto.vpc.connect_to_region("us-west-1")
vpcA = conn.create_vpc("10.0.0.0/16")
subnetA = conn.create_subnet(vpcA.id, "10.0.0.0/24", availability_zone="us-west-1a")
vpcB = conn.create_vpc("10.0.0.0/16")
subnetB1 = conn.create_subnet(
vpcB.id, "10.0.0.0/24", availability_zone="us-west-1a"
)
conn.create_subnet(vpcB.id, "10.0.1.0/24", availability_zone="us-west-1b")
subnets_by_id = conn.get_all_subnets(subnet_ids=[subnetA.id, subnetB1.id])
subnets_by_id.should.have.length_of(2)
subnets_by_id = tuple(map(lambda s: s.id, subnets_by_id))
subnetA.id.should.be.within(subnets_by_id)
subnetB1.id.should.be.within(subnets_by_id)
with pytest.raises(EC2ResponseError) as cm:
conn.get_all_subnets(subnet_ids=["subnet-does_not_exist"])
cm.value.code.should.equal("InvalidSubnetID.NotFound")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_subnet_get_by_id_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -335,82 +230,6 @@ def test_subnet_get_by_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidSubnetID.NotFound")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_subnets_filtering():
ec2 = boto.ec2.connect_to_region("us-west-1")
conn = boto.vpc.connect_to_region("us-west-1")
vpcA = conn.create_vpc("10.0.0.0/16")
subnetA = conn.create_subnet(vpcA.id, "10.0.0.0/24", availability_zone="us-west-1a")
vpcB = conn.create_vpc("10.0.0.0/16")
subnetB1 = conn.create_subnet(
vpcB.id, "10.0.0.0/24", availability_zone="us-west-1a"
)
subnetB2 = conn.create_subnet(
vpcB.id, "10.0.1.0/24", availability_zone="us-west-1b"
)
all_subnets = conn.get_all_subnets()
all_subnets.should.have.length_of(3 + len(ec2.get_all_zones()))
# Filter by VPC ID
subnets_by_vpc = conn.get_all_subnets(filters={"vpc-id": vpcB.id})
subnets_by_vpc.should.have.length_of(2)
set([subnet.id for subnet in subnets_by_vpc]).should.equal(
set([subnetB1.id, subnetB2.id])
)
# Filter by CIDR variations
subnets_by_cidr1 = conn.get_all_subnets(filters={"cidr": "10.0.0.0/24"})
subnets_by_cidr1.should.have.length_of(2)
set([subnet.id for subnet in subnets_by_cidr1]).should.equal(
set([subnetA.id, subnetB1.id])
)
subnets_by_cidr2 = conn.get_all_subnets(filters={"cidr-block": "10.0.0.0/24"})
subnets_by_cidr2.should.have.length_of(2)
set([subnet.id for subnet in subnets_by_cidr2]).should.equal(
set([subnetA.id, subnetB1.id])
)
subnets_by_cidr3 = conn.get_all_subnets(filters={"cidrBlock": "10.0.0.0/24"})
subnets_by_cidr3.should.have.length_of(2)
set([subnet.id for subnet in subnets_by_cidr3]).should.equal(
set([subnetA.id, subnetB1.id])
)
# Filter by VPC ID and CIDR
subnets_by_vpc_and_cidr = conn.get_all_subnets(
filters={"vpc-id": vpcB.id, "cidr": "10.0.0.0/24"}
)
subnets_by_vpc_and_cidr.should.have.length_of(1)
set([subnet.id for subnet in subnets_by_vpc_and_cidr]).should.equal(
set([subnetB1.id])
)
# Filter by subnet ID
subnets_by_id = conn.get_all_subnets(filters={"subnet-id": subnetA.id})
subnets_by_id.should.have.length_of(1)
set([subnet.id for subnet in subnets_by_id]).should.equal(set([subnetA.id]))
# Filter by availabilityZone
subnets_by_az = conn.get_all_subnets(
filters={"availabilityZone": "us-west-1a", "vpc-id": vpcB.id}
)
subnets_by_az.should.have.length_of(1)
set([subnet.id for subnet in subnets_by_az]).should.equal(set([subnetB1.id]))
# Filter by defaultForAz
subnets_by_az = conn.get_all_subnets(filters={"defaultForAz": "true"})
subnets_by_az.should.have.length_of(len(conn.get_all_zones()))
# Unsupported filter
conn.get_all_subnets.when.called_with(
filters={"not-implemented-filter": "foobar"}
).should.throw(NotImplementedError)
@mock_ec2
def test_get_subnets_filtering_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")

View File

@ -1,45 +1,15 @@
import boto3
import sure # noqa # pylint: disable=unused-import
import pytest
import itertools
import boto
import boto3
from botocore.exceptions import ClientError
from boto.exception import EC2ResponseError
from boto.ec2.instance import Reservation
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2
from moto import mock_ec2_deprecated, mock_ec2
from tests import EXAMPLE_AMI_ID
from .test_instances import retrieve_all_instances
from uuid import uuid4
# Has boto3 equivalent
@mock_ec2_deprecated
def test_add_tag():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
with pytest.raises(EC2ResponseError) as ex:
instance.add_tag("a key", "some value", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateTags operation: Request would have succeeded, but DryRun flag is set"
)
instance.add_tag("a key", "some value")
chain = itertools.chain.from_iterable
existing_instances = list(
chain([res.instances for res in conn.get_all_reservations()])
)
existing_instances.should.have.length_of(1)
existing_instance = existing_instances[0]
existing_instance.tags["a key"].should.equal("some value")
@mock_ec2
def test_instance_create_tags():
ec2 = boto3.resource("ec2", "us-west-1")
@ -62,36 +32,6 @@ def test_instance_create_tags():
ours["Tags"].should.equal([{"Key": "a key", "Value": "some value"}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_remove_tag():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.add_tag("a key", "some value")
tags = conn.get_all_tags()
tag = tags[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
with pytest.raises(EC2ResponseError) as ex:
instance.remove_tag("a key", dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the DeleteTags operation: Request would have succeeded, but DryRun flag is set"
)
instance.remove_tag("a key")
conn.get_all_tags().should.have.length_of(0)
instance.add_tag("a key", "some value")
conn.get_all_tags().should.have.length_of(1)
instance.remove_tag("a key", "some value")
@mock_ec2
def test_instance_delete_tags():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -133,36 +73,6 @@ def test_instance_delete_tags():
].should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_tags():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.add_tag("a key", "some value")
tags = conn.get_all_tags()
tag = tags[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_tags_with_special_characters():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.add_tag("a key", "some<> value")
tags = conn.get_all_tags()
tag = tags[0]
tag.name.should.equal("a key")
tag.value.should.equal("some<> value")
@mock_ec2
def test_get_all_tags_with_special_characters_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -179,34 +89,6 @@ def test_get_all_tags_with_special_characters_boto3():
tag.should.have.key("Value").equal("some<> value")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_create_tags():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
tag_dict = {
"a key": "some value",
"another key": "some other value",
"blank key": "",
}
with pytest.raises(EC2ResponseError) as ex:
conn.create_tags(instance.id, tag_dict, dry_run=True)
ex.value.error_code.should.equal("DryRunOperation")
ex.value.status.should.equal(412)
ex.value.message.should.equal(
"An error occurred (DryRunOperation) when calling the CreateTags operation: Request would have succeeded, but DryRun flag is set"
)
conn.create_tags(instance.id, tag_dict)
tags = conn.get_all_tags()
set([key for key in tag_dict]).should.equal(set([tag.name for tag in tags]))
set([tag_dict[key] for key in tag_dict]).should.equal(
set([tag.value for tag in tags])
)
@mock_ec2
def test_create_tags_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -242,36 +124,6 @@ def test_create_tags_boto3():
)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_tag_limit_exceeded():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
tag_dict = {}
for i in range(51):
tag_dict["{0:02d}".format(i + 1)] = ""
with pytest.raises(EC2ResponseError) as cm:
conn.create_tags(instance.id, tag_dict)
cm.value.code.should.equal("TagLimitExceeded")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
instance.add_tag("a key", "a value")
with pytest.raises(EC2ResponseError) as cm:
conn.create_tags(instance.id, tag_dict)
cm.value.code.should.equal("TagLimitExceeded")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
tags = conn.get_all_tags()
tag = tags[0]
tags.should.have.length_of(1)
tag.name.should.equal("a key")
tag.value.should.equal("a value")
@mock_ec2
def test_tag_limit_exceeded_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -302,37 +154,6 @@ def test_tag_limit_exceeded_boto3():
tags[0].should.have.key("Value").equal("a value")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_invalid_parameter_tag_null():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
with pytest.raises(EC2ResponseError) as cm:
instance.add_tag("a key", None)
cm.value.code.should.equal("InvalidParameterValue")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
# Has boto3 equivalent
@mock_ec2_deprecated
def test_invalid_id():
conn = boto.connect_ec2("the_key", "the_secret")
with pytest.raises(EC2ResponseError) as cm:
conn.create_tags("ami-blah", {"key": "tag"})
cm.value.code.should.equal("InvalidID")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
with pytest.raises(EC2ResponseError) as cm:
conn.create_tags("blah-blah", {"key": "tag"})
cm.value.code.should.equal("InvalidID")
cm.value.status.should.equal(400)
cm.value.request_id.should_not.be.none
@mock_ec2
def test_invalid_id_boto3():
client = boto3.client("ec2", region_name="us-east-1")
@ -353,34 +174,6 @@ def test_invalid_id_boto3():
ex.value.response["Error"]["Code"].should.equal("InvalidID")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_tags_resource_id_filter():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.add_tag("an instance key", "some value")
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
image.add_tag("an image key", "some value")
tags = conn.get_all_tags(filters={"resource-id": instance.id})
tag = tags[0]
tags.should.have.length_of(1)
tag.res_id.should.equal(instance.id)
tag.res_type.should.equal("instance")
tag.name.should.equal("an instance key")
tag.value.should.equal("some value")
tags = conn.get_all_tags(filters={"resource-id": image_id})
tag = tags[0]
tags.should.have.length_of(1)
tag.res_id.should.equal(image_id)
tag.res_type.should.equal("image")
tag.name.should.equal("an image key")
tag.value.should.equal("some value")
@mock_ec2
def test_get_all_tags_resource_filter_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -433,99 +226,6 @@ def test_get_all_tags_resource_filter_boto3():
tags.should.equal([])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_tags_resource_type_filter():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.add_tag("an instance key", "some value")
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
image.add_tag("an image key", "some value")
tags = conn.get_all_tags(filters={"resource-type": "instance"})
tag = tags[0]
tags.should.have.length_of(1)
tag.res_id.should.equal(instance.id)
tag.res_type.should.equal("instance")
tag.name.should.equal("an instance key")
tag.value.should.equal("some value")
tags = conn.get_all_tags(filters={"resource-type": "image"})
tag = tags[0]
tags.should.have.length_of(1)
tag.res_id.should.equal(image_id)
tag.res_type.should.equal("image")
tag.name.should.equal("an image key")
tag.value.should.equal("some value")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_tags_key_filter():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.add_tag("an instance key", "some value")
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
image.add_tag("an image key", "some value")
tags = conn.get_all_tags(filters={"key": "an instance key"})
tag = tags[0]
tags.should.have.length_of(1)
tag.res_id.should.equal(instance.id)
tag.res_type.should.equal("instance")
tag.name.should.equal("an instance key")
tag.value.should.equal("some value")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_get_all_tags_value_filter():
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance = reservation.instances[0]
instance.add_tag("an instance key", "some value")
reservation_b = conn.run_instances(EXAMPLE_AMI_ID)
instance_b = reservation_b.instances[0]
instance_b.add_tag("an instance key", "some other value")
reservation_c = conn.run_instances(EXAMPLE_AMI_ID)
instance_c = reservation_c.instances[0]
instance_c.add_tag("an instance key", "other value*")
reservation_d = conn.run_instances(EXAMPLE_AMI_ID)
instance_d = reservation_d.instances[0]
instance_d.add_tag("an instance key", "other value**")
reservation_e = conn.run_instances(EXAMPLE_AMI_ID)
instance_e = reservation_e.instances[0]
instance_e.add_tag("an instance key", "other value*?")
image_id = conn.create_image(instance.id, "test-ami", "this is a test ami")
image = conn.get_image(image_id)
image.add_tag("an image key", "some value")
tags = conn.get_all_tags(filters={"value": "some value"})
tags.should.have.length_of(2)
tags = conn.get_all_tags(filters={"value": "some*value"})
tags.should.have.length_of(3)
tags = conn.get_all_tags(filters={"value": "*some*value"})
tags.should.have.length_of(3)
tags = conn.get_all_tags(filters={"value": "*some*value*"})
tags.should.have.length_of(3)
tags = conn.get_all_tags(filters={"value": r"*value\*"})
tags.should.have.length_of(1)
tags = conn.get_all_tags(filters={"value": r"*value\*\*"})
tags.should.have.length_of(1)
tags = conn.get_all_tags(filters={"value": r"*value\*\?"})
tags.should.have.length_of(1)
@mock_ec2
def test_get_all_tags_value_filter_boto3():
ec2 = boto3.resource("ec2", region_name="us-east-1")
@ -564,38 +264,6 @@ def test_get_all_tags_value_filter_boto3():
filter_by_value(r"*value\*\?", [instance_e.id])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_retrieved_instances_must_contain_their_tags():
tag_key = "Tag name"
tag_value = "Tag value"
tags_to_be_set = {tag_key: tag_value}
conn = boto.connect_ec2("the_key", "the_secret")
reservation = conn.run_instances(EXAMPLE_AMI_ID)
reservation.should.be.a(Reservation)
reservation.instances.should.have.length_of(1)
instance = reservation.instances[0]
reservations = conn.get_all_reservations()
reservations.should.have.length_of(1)
reservations[0].id.should.equal(reservation.id)
instances = reservations[0].instances
instances.should.have.length_of(1)
instances[0].id.should.equal(instance.id)
conn.create_tags([instance.id], tags_to_be_set)
reservations = conn.get_all_reservations()
instance = reservations[0].instances[0]
retrieved_tags = instance.tags
# Cleanup of instance
conn.terminate_instances([instances[0].id])
# Check whether tag is present with correct value
retrieved_tags[tag_key].should.equal(tag_value)
@mock_ec2
def test_retrieved_instances_must_contain_their_tags_boto3():
tag_key = "Tag name"
@ -622,30 +290,6 @@ def test_retrieved_instances_must_contain_their_tags_boto3():
retrieved_tags.should.equal([{"Key": tag_key, "Value": tag_value}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_retrieved_volumes_must_contain_their_tags():
tag_key = "Tag name"
tag_value = "Tag value"
tags_to_be_set = {tag_key: tag_value}
conn = boto.connect_ec2("the_key", "the_secret")
volume = conn.create_volume(80, "us-east-1a")
all_volumes = conn.get_all_volumes()
volume = all_volumes[0]
conn.create_tags([volume.id], tags_to_be_set)
# Fetch the volume again
all_volumes = conn.get_all_volumes()
volume = all_volumes[0]
retrieved_tags = volume.tags
volume.delete()
# Check whether tag is present with correct value
retrieved_tags[tag_key].should.equal(tag_value)
@mock_ec2
def test_retrieved_volumes_must_contain_their_tags_boto3():
tag_key = "Tag name"
@ -663,31 +307,6 @@ def test_retrieved_volumes_must_contain_their_tags_boto3():
volume.tags.should.equal([{"Key": tag_key, "Value": tag_value}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_retrieved_snapshots_must_contain_their_tags():
tag_key = "Tag name"
tag_value = "Tag value"
tags_to_be_set = {tag_key: tag_value}
conn = boto.connect_ec2(
aws_access_key_id="the_key", aws_secret_access_key="the_secret"
)
volume = conn.create_volume(80, "eu-west-1a")
snapshot = conn.create_snapshot(volume.id)
conn.create_tags([snapshot.id], tags_to_be_set)
# Fetch the snapshot again
all_snapshots = conn.get_all_snapshots()
snapshot = [item for item in all_snapshots if item.id == snapshot.id][0]
retrieved_tags = snapshot.tags
conn.delete_snapshot(snapshot.id)
volume.delete()
# Check whether tag is present with correct value
retrieved_tags[tag_key].should.equal(tag_value)
@mock_ec2
def test_retrieved_snapshots_must_contain_their_tags_boto3():
tag_key = "Tag name"
@ -705,29 +324,6 @@ def test_retrieved_snapshots_must_contain_their_tags_boto3():
snapshot["Tags"].should.equal([{"Key": tag_key, "Value": tag_value}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_filter_instances_by_wildcard_tags():
conn = boto.connect_ec2(
aws_access_key_id="the_key", aws_secret_access_key="the_secret"
)
reservation = conn.run_instances(EXAMPLE_AMI_ID)
instance_a = reservation.instances[0]
instance_a.add_tag("Key1", "Value1")
reservation_b = conn.run_instances(EXAMPLE_AMI_ID)
instance_b = reservation_b.instances[0]
instance_b.add_tag("Key1", "Value2")
reservations = conn.get_all_reservations(filters={"tag:Key1": "Value*"})
reservations.should.have.length_of(2)
reservations = conn.get_all_reservations(filters={"tag-key": "Key*"})
reservations.should.have.length_of(2)
reservations = conn.get_all_reservations(filters={"tag-value": "Value*"})
reservations.should.have.length_of(2)
@mock_ec2
def test_filter_instances_by_wildcard_tags_boto3():
ec2 = boto3.resource("ec2", region_name="eu-west-1")

View File

@ -1,9 +1,8 @@
import boto
import boto3
import pytest
import sure # noqa # pylint: disable=unused-import
from moto import mock_ec2_deprecated, mock_ec2
from moto import mock_ec2
from botocore.exceptions import ClientError
from .test_tags import retrieve_all_tagged
@ -97,6 +96,41 @@ def test_describe_vpn_connections_state_filter_attached():
my_gateway["VpcAttachments"].should.contain({"State": "attached", "VpcId": vpc_id})
@mock_ec2
def test_virtual_private_gateways_boto3():
client = boto3.client("ec2", region_name="us-west-1")
vpn_gateway = client.create_vpn_gateway(
Type="ipsec.1", AvailabilityZone="us-east-1a"
)["VpnGateway"]
vpn_gateway["VpnGatewayId"].should.match(r"vgw-\w+")
vpn_gateway["Type"].should.equal("ipsec.1")
vpn_gateway["State"].should.equal("available")
vpn_gateway["AvailabilityZone"].should.equal("us-east-1a")
@mock_ec2
def test_describe_vpn_gateway_boto3():
client = boto3.client("ec2", region_name="us-west-1")
vpn_gateway = client.create_vpn_gateway(
Type="ipsec.1", AvailabilityZone="us-east-1a"
)["VpnGateway"]
vgws = client.describe_vpn_gateways(VpnGatewayIds=[vpn_gateway["VpnGatewayId"]])[
"VpnGateways"
]
vgws.should.have.length_of(1)
gateway = vgws[0]
gateway["VpnGatewayId"].should.match(r"vgw-\w+")
gateway["VpnGatewayId"].should.equal(vpn_gateway["VpnGatewayId"])
# TODO: fixme. This currently returns the ID
# gateway["Type"].should.equal("ipsec.1")
gateway["State"].should.equal("available")
gateway["AvailabilityZone"].should.equal("us-east-1a")
@mock_ec2
def test_describe_vpn_connections_state_filter_deatched():
"""describe_vpn_gateways attachment.state filter - don't match detatched"""
@ -178,87 +212,6 @@ def test_describe_vpn_connections_type_filter_miss():
gateways["VpnGateways"].should.have.length_of(0)
# Has boto3 equivalent
@mock_ec2_deprecated
def test_virtual_private_gateways():
conn = boto.connect_vpc("the_key", "the_secret")
vpn_gateway = conn.create_vpn_gateway("ipsec.1", "us-east-1a")
vpn_gateway.should_not.be.none
vpn_gateway.id.should.match(r"vgw-\w+")
vpn_gateway.type.should.equal("ipsec.1")
vpn_gateway.state.should.equal("available")
vpn_gateway.availability_zone.should.equal("us-east-1a")
@mock_ec2
def test_virtual_private_gateways_boto3():
client = boto3.client("ec2", region_name="us-west-1")
vpn_gateway = client.create_vpn_gateway(
Type="ipsec.1", AvailabilityZone="us-east-1a"
)["VpnGateway"]
vpn_gateway["VpnGatewayId"].should.match(r"vgw-\w+")
vpn_gateway["Type"].should.equal("ipsec.1")
vpn_gateway["State"].should.equal("available")
vpn_gateway["AvailabilityZone"].should.equal("us-east-1a")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_describe_vpn_gateway():
conn = boto.connect_vpc("the_key", "the_secret")
vpn_gateway = conn.create_vpn_gateway("ipsec.1", "us-east-1a")
vgws = conn.get_all_vpn_gateways()
vgws.should.have.length_of(1)
gateway = vgws[0]
gateway.id.should.match(r"vgw-\w+")
gateway.id.should.equal(vpn_gateway.id)
vpn_gateway.type.should.equal("ipsec.1")
vpn_gateway.state.should.equal("available")
vpn_gateway.availability_zone.should.equal("us-east-1a")
@mock_ec2
def test_describe_vpn_gateway_boto3():
client = boto3.client("ec2", region_name="us-west-1")
vpn_gateway = client.create_vpn_gateway(
Type="ipsec.1", AvailabilityZone="us-east-1a"
)["VpnGateway"]
vgws = client.describe_vpn_gateways(VpnGatewayIds=[vpn_gateway["VpnGatewayId"]])[
"VpnGateways"
]
vgws.should.have.length_of(1)
gateway = vgws[0]
gateway["VpnGatewayId"].should.match(r"vgw-\w+")
gateway["VpnGatewayId"].should.equal(vpn_gateway["VpnGatewayId"])
# TODO: fixme. This currently returns the ID
# gateway["Type"].should.equal("ipsec.1")
gateway["State"].should.equal("available")
gateway["AvailabilityZone"].should.equal("us-east-1a")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_vpn_gateway_vpc_attachment():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
vpn_gateway = conn.create_vpn_gateway("ipsec.1", "us-east-1a")
conn.attach_vpn_gateway(vpn_gateway_id=vpn_gateway.id, vpc_id=vpc.id)
gateway = conn.get_all_vpn_gateways()[0]
attachments = gateway.attachments
attachments.should.have.length_of(1)
attachments[0].vpc_id.should.equal(vpc.id)
attachments[0].state.should.equal("attached")
@mock_ec2
def test_vpn_gateway_vpc_attachment_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")
@ -276,18 +229,6 @@ def test_vpn_gateway_vpc_attachment_boto3():
attachments.should.equal([{"State": "attached", "VpcId": vpc.id}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_delete_vpn_gateway():
conn = boto.connect_vpc("the_key", "the_secret")
vpn_gateway = conn.create_vpn_gateway("ipsec.1", "us-east-1a")
conn.delete_vpn_gateway(vpn_gateway.id)
vgws = conn.get_all_vpn_gateways()
vgws.should.have.length_of(1)
vgws[0].state.should.equal("deleted")
@mock_ec2
def test_delete_vpn_gateway_boto3():
client = boto3.client("ec2", region_name="us-west-1")
@ -302,23 +243,6 @@ def test_delete_vpn_gateway_boto3():
gateways[0].should.have.key("State").equal("deleted")
# Has boto3 equivalent
@mock_ec2_deprecated
def test_vpn_gateway_tagging():
conn = boto.connect_vpc("the_key", "the_secret")
vpn_gateway = conn.create_vpn_gateway("ipsec.1", "us-east-1a")
vpn_gateway.add_tag("a key", "some value")
tag = conn.get_all_tags()[0]
tag.name.should.equal("a key")
tag.value.should.equal("some value")
# Refresh the subnet
vpn_gateway = conn.get_all_vpn_gateways()[0]
vpn_gateway.tags.should.have.length_of(1)
vpn_gateway.tags["a key"].should.equal("some value")
@mock_ec2
def test_vpn_gateway_tagging_boto3():
client = boto3.client("ec2", region_name="us-west-1")
@ -340,30 +264,6 @@ def test_vpn_gateway_tagging_boto3():
# vpn_gateway["Tags"].should.equal([{'Key': 'a key', 'Value': 'some value'}])
# Has boto3 equivalent
@mock_ec2_deprecated
def test_detach_vpn_gateway():
conn = boto.connect_vpc("the_key", "the_secret")
vpc = conn.create_vpc("10.0.0.0/16")
vpn_gateway = conn.create_vpn_gateway("ipsec.1", "us-east-1a")
conn.attach_vpn_gateway(vpn_gateway_id=vpn_gateway.id, vpc_id=vpc.id)
gateway = conn.get_all_vpn_gateways()[0]
attachments = gateway.attachments
attachments.should.have.length_of(1)
attachments[0].vpc_id.should.equal(vpc.id)
attachments[0].state.should.equal("attached")
conn.detach_vpn_gateway(vpn_gateway_id=vpn_gateway.id, vpc_id=vpc.id)
gateway = conn.get_all_vpn_gateways()[0]
attachments = gateway.attachments
attachments.should.have.length_of(1)
attachments[0].state.should.equal("detached")
@mock_ec2
def test_detach_vpn_gateway_boto3():
ec2 = boto3.resource("ec2", region_name="us-west-1")

Some files were not shown because too many files have changed in this diff Show More