{ "info": { "author": "Gene Wood", "author_email": "gene_wood@cementhorizon.com", "bugtrack_url": null, "classifiers": [ "Development Status :: 4 - Beta", "Intended Audience :: Developers", "License :: OSI Approved :: Mozilla Public License 2.0 (MPL 2.0)", "Programming Language :: Python :: 2.7" ], "description": "cfnlambda\n=========\n\ncfnlambda is a collection of AWS Lambda tools to enable use of AWS Lambda \nfunctions with CloudFormation. At it's core it is the `cfn_response` function \nand the `handler_decorator` decorator. These enable an AWS Lambda function, \nlaunched from a CloudFormation stack, to log to CloudWatch, return data to the\nCloudFormation stack and gracefully deal with exceptions.\n\nQuickstart\n----------\nThe easiest way to use cfnlambda is to use the `handler_decorator` decorator on\nyour AWS Lambda function.\n\n::\n\n from cfnlambda import handler_decorator\n\n @handler_decorator()\n def lambda_handler(event, context):\n result = (float(event['ResourceProperties']['key1']) + \n float(event['ResourceProperties']['key2']))\n return {'sum': result}\n\nhandler_decorator\n-----------------\n\nWhen you decorate your AWS Lambda function with the `handler_decorator` a few\nthings happen. Your AWS Lambda function can now emit output back to the\nCloudFormation stack that launched it simply by `returning`_ a dictionary of\nkey/value pairs, all of which become available to the CloudFormation stack as\nattributes of the custom resource in the stack. These values can then be\naccessed with the `Fn::GetAtt` CloudFormation function.\n\n::\n\n { \"Fn::GetAtt\": [ \"MyCustomResource\", \"a_key_returned_by_my_lambda_function\" ] }\n\nAny non-dictionary returned will be put into an custom resource attribute\ncalled `result`. Any exceptions raised by your AWS Lambda function will be\ncaught by `handler_decorator`, logged to the CloudWatch logs and returned to\nyour CloudFormation stack in the `result` attribute.\n\n::\n\n { \"Fn::GetAtt\": [ \"MyCustomResource\", \"result\" ] }\n\nUnless the `delete_logs` argument is set to False in `handler_decorator`, all\nCloudWatch logs generated while the stack was created, updated and deleted will\nbe deleted upon a successful stack deletion. If an exception is thrown during\nstack deletion, the logs will always be retained to facilitate troubleshooting.\nTo force retention of logs after a stack is deleted, set `delete_logs` to False.\n\n::\n\n from cfnlambda import handler_decorator\n logging.getLogger().setLevel(logging.DEBUG)\n\n @handler_decorator(delete_logs=False)\n def lambda_handler(event, context):\n mirror_text = event['ResourceProperties']['key1'][::-1]\n return {'MirrorText': mirror_text}\n\n\nFinally, AWS Lambda functions decorated with `handler_decorator` will not\nreport a status of FAILED when a stack DELETE is attempted. This will prevent\na CloudFormation stack from getting stuck in a DELETE_FAILED state. One side\neffect of this is that if your AWS Lambda function throws an exception while\ntrying to process a stack deletion, though the stack will show a status of\nDELETE_COMPLETE, there could still be resources which your AWS Lambda function\ncreated which have not been deleted. To disable this feature, pass\n`hide_stack_delete_failure=False` as an argument to `handler_decorator`. \n\n::\n\n from cfnlambda import handler_decorator\n\n @handler_decorator(hide_stack_delete_failure=False)\n def lambda_handler(event, context):\n raise Exception(\n 'This will result in a CloudFormation stack stuck in a\n DELETE_FAILED state')\n\nhandler_decorator usage walkthrough\n###################################\n\nHere is an example showing the creation of a very simple AWS Lambda function\nwhich sums two values passed in from the CloudFormation stack ('key1' and \n'key2) and returns the result back to the stack as 'sum'.\n\nExample assumptions:\n\n* You have a pre-existing s3 bucket called `example-bucket-us-west-2` in the\n `us-west-2` region which is either public or readable by the user launching\n the CloudFormation stack.\n* You have some way to upload a file into that s3 bucket. In the example we're\n using the `AWS CLI`_ tool. Here's how to `install and configure AWS CLI`_.\n\nFirst, this Lambda code must be zipped and uploaded to an s3 bucket.\n\n::\n\n from cfnlambda import handler_decorator\n import logging\n logging.getLogger().setLevel(logging.INFO)\n\n @handler_decorator()\n def lambda_handler(event, context):\n result = (float(event['ResourceProperties']['key1']) + \n float(event['ResourceProperties']['key2']))\n return {'sum': result}\n\nHere are a set of commands to create and upload the AWS Lambda function\n\n::\n\n dir=/path/to/PythonExampleDir\n mkdir $dir\n\n # Create your AWS Lambda function\n cat > $dir/example_lambda_module.py <