Fix ec2 tags in instance create. Closes #938.
This commit is contained in:
parent
0fe824277b
commit
97b920f6cf
@ -1,4 +1,6 @@
|
|||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
|
|
||||||
|
from collections import defaultdict
|
||||||
import datetime
|
import datetime
|
||||||
import json
|
import json
|
||||||
import logging
|
import logging
|
||||||
@ -330,6 +332,26 @@ class BaseResponse(_TemplateEnvironmentMixin):
|
|||||||
|
|
||||||
return results
|
return results
|
||||||
|
|
||||||
|
def _parse_tag_specification(self, param_prefix):
|
||||||
|
tags = self._get_list_prefix(param_prefix)
|
||||||
|
|
||||||
|
results = defaultdict(dict)
|
||||||
|
for tag in tags:
|
||||||
|
resource_type = tag.pop("resource_type")
|
||||||
|
|
||||||
|
param_index = 1
|
||||||
|
while True:
|
||||||
|
key_name = 'tag.{0}._key'.format(param_index)
|
||||||
|
value_name = 'tag.{0}._value'.format(param_index)
|
||||||
|
|
||||||
|
try:
|
||||||
|
results[resource_type][tag[key_name]] = tag[value_name]
|
||||||
|
except KeyError:
|
||||||
|
break
|
||||||
|
param_index += 1
|
||||||
|
|
||||||
|
return results
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def request_json(self):
|
def request_json(self):
|
||||||
return 'JSON' in self.querystring.get('ContentType', [])
|
return 'JSON' in self.querystring.get('ContentType', [])
|
||||||
|
@ -141,6 +141,10 @@ class TaggedEC2Resource(BaseModel):
|
|||||||
def add_tag(self, key, value):
|
def add_tag(self, key, value):
|
||||||
self.ec2_backend.create_tags([self.id], {key: value})
|
self.ec2_backend.create_tags([self.id], {key: value})
|
||||||
|
|
||||||
|
def add_tags(self, tag_map):
|
||||||
|
for key, value in tag_map.items():
|
||||||
|
self.ec2_backend.create_tags([self.id], {key: value})
|
||||||
|
|
||||||
def get_filter_value(self, filter_name):
|
def get_filter_value(self, filter_name):
|
||||||
tags = self.get_tags()
|
tags = self.get_tags()
|
||||||
|
|
||||||
@ -638,6 +642,10 @@ class InstanceBackend(object):
|
|||||||
security_groups.extend(self.get_security_group_from_id(sg_id)
|
security_groups.extend(self.get_security_group_from_id(sg_id)
|
||||||
for sg_id in kwargs.pop("security_group_ids", []))
|
for sg_id in kwargs.pop("security_group_ids", []))
|
||||||
self.reservations[new_reservation.id] = new_reservation
|
self.reservations[new_reservation.id] = new_reservation
|
||||||
|
|
||||||
|
tags = kwargs.pop("tags", {})
|
||||||
|
instance_tags = tags.get('instance', {})
|
||||||
|
|
||||||
for index in range(count):
|
for index in range(count):
|
||||||
new_instance = Instance(
|
new_instance = Instance(
|
||||||
self,
|
self,
|
||||||
@ -647,6 +655,7 @@ class InstanceBackend(object):
|
|||||||
**kwargs
|
**kwargs
|
||||||
)
|
)
|
||||||
new_reservation.instances.append(new_instance)
|
new_reservation.instances.append(new_instance)
|
||||||
|
new_instance.add_tags(instance_tags)
|
||||||
new_instance.setup_defaults()
|
new_instance.setup_defaults()
|
||||||
return new_reservation
|
return new_reservation
|
||||||
|
|
||||||
|
@ -47,13 +47,15 @@ class InstanceResponse(BaseResponse):
|
|||||||
associate_public_ip = self.querystring.get(
|
associate_public_ip = self.querystring.get(
|
||||||
"AssociatePublicIpAddress", [None])[0]
|
"AssociatePublicIpAddress", [None])[0]
|
||||||
key_name = self.querystring.get("KeyName", [None])[0]
|
key_name = self.querystring.get("KeyName", [None])[0]
|
||||||
|
tags = self._parse_tag_specification("TagSpecification")
|
||||||
|
|
||||||
if self.is_not_dryrun('RunInstance'):
|
if self.is_not_dryrun('RunInstance'):
|
||||||
new_reservation = self.ec2_backend.add_instances(
|
new_reservation = self.ec2_backend.add_instances(
|
||||||
image_id, min_count, user_data, security_group_names,
|
image_id, min_count, user_data, security_group_names,
|
||||||
instance_type=instance_type, placement=placement, subnet_id=subnet_id,
|
instance_type=instance_type, placement=placement, subnet_id=subnet_id,
|
||||||
key_name=key_name, security_group_ids=security_group_ids,
|
key_name=key_name, security_group_ids=security_group_ids,
|
||||||
nics=nics, private_ip=private_ip, associate_public_ip=associate_public_ip)
|
nics=nics, private_ip=private_ip, associate_public_ip=associate_public_ip,
|
||||||
|
tags=tags)
|
||||||
|
|
||||||
template = self.response_template(EC2_RUN_INSTANCES)
|
template = self.response_template(EC2_RUN_INSTANCES)
|
||||||
return template.render(reservation=new_reservation)
|
return template.render(reservation=new_reservation)
|
||||||
@ -282,6 +284,14 @@ EC2_RUN_INSTANCES = """<RunInstancesResponse xmlns="http://ec2.amazonaws.com/doc
|
|||||||
<clientToken/>
|
<clientToken/>
|
||||||
<hypervisor>xen</hypervisor>
|
<hypervisor>xen</hypervisor>
|
||||||
<ebsOptimized>false</ebsOptimized>
|
<ebsOptimized>false</ebsOptimized>
|
||||||
|
<tagSet>
|
||||||
|
{% for tag in instance.get_tags() %}
|
||||||
|
<item>
|
||||||
|
<key>{{ tag.key }}</key>
|
||||||
|
<value>{{ tag.value }}</value>
|
||||||
|
</item>
|
||||||
|
{% endfor %}
|
||||||
|
</tagSet>
|
||||||
<networkInterfaceSet>
|
<networkInterfaceSet>
|
||||||
{% for nic in instance.nics.values() %}
|
{% for nic in instance.nics.values() %}
|
||||||
<item>
|
<item>
|
||||||
|
@ -178,6 +178,44 @@ def test_get_paginated_instances():
|
|||||||
assert 'NextToken' not in resp2.keys()
|
assert 'NextToken' not in resp2.keys()
|
||||||
|
|
||||||
|
|
||||||
|
@mock_ec2
|
||||||
|
def test_create_with_tags():
|
||||||
|
ec2 = boto3.client('ec2', region_name='us-west-2')
|
||||||
|
instances = ec2.run_instances(
|
||||||
|
ImageId='ami-123',
|
||||||
|
MinCount=1,
|
||||||
|
MaxCount=1,
|
||||||
|
InstanceType='t2.micro',
|
||||||
|
TagSpecifications=[
|
||||||
|
{
|
||||||
|
'ResourceType': 'instance',
|
||||||
|
'Tags': [
|
||||||
|
{
|
||||||
|
'Key': 'MY_TAG1',
|
||||||
|
'Value': 'MY_VALUE1',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
'Key': 'MY_TAG2',
|
||||||
|
'Value': 'MY_VALUE2',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
'ResourceType': 'instance',
|
||||||
|
'Tags': [
|
||||||
|
{
|
||||||
|
'Key': 'MY_TAG3',
|
||||||
|
'Value': 'MY_VALUE3',
|
||||||
|
},
|
||||||
|
]
|
||||||
|
},
|
||||||
|
],
|
||||||
|
)
|
||||||
|
assert 'Tags' in instances['Instances'][0]
|
||||||
|
len(instances['Instances'][0]['Tags']).should.equal(3)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@mock_ec2_deprecated
|
@mock_ec2_deprecated
|
||||||
def test_get_instances_filtering_by_state():
|
def test_get_instances_filtering_by_state():
|
||||||
conn = boto.connect_ec2()
|
conn = boto.connect_ec2()
|
||||||
|
Loading…
Reference in New Issue
Block a user