Environment variables
Environment variables are the perfect solution to configure the application (as recommended in the 12 factor guide (opens in a new tab)).
Definition
Environment variables can be defined in serverless.yml
.
To define an environment variable that will be available in all functions declare it in the provider
section:
provider:
# ...
environment:
MY_VARIABLE: 'my value'
To define an environment variable that will be available in a specific function declare it inside the function's properties:
functions:
foo:
# ...
environment:
MY_VARIABLE: 'my value'
Do not store secret values in serverless.yml
directly. Check out the next section to handle secrets.
Secrets
Secrets (API tokens, database passwords, etc.) should not be defined in serverless.yml
or committed into your git repository.
Instead, you can use the SSM parameter store (opens in a new tab), a free service provided by AWS.
Creating secrets
To create a parameter, you can do it via the AWS SSM console (opens in a new tab) or the Bref Dashboard (opens in a new tab):
You can also do it in the CLI via the following command:
aws ssm put-parameter --region us-east-1 --name '/my-app/my-parameter' --type String --value 'mysecretvalue'
On Windows, the first part of the path needs to be double slashes and all subsequent forward slashes changed to backslashes:
aws ssm put-parameter --region us-east-1 --name '//my-app\my-parameter' --type String --value 'mysecretvalue'
It is recommended to prefix the parameter name with your application name, for example: /my-app/my-parameter
.
SSM also allows to store a SecureString parameter, which is encrypted with AWS KMS. To use a SecureString, simply change the --type
argument to --type SecureString
. Bref takes care of decrypting the value.
Retrieving secrets
You can inject a secret in an environment variable:
- either at deployment time (simplest)
- or at runtime (more secure)
At deployment time
Use the ${ssm:<parameter>}
syntax (opens in a new tab) to have the variable be replaced by the secret value on deployment:
provider:
# ...
environment:
MY_PARAMETER: ${ssm:/my-app/my-parameter}
# If you need to set a different value per stage:
OTHER_PARAMETER: ${ssm:/my-app/${sls:stage}/my-parameter}
Advantages:
- Simpler, it just works.
Disadvantages:
- The user deploying must be allowed to retrieve the secret value.
- The secret value will be set in clear text in the Lambda function configuration (anyone who can access the function can also view the value).
At runtime
Alternatively, Bref can fetch the secret values at runtime when the Lambda function starts (aka the "cold start"). To use that feature, we must install the bref/secrets-loader
package:
composer require bref/secrets-loader
To use it, the environment variable should contain the path to the SSM parameter prefixed with bref-ssm:
. We also need to authorize Lambda to retrieve the parameter. For example:
provider:
# ...
environment:
MY_PARAMETER: bref-ssm:/my-app/my-parameter
iam:
role:
statements:
# Allow our Lambda functions to retrieve the parameter from SSM
- Effect: Allow
Action: ssm:GetParameters
Resource: 'arn:aws:ssm:${aws:region}:${aws:accountId}:parameter/my-app/my-parameter'
# If you want to be more generic you can uncomment the line below instead.
# But it authorizes retrieving *any* SSM parameter, which is less secure.
#Resource: '*'
On a cold start, Bref automatically checks all environment variables that start with bref-ssm:
and will resolve the values by calling the AWS SSM API. It adds a very small latency overhead for the first request (note: all SSM values are fetched in a single API call).
Advantages:
- The value doesn't have to be accessible by the user deploying.
- The value is not stored in plain text in the AWS console.
Disadvantages:
- More complex configuration.
- Small added latency to cold starts.
An alternative: AWS Secrets Manager
As an alternative, you can store secrets in AWS Secrets Manager (opens in a new tab). This solution, while very similar to SSM, will provide:
- better permission management using IAM
- JSON values, allowing to store multiple values in one parameter
However, Secrets Manager is not free: pricing details (opens in a new tab).
SSM is good enough for most projects.
Local development
When developing locally using serverless bref:local
, you can set environment variables using bash:
VAR1=val1 VAR2=val2 serverless bref:local -f <function>
# Or using `export`:
export VAR1=val1
export VAR2=val2
serverless bref:local -f <function>
Learn more
While this page mentions environment variables, serverless.yml
allows other types of variables to be used.
Read the serverless.yml
variables (opens in a new tab) documentation to learn more.