def handler(event, context) -> None: """ Handles incoming event. :param event: Invocation event. :param context: Invocation context. :return: No return. """ response = CfnResponse(event, context) try: data, resource_id = __handle(event, context) response.respond(CfnResponse.CfnResponseStatus.SUCCESS, data=data, resource_id=resource_id) except ClientError as ex: err_msg = f'{repr(ex)}:{ex.response}' response.respond(CfnResponse.CfnResponseStatus.FAILED, status_reason=err_msg) logger.exception(ex) except Exception as ex: response.respond(CfnResponse.CfnResponseStatus.FAILED, status_reason=repr(ex)) logger.exception(ex)
def handler(event: Union[CreateEvent, UpdateEvent, DeleteEvent], context): # Log the event to CloudWatch Logs for debugging (if needed) # Using /r instead of /n makes the log entry nicely expandable in CloudWatch logs print(json.dumps(event, indent=2).replace("\n", "\r")) # The outer try-except block ensures that a response is ALWAYS send to CloudFormation try: # Use the "RequestType" from the event (Create/Update/Delete), # to determine the right function to call, and then call it passing the event. # # Each handling function should return a tuple containing: # - physical_resource_id (str): the physical resource id of your Custom Resource. # This is an important field that you should specify explicitly. # If you change the value of this field during a CloudFormation Update, # CloudFormation will issue a Delete against the previous value. # - response_data (dict): dictionary with key-value pairs that you can !GetAtt # in your CloudFormation template physical_resource_id, response_data = getattr( Handlers, event["RequestType"])(event) # All done! Let CloudFormation know about our success CfnResponse.send( event, context, CfnResponse.SUCCESS, response_data=response_data, physical_resource_id=physical_resource_id, ) except Exception as e: # Oops, we failed! Let's tell CloudFormation about this, so it knows # and can rollback other changes in the stack CfnResponse.send( event, context, CfnResponse.FAILED, str(e), physical_resource_id=cast(Union[UpdateEvent, DeleteEvent], event).get("PhysicalResourceId"), ) # Do raise the error again after sending the CloudFormation response: # - this makes the error (and stack) visible in CloudWatch Logs # - this reflects the invocation failure in CloudWatch metrics raise