in source/idea/idea-administrator/resources/lambda_functions/idea_custom_resource_update_cluster_settings/handler.py [0:0]
def handler(event: dict, context):
"""
Create or Update Cluster Configuration based on key received key value pairs
"""
logger.info(f'ReceivedEvent: {json.dumps(event)}')
request_type = event.get('RequestType', None)
resource_properties = event.get('ResourceProperties', {})
old_resource_properties = event.get('OldResourceProperties', None)
cluster_name = resource_properties.get('cluster_name')
module_id = resource_properties.get('module_id')
version = resource_properties.get('version')
stack_name = f'{cluster_name}-{module_id}'
physical_resource_id = f'{cluster_name}-{module_id}-settings'
client = HttpClient()
try:
dynamodb = boto3.resource('dynamodb')
cluster_settings_table_name = f'{cluster_name}.cluster-settings'
cluster_settings_table = dynamodb.Table(cluster_settings_table_name)
settings = resource_properties.get('settings')
modules_table_name = f'{cluster_name}.modules'
modules_table = dynamodb.Table(modules_table_name)
if request_type == 'Delete':
for key in settings:
config_key = f'{module_id}.{key}'
logger.info(f'deleting config: {config_key}')
cluster_settings_table.delete_item(
Key={
'key': config_key
}
)
modules_table.update_item(
Key={
'module_id': module_id
},
UpdateExpression='SET #status=:status, #stack_name=:stack_name, #version=:version',
ExpressionAttributeNames={
'#status': 'status',
'#stack_name': 'stack_name',
'#version': 'version',
},
ExpressionAttributeValues={
':status': 'not-deployed',
':stack_name': None,
':version': None
}
)
else:
for key in settings:
value = settings[key]
config_key = f'{module_id}.{key}'
logger.info(f'updating config: {config_key} = {value}')
cluster_settings_table.update_item(
Key={
'key': config_key
},
UpdateExpression='SET #value=:value, #source=:source ADD #version :version',
ExpressionAttributeNames={
'#value': 'value',
'#version': 'version',
'#source': 'source'
},
ExpressionAttributeValues={
':value': value,
':source': 'stack',
':version': 1
}
)
modules_table.update_item(
Key={
'module_id': module_id
},
UpdateExpression='SET #status=:status, #stack_name=:stack_name, #version=:version',
ExpressionAttributeNames={
'#status': 'status',
'#stack_name': 'stack_name',
'#version': 'version',
},
ExpressionAttributeValues={
':status': 'deployed',
':stack_name': stack_name,
':version': version
}
)
# in case of a stack Update event, compute a delta using OldResourceProperties
# and clean up any values that are no longer applicable
# this takes care of scenarios where a resource was deleted from the updated stack
if old_resource_properties is not None:
old_settings = old_resource_properties.get('settings', {})
settings_to_delete = []
for old_key in old_settings:
if old_key not in settings:
settings_to_delete.append(old_key)
if len(settings_to_delete) > 0:
for key in settings_to_delete:
config_key = f'{module_id}.{key}'
logger.info(f'deleting config: {config_key}')
cluster_settings_table.delete_item(
Key={
'key': config_key
}
)
client.send_cfn_response(CfnResponse(
context=context,
event=event,
status=CfnResponseStatus.SUCCESS,
data={},
physical_resource_id=physical_resource_id
))
except Exception as e:
logger.exception(f'failed to update cluster settings for module: {module_id} - {e}')
client.send_cfn_response(CfnResponse(
context=context,
event=event,
status=CfnResponseStatus.FAILED,
data={},
physical_resource_id=physical_resource_id
))
finally:
client.destroy()