def remove_private_dns_record(self, instance): logs.info( self.__class__.__name__, "remove_private_dns_record {}".format(instance), ) self.remove_dns_record(instance.get("private_dns"), self.hosted_zone_ids.get("private"))
def create(event, context): if "body" not in event or event.get("body") is None: return Response.error( "Missing required parameters: account, region, id") event = json.loads(event.get("body")) account_name = event.get("account", None) region = event.get("region", None) logs.info("Handler", "create: {}, {}".format(account_name, region)) try: account, instances = _build_instance_model(account_name, region) except Exception as error: logs.info("Handler", "Error: create setup {}".format(error.args[0])) return Response.error(error.args[0]) try: instances.create(Instance(event, account)) except Exception as error: return Response.error(error.args[0]) return Response.created( "perfecto - within 5 minutes your instance be ready available!")
def get_new_session(self, account_name, role, region): logs.info( "AwsAccountProvider", "assume_role_session({}, {}, {})".format(account_name, role, region), ) return assume_role_session(account_name, role, region)
def create(event, context): if "body" not in event or event.get("body") is None: return Response.error( "Missing required parameters: resultados and comentarios") event = jason.loads(event.get("body")) seconds = time.time() resultados = event.get("resultados", None) votos = [] for r in resultados.split('&'): votos.append(r.split('=')) comentarios = Comentarios(encuesta_id=seconds, comentario=event.get("comentarios", None)) s = Session(mysql_engine()) objects = [] for v in votos: e = Votos(pregunta=v[0], voto=v[1], encuesta_id=seconds) objects.append(e) s.bulk_save_objects(objects) s.bulk_save_objects([comentarios]) s.commit() logs.info("Handler", "create: {}, {}".format(votos, comentarios)) return Response.created("create: {}, {}".format(resultados, comentarios))
def create(self, entity, platform_input_data=None): if platform_input_data: logs.info( self.__class__.__name__, "create platform {}".format(platform_input_data), ) else: logs.info( self.__class__.__name__, "create instance {}".format(entity.attributes), ) m = self.account_provider.find_by_name(entity.name) if len(m) > 0: raise Exception( "Instance Name alreay exist: {}, choose a different name". format(entity.name)) entity.cloud_init = ( self.account_provider.userdata_cloud_init_platform( platform_input_data) if platform_input_data else self.account_provider.userdata_cloud_init()) instance = self.account_provider.create(entity) self.account_provider.create_private_dns_record(instance) if instance.get("public_ip"): self.account_provider.create_public_dns_record(instance) self.dispatcher.send("info", {"event": "create", "resource": instance}) return instance
def start(self, instance_id): logs.info(self.__class__.__name__, "start instance {}".format(instance_id)) if not instance_id: raise Exception("Missing id") instance = self.account_provider.get_instance(instance_id) if instance.get("state") not in ("stopped"): raise Exception("Wrong state, Instance must be state stopped") self.account_provider.start() instance = self.account_provider.get_instance() try: self.account_provider.create_instance_dns_records(instance) except Exception as error: logs.warning( "Model", "create_dns_record failed because {}".format(error.args[0]), ) raise exception.DnsRecordsTagsMissing( "create_dns_record failed because {}".format(error.args[0])) finally: try: self.dispatcher.send("info", { "event": "start", "resource": instance }) except Exception as error: logs.warning("Model", "notify failed") pass
def stop(self, instance_id): logs.info(self.__class__.__name__, "stop instance {}".format(instance_id)) if not instance_id: raise Exception("Missing id") instance = self.account_provider.get_instance(instance_id) if instance.get("state") != "running": raise Exception("Instance is not running") self.account_provider.stop() instance = self.account_provider.get_instance() try: self.account_provider.remove_instance_dns_records(instance) except Exception as error: logs.warning("Model", "remove_dns_record failed") pass finally: try: self.dispatcher.send("info", { "event": "stop", "resource": instance }) except Exception as error: logs.warning("Model", "notify failed") pass
def dns_record(self, action, name, value, hosted_zone_id): if value is None or name is None: logs.info( self.__class__.__name__, "dns_record name is {} and value is {}".format(name, value), ) return logs.info( self.__class__.__name__, "{} change_resource_record_sets {} with value {}".format( action, name, value), ) self.route53.change_resource_record_sets( HostedZoneId=hosted_zone_id, ChangeBatch={ "Comment": "{} record set".format(action), "Changes": [{ "Action": action, "ResourceRecordSet": { "Name": name, "Type": "A", "TTL": 0, "ResourceRecords": [ { "Value": value }, ], }, }], }, )
def terminate(self, instance_id): logs.info( self.__class__.__name__, "terminate instance {}".format(instance_id), ) if not instance_id: raise Exception("Missing id") instance = self.account_provider.get_instance(instance_id) try: self.account_provider.remove_instance_dns_records(instance) except Exception as error: logs.warning("Model", "remove_dns_records failed") pass self.account_provider.terminate() try: self.dispatcher.send("info", { "event": "terminate", "resource": instance }) except Exception as error: logs.warning("Model", "notify failed") pass
def stop(self): logs.info(self.__class__.__name__, "stop {}".format(self.instance)) self.instance.stop() self.instance.create_tags(Tags=[{ "Key": self.presenter.INSTANCE_TAGS_MAPPINGS.get("last_stop_at"), "Value": self.now.strftime("%d/%m/%Y %H:%M:%S"), }])
def modify_attribute(self, attribute, value): if attribute not in self.instance_attributes.values(): raise Exception( "attribiute {} not allowed to modify".format(attribute)) logs.info( self.__class__.__name__, "instance modify_attribute {} value {}".format(attribute, value), ) return self.instance.modify_attribute(attribute, value)
def terminate(self): logs.info(self.__class__.__name__, "terminate {}".format(self.instance)) self.instance.create_tags(Tags=[{ "Key": self.presenter.INSTANCE_TAGS_MAPPINGS.get("terminate_date"), "Value": self.now.strftime("%d/%m/%Y %H:%M:%S"), }]) self.instance.terminate()
def get_instance(self, instance_id=None): logs.info(self.__class__.__name__, "get_instance {}".format(instance_id)) if self.instance is None and instance_id is None: raise Exception("Instance is not set") elif instance_id: self.instance = self.ec2_resource.Instance(instance_id) self.instance.reload() return self.presenter.instance(self.instance)
def set_ready_state(self, instance_id): logs.info(self.__class__.__name__, "set_ready_state {}".format(instance_id)) if not instance_id: raise Exception("Missing id") self.account_provider.set_ready_state_tags(instance_id) self.dispatcher.send("info", { "event": "set_ready_state", "instance_id": instance_id })
def start(self): logs.info(self.__class__.__name__, "start {}".format(self.instance)) self.instance.start() self.instance.create_tags(Tags=[{ "Key": self.presenter.INSTANCE_TAGS_MAPPINGS.get("last_start_at"), "Value": self.now.strftime("%d/%m/%Y %H:%M:%S"), }]) self.instance = self.wait_for_public_ip(self.instance, 1) return self.presenter.instance( self.instance) # Fetch info again so it includes up-to-date data
def __init__(self, config): """ :type account: Account object :type settings: Settings.config map """ self.dynamodb = boto3.resource("dynamodb") self.table = self.dynamodb.Table(config.get("dynamodb").get("table")) logs.info("Storage", "Table {}".format(config.get("dynamodb").get("table"))) self.s3 = boto3.resource("s3") self.bucket = self.s3.Bucket(config.get("s3").get("bucket")) logs.info("Storage", "s3 {}".format(config.get("s3").get("bucket")))
def list_images(self): logs.info( self.__class__.__name__, "attributes images by tags {}".format(self.image_filters), ) self.images_list = self.ec2_client.describe_images( Filters=self.image_filters) images = self.presenter.images_list(self.images_list) logs.info( self.__class__.__name__, "attributes found {} images".format(len(images)), ) return images
def info(event, context): storage = Storage(Settings().config) try: owners_list = storage.list_all_owners() except Exception as error: logs.info("Handler", "Error: list_all_owners {}".format(error.args[0])) return Response.error(error.args[0]) response = { "users": owners_list, "environments": ["test", "prod", "poc", "demo"], } return Response.success(response)
def wait_for_public_ip(self, instance, iteration, required=False): logs.info( self.__class__.__name__, "wait_for_public_ip {} iteration {}".format(instance, iteration), ) limit = 10 if iteration > limit: logs.info( self.__class__.__name__, "Failed to get public IP address".format( self.__class__.__name__), ) if required: raise Exception("{} Failed to get public IP address".format( self.__class__.__name__)) return instance if not instance.public_ip_address and iteration <= limit: logs.info( self.__class__.__name__, "Cannot to get public IP address, retrying in 5 sec...".format( self.__class__.__name__), ) time.sleep(5) instance.reload() return self.wait_for_public_ip(instance, iteration + 1) logs.info( self.__class__.__name__, "Found instance.public_ip_address {}".format( instance.public_ip_address), ) return instance
def set_ready_state_tags(self, instance_id): logs.info( self.__class__.__name__, "set_ready_state_tags {}".format(instance_id), ) self.ec2_client.create_tags( DryRun=False, Resources=[instance_id], Tags=[{ "Key": self.presenter.INSTANCE_TAGS_MAPPINGS.get("ready_status"), "Value": "Ready", }], )
def create_public_dns_record(self, instance): logs.info(self.__class__.__name__, "create_dns_record {}".format(instance)) if not instance.get("public_dns"): raise exception.DnsRecordsTagsMissing( "public_dns missing from instance, fix it by updating it (click update->save)" ) self.dns_record( "UPSERT", instance.get("public_dns"), instance.get("public_ip"), self.hosted_zone_ids.get("public"), )
def list_instances(self, filters=None): tags_filters = self.presenter.get_tag_filters(self.instance_filters, filters) logs.info( self.__class__.__name__, "attributes instances by tags {}".format(tags_filters), ) self.instance_list = self.ec2_client.describe_instances( Filters=tags_filters) instances = self.presenter.instances_list(self.instance_list) logs.info( self.__class__.__name__, "attributes found {} instances".format(len(instances)), ) return instances
def list_security_groups(self): logs.info( self.__class__.__name__, "attributes security_groups by tags {}".format( self.security_groups_filters), ) self.security_groups_list = self.ec2_client.describe_security_groups( Filters=self.security_groups_filters) security_groups = self.presenter.security_groups_list( self.security_groups_list) logs.info( self.__class__.__name__, "attributes found {} security_groups".format(len(security_groups)), ) return security_groups
def create_image(self, instance_id, image_name): logs.info(self.__class__.__name__, "stop instance {}".format(instance_id)) if not instance_id: raise Exception("Missing id") instance = self.account_provider.get_instance(instance_id) self.account_provider.create_image(image_name, instance) self.dispatcher.send( "info", { "event": "create_image", "name": image_name, "instance_id": instance_id, }, )
def _build_instance_model(account_name, region, settings=None): if settings is None: try: settings = Settings() except Exception as error: logs.info("Handler", "Error getting settings {}".format(error.args[0])) raise Exception("Error getting settings, {}".format(error.args[0])) account_map = settings.accounts.get(account_name) if not account_map.get("enabled", False): raise Exception("Error {} is set enabled: false".format(account_name)) account = Account(account_map, region) instances = Instances(Provider(account, settings), Dispatcher(settings.config.get("sns"))) return (account, instances)
def __init__(self, account_entity, settings): """ :type account_entity: Account Entity :type settings: Settings object """ self.settings = settings self.account = account_entity self.presenter = Presenter() logs.info( "AWSAccountProvider", "account_entity = {}".format(account_entity.__dict__), ) logs.info( "AWSAccountProvider", "account_entity.id = {}".format(account_entity.id), ) logs.info( "AWSAccountProvider", "account_entity.sts_role = {}".format(account_entity.sts_role), ) logs.info( "AWSAccountProvider", "account_entity.region = {}".format(account_entity.region), ) session = self.get_new_session(account_entity.id, account_entity.sts_role, account_entity.region) self.ec2_resource = session.resource("ec2") self.ec2_client = session.client("ec2") self.route53 = session.client("route53") self.hosted_zone_names = account_entity.hosted_zone_names self.hosted_zone_ids = account_entity.hosted_zones_ids self.instance_filters = account_entity.tag_filters.get("instances") self.image_filters = account_entity.tag_filters.get("images") self.security_groups_filters = account_entity.tag_filters.get( "security_groups") # Attributes set after object Creation # AWS Resource Only when start, stop, terminate, create, create_image self.instance = None # [] Only when list, stop_tagged_instances, terminate_tagged_instances, start_tagged_instances self.instance_list = None # [] Only when list_images self.images_list = None # [] Only when list_security_groups self.security_groups_list = None
def start_instances(self, instances_ids): logs.info(self.__class__.__name__, "start_instances {}".format(instances_ids)) self.ec2_client.start_instances( InstanceIds=instances_ids, DryRun=False, ) self.ec2_client.create_tags( DryRun=False, Resources=instances_ids, Tags=[{ "Key": self.presenter.INSTANCE_TAGS_MAPPINGS.get("last_start_at"), "Value": "{} - scheduled".format( self.now.strftime("%d/%m/%Y %H:%M:%S")), }], )
def instance_ready(event, context): if "body" not in event or event.get("body") is None: return Response.error( "Missing required parameters: account, region, id") event = json.loads(event.get("body")) account_name = event.get("account", None) region = event.get("region", None) instance_id = event.get("id", None) logs.info( "Handler", "start: {}, {}, {}".format(account_name, region, instance_id), ) try: _, instances = _build_instance_model(account_name, region) except Exception as error: logs.info("Handler", "Error: start setup {}".format(error.args[0])) return Response.error(error.args[0]) try: instances.set_ready_state(instance_id) except Exception as error: logs.info("Handler", "Error: set_ready_state {}".format(error.args[0])) return Response.error(error.args[0]) return Response.success("wohooo - ready state set!")
def create_image(event, context): if "body" not in event or event.get("body") is None: return Response.error( "Missing required parameters: account, region, id") event = json.loads(event.get("body")) account_name = event.get("account", None) region = event.get("region", None) instance_id = event.get("id", None) image_name = event.get("image_name", None) logs.info( "Handler", "start: {}, {}, {}".format(account_name, region, instance_id), ) try: _, instances = _build_instance_model(account_name, region) except Exception as error: logs.info("Handler", "Error: start setup {}".format(error.args[0])) return Response.error(error.args[0]) try: instances.create_image(instance_id, image_name) except Exception as error: logs.info("Handler", "Error: Start Instance {}".format(error.args[0])) return Response.error(error.args[0]) return Response.success("ja precies - creating image!")
def create(self, post_data=None): if not post_data: post_data = { "name": "cloudinstance-unittest-{}".format(time.time_ns()), "image_id": "ami-0151d8654227898e7", "owner": "hector", "environment": "test", # env = CloudInstances-api-test sets special tags "type": "t2.small", "termination_date": "", "account": "engineering", "region": "frankfurt", } print("\n\n########## CREATE ###########\n\n") entity = Entity(post_data, self.account) instance = self.model.create(entity) instance = self.model.account_provider.get_provider_resource( instance.get("id")) logs.info(self.__class__.__name__, "instance state {}".format(instance.state)) logs.info(self.__class__.__name__, "wait_until_running") instance.wait_until_exists({ "Name": "instance-id", "Values": [ instance.id, ] }) while instance.state.get("Name") != "running": go_sleep(5, "state {}".format(instance.state)) instance.reload() self.assertRegex(instance.get("id"), "i-") self.assertEquals(post_data.get("name"), instance.get("name")) print(instance) return instance