add ec2 tags
This commit is contained in:
parent
568d99dd42
commit
f824110ceb
@ -1,13 +1,16 @@
|
||||
from collections import defaultdict
|
||||
|
||||
from boto.ec2.instance import Instance, InstanceState, Reservation
|
||||
|
||||
from moto.core import BaseBackend
|
||||
from .utils import random_instance_id, random_reservation_id
|
||||
|
||||
|
||||
class EC2Backend(BaseBackend):
|
||||
class InstanceBackend(object):
|
||||
|
||||
def __init__(self):
|
||||
self.reservations = {}
|
||||
super(InstanceBackend, self).__init__()
|
||||
|
||||
def get_instance(self, instance_id):
|
||||
for instance in self.all_instances():
|
||||
@ -73,4 +76,36 @@ class EC2Backend(BaseBackend):
|
||||
return self.reservations.values()
|
||||
|
||||
|
||||
class TagBackend(object):
|
||||
|
||||
def __init__(self):
|
||||
self.tags = defaultdict(dict)
|
||||
super(TagBackend, self).__init__()
|
||||
|
||||
def create_tag(self, resource_id, key, value):
|
||||
self.tags[resource_id][key] = value
|
||||
return value
|
||||
|
||||
def delete_tag(self, resource_id, key):
|
||||
return self.tags[resource_id].pop(key)
|
||||
|
||||
def describe_tags(self):
|
||||
results = []
|
||||
for resource_id, tags in self.tags.iteritems():
|
||||
ami = 'ami' in resource_id
|
||||
for key, value in tags.iteritems():
|
||||
result = {
|
||||
'resource_id': resource_id,
|
||||
'key': key,
|
||||
'value': value,
|
||||
'resource_type': 'image' if ami else 'instance',
|
||||
}
|
||||
results.append(result)
|
||||
return results
|
||||
|
||||
|
||||
class EC2Backend(BaseBackend, InstanceBackend, TagBackend):
|
||||
pass
|
||||
|
||||
|
||||
ec2_backend = EC2Backend()
|
@ -3,11 +3,12 @@ from urlparse import parse_qs
|
||||
from moto.ec2.utils import method_namess_from_class
|
||||
|
||||
from .instances import InstanceResponse
|
||||
from .tags import TagResponse
|
||||
|
||||
|
||||
class EC2Response(object):
|
||||
|
||||
sub_responses = [InstanceResponse,]
|
||||
sub_responses = [InstanceResponse, TagResponse]
|
||||
|
||||
def dispatch(self, uri, body, headers):
|
||||
if body:
|
||||
@ -23,3 +24,4 @@ class EC2Response(object):
|
||||
response = sub_response(querystring)
|
||||
method = getattr(response, action)
|
||||
return method()
|
||||
import pdb;pdb.set_trace()
|
||||
|
50
moto/ec2/responses/tags.py
Normal file
50
moto/ec2/responses/tags.py
Normal file
@ -0,0 +1,50 @@
|
||||
from jinja2 import Template
|
||||
|
||||
from moto.ec2.models import ec2_backend
|
||||
from moto.ec2.utils import resource_ids_from_querystring, camelcase_to_underscores, method_namess_from_class
|
||||
|
||||
|
||||
class TagResponse(object):
|
||||
def __init__(self, querystring):
|
||||
self.querystring = querystring
|
||||
self.resource_ids = resource_ids_from_querystring(querystring)
|
||||
|
||||
def CreateTags(self):
|
||||
for resource_id, tag in self.resource_ids.iteritems():
|
||||
ec2_backend.create_tag(resource_id, tag[0], tag[1])
|
||||
return CREATE_RESPONSE
|
||||
|
||||
def DeleteTags(self):
|
||||
ec2_backend.delete_tag()
|
||||
template = Template(DELETE_RESPONSE)
|
||||
return template.render(reservations=ec2_backend.all_reservations())
|
||||
|
||||
def DescribeTags(self):
|
||||
tags = ec2_backend.describe_tags()
|
||||
template = Template(DESCRIBE_RESPONSE)
|
||||
return template.render(tags=tags)
|
||||
|
||||
|
||||
CREATE_RESPONSE = """<CreateTagsResponse xmlns="http://ec2.amazonaws.com/doc/2012-12-01/">
|
||||
<requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
|
||||
<return>true</return>
|
||||
</CreateTagsResponse>"""
|
||||
|
||||
DELETE_RESPONSE = """<DeleteTagsResponse xmlns="http://ec2.amazonaws.com/doc/2012-12-01/">
|
||||
<requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
|
||||
<return>true</return>
|
||||
</DeleteTagsResponse>"""
|
||||
|
||||
DESCRIBE_RESPONSE = """<DescribeTagsResponse xmlns="http://ec2.amazonaws.com/doc/2012-12-01/">
|
||||
<requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
|
||||
<tagSet>
|
||||
{% for tag in tags %}
|
||||
<item>
|
||||
<resourceId>{{ tag.resource_id }}</resourceId>
|
||||
<resourceType>{{ tag.resource_type }}</resourceType>
|
||||
<key>{{ tag.key }}</key>
|
||||
<value>{{ tag.value }}</value>
|
||||
</item>
|
||||
{% endfor %}
|
||||
</tagSet>
|
||||
</DescribeTagsResponse>"""
|
@ -26,6 +26,19 @@ def instance_ids_from_querystring(querystring_dict):
|
||||
return instance_ids
|
||||
|
||||
|
||||
def resource_ids_from_querystring(querystring_dict):
|
||||
prefix = 'ResourceId'
|
||||
response_values = {}
|
||||
for key, value in querystring_dict.iteritems():
|
||||
if prefix in key:
|
||||
resource_index = key.replace(prefix + ".", "")
|
||||
tag_key = querystring_dict.get("Tag.{}.Key".format(resource_index))[0]
|
||||
tag_value = querystring_dict.get("Tag.{}.Value".format(resource_index))[0]
|
||||
response_values[value[0]] = (tag_key, tag_value)
|
||||
|
||||
return response_values
|
||||
|
||||
|
||||
def camelcase_to_underscores(argument):
|
||||
''' Converts a camelcase param like theNewAttribute to the equivalent
|
||||
python underscore variable like the_new_attribute'''
|
||||
|
20
tests/test_ec2/test_tags.py
Normal file
20
tests/test_ec2/test_tags.py
Normal file
@ -0,0 +1,20 @@
|
||||
import boto
|
||||
from boto.ec2.instance import Reservation, InstanceAttribute
|
||||
from sure import expect
|
||||
|
||||
from moto import mock_ec2
|
||||
|
||||
|
||||
|
||||
@mock_ec2
|
||||
def test_instance_launch_and_terminate():
|
||||
conn = boto.connect_ec2('the_key', 'the_secret')
|
||||
reservation = conn.run_instances('<ami-image-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")
|
Loading…
Reference in New Issue
Block a user