blambda
v0.1.0
Published
Better Lambda Deployment for monorepos
Downloads
3
Maintainers
Readme
Blambda
Basic tool to deploy Lambda Functions to AWS from a monorepo without specifying any function configuration. This is the programmatic version of blambda-cli.
Requires Node 8+
Why?
Most Lambda deployment tools out there work in various different ways, but our team was looking for something that can handle just the basics. Blambda assumes that you have already deployed or setup the Lambda function in AWS, whether is be manually, with Terraform or CloudFormation. Our team writes the configuration for Lambda with Terraform and deploy. Tools like Apex and Serverless handles most of that for you and it was just not possible in our environment.
In this case, Blambda was born as a way to deploy function code without setting any of configuration for Lambda, although it has been written in a way that could, but it doesn't support it out of the box. Blambda also works exclusively monorepos only.
- Deploys multiple Lambda Functions in a monorepo to AWS.
- Skips the configuration and just handles the deployment.
- Deploys via an S3 Bucket to handle size restrictions with direct upload deployment.
- Provides functionality like aliasing, rollback and remote invocation.
- Has available CLI tool for simple use on a CI platform.
Usage
Install
npm install --save blambda
Example
const blambda = require('blambda')({
/* options */
});
// ...
// Searches CWD to find all available Lambda functions
const functions = await blambda.getFunctions();
console.log(`Found ${functions.length} lambda functions`);
for(const func of functions) {
// Initializes the Lambda Function by retrieving information from AWS about the function
await func.init();
// Deploy the function
await func.deploy();
}
API Documentation
blambda
blambda([options]) ⇒ Blambda ⏏
Creates a new instance of Blambda with the provided options.
Kind: Exported function
Returns: Blambda - Instance of the Blambda class.
| Param | Type | Default | Description |
| --- | --- | --- | --- |
| [options] | Object | {} | Options for Blamda. More information available here. |
| [options.cwd] | String | process.cwd() | The current working directory to run Blambda in. |
| [options.environment] | String | process.env.NODE_ENV | The environment in which to deploy the lambda function. Defaults to production
. |
| [options.deployTimeout] | Number | 300 | Timeout for deployments in seconds. |
| [options.tempDir] | String | os.tmpdir() | Temp directory to store archives before uploading to S3. |
| [options.colors] | Boolean | true | Enables/disables terminal colors for log outputs. Will autodetect color support by default. |
| [options.install] | String | Boolean | 'npm i --production -s' | Default dependencies install command to run for each function. Set to false
to skip install step. See install command. |
| [options.proxy] | http.Agent | | Instance of a proxy agent to use. (ex. proxy-agent). See proxy. |
| [options.region] | String | process.env.AWS_REGION | AWS Region to deploy to. |
| [options.profile] | String | process.env.AWS_PROFILE | AWS profile to use if using credentials from .aws
. |
| [options.accessKeyId] | String | | AWS Access Key ID. |
| [options.secretAccessKey] | String | | AWS Secret Access Key. |
| [options.sessionToken] | String | | AWS session token to utilize for access. |
| [options.bucket] | String | process.env.BLAMBDA_ARTIFACT_BUCKET | Bucket in which to store artifacts for deployment. Must already exist. See S3 bucket. |
| [options.awsConfig] | Object | {} | Optional AWS configuration to pass into the AWS SDK. See AWS.Config. |
| [options.nameTemplate] | String | '{{dirName}}' | Template for generating lambda function names. See name template. |
| [options.envMapping] | Object | | Maps NODE_ENV
strings to a custom name. Mapped names are used when creating aliases for function versions during deployment. See environment mapping. |
| [options.exclude] | Array.<String> | | Array of directory names to exclude when searching for functions. Blamda will automatically skip any directories that start with a .
. See exclude. |
| [options.hooks] | Object | {} | Shell commands to execute at different stages of the process for each function. Additional hooks can be added by using function configuration for a specific function. See Hooks. |
| [options.hooks.beforeInstall] | String | | Shell command to run before installing dependencies. See Hooks. |
| [options.hooks.afterInstall] | String | | Shell command to run after installing dependencies. See Hooks. |
| [options.hooks.zip] | String | | Shell command to run after creating the zip archive for a function. See Hooks. |
| [options.hooks.beforeDeploy] | String | | Shell command to run before deploying the function to AWS. See Hooks. |
| [options.hooks.afterDeploy] | String | | Shell command to run after deploying the function to AWS. See Hooks. |
| [options.hooks.deployComplete] | String | | Shell command to run after deploying and updating function information from AWS. See Hooks. |
| [options.params] | Object | {} | Default parameters to use when creating new functions. Can contain any of the parameters from lambda.createFunction although Code
and FunctionName
are dynamically generated and should not be provided. Must contain a minimum of Handler
, Role
and Runtime
. May be overridden by using function configuration. See params. |
Blamda
Kind: global class
new Blamda(opts)
Creates an instance of Blamda.
| Param | Type | Description | | --- | --- | --- | | opts | Object | Options to control Blambda. |
blambda.getFunctions() ⇒ Promise.<FunctionList>
Finds and returns an Array of functions found.
Kind: instance method of Blamda
Returns: Promise.<FunctionList> - Array of valid Lambda functions found.
LambdaFunction ⇐ Utils
Kind: global class
Extends: Utils
- LambdaFunction ⇐ Utils
- new LambdaFunction(opts, func)
- func.name : String
- func.dirName : String
- func.path : String
- func.package : Object
- func.isNew : Boolean
- func.aliases : Array.<Object>
- func.versions : Array.<String>
- func.config : Object
- func.config
- func.init() ⇒ Promise.<undefined>
- func.deploy([allAliases]) ⇒ Promise.<Object>
- func.alias(alias, version) ⇒ Promise.<Array.<Object>>
- func.rollback(version) ⇒ Promise.<Array.<Object>>
- func.invoke(payload, [qualifier]) ⇒ Promise.<Object>
- Event: deploy
- Event: deploy:changed
- Event: deploy:creating
- Event: deploy:creating
- Event: deploy:creating
- Event: deploy:aliases
- Event: error
new LambdaFunction(opts, func)
Creates an instance of LambdaFunction.
| Param | Type | Description | | --- | --- | --- | | opts | Object | Blambda options object. | | func | Object | Function configuration object. |
func.name : String
The generated name for the function.
Kind: instance property of LambdaFunction
func.dirName : String
Name of the directory in which the function code lives in.
Kind: instance property of LambdaFunction
func.path : String
Path to the directory containing the function code.
Kind: instance property of LambdaFunction
func.package : Object
Object containing all information from package.json
.
Kind: instance property of LambdaFunction
func.isNew : Boolean
Flag to determine if this is a new Lambda function (not deployed yet).
Kind: instance property of LambdaFunction
func.aliases : Array.<Object>
List of alias data returned from lambda.listAliases()
in the AWS SDK.
Kind: instance property of LambdaFunction
func.versions : Array.<String>
List of most recent versions deployed for this lambda from the AWS SDK.
Kind: instance property of LambdaFunction
func.config : Object
Gets the compiled configuration object for Blambda and this function.
Kind: instance property of LambdaFunction
func.config
Sets the configuration object by merging in the original configuration options.
Kind: instance property of LambdaFunction
func.init() ⇒ Promise.<undefined>
Initializes the class by calling the AWS SDK to pull in relevant information about the function.
Kind: instance method of LambdaFunction
func.deploy([allAliases]) ⇒ Promise.<Object>
Runs all the steps to deploy a lambda function.
Kind: instance method of LambdaFunction
Returns: Promise.<Object> - Response from lambda.updateFunctionCode()
or lambda.createFunction()
.
| Param | Type | Default | Description | | --- | --- | --- | --- | | [allAliases] | Boolean | false | Forces updating all aliases with the new version for existing functions. |
func.alias(alias, version) ⇒ Promise.<Array.<Object>>
Creates or updates an alias to a specified version.
Kind: instance method of LambdaFunction
Returns: Promise.<Array.<Object>> - Response from lambda.createAlias()
or lambda.updateAlias()
.
| Param | Type | Description | | --- | --- | --- | | alias | String | The alias to create/update. | | version | String | Version to set the alias to. |
func.rollback(version) ⇒ Promise.<Array.<Object>>
Rollback the function to the specific version. This simply updates the alias for the set opts.environment
to the provided version.
Kind: instance method of LambdaFunction
Returns: Promise.<Array.<Object>> - Response from lambda.createAlias()
or lambda.updateAlias()
.
| Param | Type | Description | | --- | --- | --- | | version | String | The version in which to set the alias to. |
func.invoke(payload, [qualifier]) ⇒ Promise.<Object>
Invokes the deployed function on AWS and returns the results.
Kind: instance method of LambdaFunction
Returns: Promise.<Object> - Response from lambda.invoke()
.
| Param | Type | Description | | --- | --- | --- | | payload | String | JSON stringified data to pass to the lambda function. | | [qualifier] | String | The version or alias to invoke. If omitted, it will default to the lastest version. |
Event: deploy
Emitted when deployment starts.
Kind: event emitted by LambdaFunction
Event: deploy:changed
Emitted if a lambda function has changed or not since the last deployment.
Kind: event emitted by LambdaFunction
Properties
| Name | Type | Description | | --- | --- | --- | | changed | Boolean | Whether the lambda function has changed. |
Event: deploy:creating
Emitted prior to creating a new function on AWS.
Kind: event emitted by LambdaFunction
Event: deploy:creating
Emitted prior to updating a function on AWS.
Kind: event emitted by LambdaFunction
Event: deploy:creating
Emitted after the lambda function has been deployed.
Kind: event emitted by LambdaFunction
Properties
| Name | Type | Description | | --- | --- | --- | | response | Object | The response from the AWS SDK. |
Event: deploy:aliases
Emitted prior to setting the aliases for the function.
Kind: event emitted by LambdaFunction
Event: error
Emitted when there is an error.
Kind: event emitted by LambdaFunction
Properties
| Name | Type | Description | | --- | --- | --- | | err | * | The resulting error. |
FunctionList ⇐ Array
Kind: global class
Extends: Array
new FunctionList([funcs])
Creates an instance of FunctionList.
| Param | Type | Default | Description | | --- | --- | --- | --- | | [funcs] | Array.<LambdaFunction> | [] | List of functions to push into the array. |
list.get(val) ⇒ LambdaFunction
Gets a specific function based on the provided value.
Kind: instance method of FunctionList
Returns: LambdaFunction - The found LambdaFunction instance or undefined
if not found.
| Param | Type | Description |
| --- | --- | --- |
| val | String | Searches based on the function name, directory name and name inside package.json
for the function. |
Utils ⇐ EventEmitter
Kind: global class
Extends: EventEmitter
new Utils()
Utility functions that are utilized in the LambdaFunction class. Internally used.
More Information
AWS Permissions
In order to deploy and manage Lambda functions with Blambda, you must either use Access Keys with a minimum of the following permissions or create an assumable role in which has the following permissions:
lambda:ListFunctions
lambda:ListVersionsByFunction
lambda:GetFunction
lambda:GetFunctionConfiguration
lambda:CreateFunction
lambda:UpdateFunctionConfiguration
lambda:UpdateFunctionCode
lambda:PublishVersion
lambda:InvokeFunction
lambda:ListAliases
lambda:GetAlias
lambda:CreateAlias
lambda:UpdateAlias
lambda:TagResource
s3:ListBucket
s3:PutObject
In the future, Blambda may require the following permissions and can be added to support the features now before they are available:
lambda:DeleteAlias
lambda:DeleteFunction
lambda:ListLayers
lambda:ListLayerVersions
lambda:GetLayerVersion
lambda:AddLayerVersionPermission
lambda:RemoveLayerVersionPermission
lambda:DeleteLayerVersion
lambda:PublishLayerVersion
Function Configuration
Each function can have its own configuration based off of the Blambda Options. In order to configure each function individually, you must put the options in one of the following files within the function's directory:
package.json
- You may specify the configuration in your package.json in a property calledfunction
..functionrc
- Can be either YAML or JSON format..functionrc.json
.functionrc.yml
or.functionrc.yaml
.functionrc.js
- Must export an object with the configuration.function.config.js
- Must export an object with the configuration. Useful when needing to dynamically set configuration options, such asproxy
.
Most of the configuration options from the global options are allowed in the function configuration except for the following:
- cwd
- environment
- colors
- nameTemplate
- exclude
Specifying any of the above properties will not do anything, although it could cause side-effects to a deployment so it's best to not have them at all.
All configuration properties specified for a function will override/merge with the global options and will only be applied to that function.
Install Command
You may specify the install command which will install the dependencies for each of the functions. This command can be globally specified in the options but also overridden within each individual function inside of the Function Configuration. By default, the install command is:
npm i --production -s
If you set the install
configuration option to false
, Blambda will skip the installation step.
Note: If the install command contains -s
or --silent
, the output will not be displayed to the console.
Proxy
If you need to proxy all AWS traffic from Blambda, you have the ability to provide a proxy agent in the global options. In order to specify the proxy, you must install a proxy agent package like proxy-agent. Once installed, specify your proxy settings based on your package and set the result as the proxy
option in the global options.
const proxy = require('proxy-agent')({
/* proxy options for proxy-agent */
});
const blambda = require('blambda')({
proxy: proxy
});
S3 Bucket
In order to use Blambda, you must have an existing S3 bucket in your AWS account in which can be used for storing the artifacts (zip archive) generated by Blambda to update a function's code. This method is used to bypass the limitations of package size AWS enforces when directly pushing a ZIP file for deployment.
Name Template
The nameTemplate
option allows you to control the template used by Blambda to generate out the name of the Lambda Function created on AWS. Multiple different values are available to be used in the template as described below. By default, the name template is simply {{dirName}}
which means the generated name of the function will be the name of the directory it lives in.
The following variables are available for the name template:
env
- The current environment name fromoptions.environment
orprocess.env.NODE_ENV
.alias
- The alias name fromoptions.envMapping
that is tied to the current environment or justenv
if there is not a mapping available.dirName
- Directory name in which the function resides in.package.*
- Any available value from within package.json for the function. (ex.package.name
will be the name field in the package.json file)
Examples:
// Append environment to end of function name
{{dirName}}-{{env}}
// Use name from package.json instead
{{package.name}}
// Apply a constant text
tools-
Environment Mapping
The envMapping
option allows mapping certain environment names (ex. production, staging, test) to a specific value which is used for creating aliases for a function. This object must be defined with the keys being the environment name and the value being the desired alias name for that environment. By default, the mapping is set to:
{
development: 'dev',
staging: 'stage',
production: 'prod'
}
You may set any additional keys as desired to match the different environments you use.
For example, if your environment is set to staging
, the alias for the deploy function(s) will be set to stage
.
Exclude
Blambda gives the ability to exclude directories within the current working directory from being loaded and deployed by specifying the name of the directory in options.exclude
. If you are working on something new or have a directory that is not a Lambda Function, you can add it to the exclude array in the global options to prevent it from being deployed.
By default, all directories that match the following are excluded:
- Starts with a dot (
.
). - Does not have a
package.json
in its root.
Hooks
Hooks allow you to run a shell command at certain parts of the process which allows you to manuipulate various things outside of the Blambda process itself. Various hooks provide additional information to the command that can be templated in. Similar to options.nameTemplate
, hook commands also can be templated with various values. All hooks run in the directory of the current lambda function.
For all hooks, the following template variables are available:
options.*
- Access to the Blambda options object (global options).config.*
- Access to the function configuration object within itspackage.json
.name
- The generated name of the function.dirName
- The name of the directory in which the function resides.path
- The full path to the function.package.*
- Any available value from within package.json for the function. (ex.package.name
will be the name field in the package.json file)
Hook: beforeInstall
Shell command to run before installing the dependencies for the current function.
Additional Template Variables: None
Hook: afterInstall
Shell command to run after installing the dependencies for the current function.
Additional Template Variables: None
Hook: zip
Shell command to run after the zip archive is created for the function.
Additional Template Variables:
zip
- Absolute path the the zip file created.
Hook: beforeDeploy
Shell command to run before deploying the current function.
Additional Template Variables: None
Hook: afterDeploy
Shell command to run deploying the current function.
Additional Template Variables: None
Hook: deployComplete
Shell command to run before installing the dependencies for the current function.
Additional Template Variables: None
Params
You may specify parameters to pass into AWS.Lambda.createFunction()
when deploying a function that does not exist already. If the function does already exist, anything within the provided parameters are ignored and never updated. Blambda is for deployment, not for configuration.
See AWS.Lambda.createFunction() for a list of properties you can pass into the parameters when creating a new function. Keep in mind, you must at least provide Handler
, Role
and Runtime
in the parameters otherwise the SDK will throw an error.
Environment Variables
Some pieces of the Blambda configuration can be controlled via Environment Variables. All environment variables from the AWS SDK will work, along with the following additional variables:
NODE_ENV
- The environment in which to deploy the lambdas to.AWS_REGION
- The region of your AWS account or region to deploy to.AWS_PROFILE
- AWS profile name from~/.aws
to use for loading credentials.BLAMBDA_ARTIFACT_BUCKET
- S3 Bucket name in which to deploy the artifacts to.
Tests
To run tests locally, clone this repo and run:
npm test
License
MIT License