Only building with node 8
With aws-secrets you can safely store, version, and use secrets by leveraging AWS Key Managment Store.
- You put your secrets in a JSON file (other formats like YAML are fine too but require a parser to be supplied to the application).
- Use the CLI to encrypt that file
- Include the encrypted data in your source repository alongside your source code. You only need to decrypt that file back to disk when you need to make changes.
- At runtime, use aws-secrets to access your unencrypted secrets without writing them to the filesystem.
Only AWS users with access to your Key Management Store master key will be able to access the unencrypted secrets.
npm install aws-secrets --save
Before you can use the module, you need to have set in place several things:
-
Install the AWS CLI and configure it so that you can access your AWS account. Running
aws s3 ls
is a reasonable way to verify it is properly configured, assuming you are authorized to perform that operation.- Set the AWS_REGION environment variable if using the AWS CLI
-
Create a master key in the AWS Key Management Service. Keys are region-specific, so be sure you create the key in the same region you intend to encrypt and decrypt secrets. Note that you cannot use the keys created automatically by AWS for securing services. Copy the ARN or the id of the key, which you will need later. To view your keys, find them in IAM under the section titled Encryption keys.
Using this module involves both the command line and code:
- Put your secrets in a JSON file--say
.secrets.json
. For example:
{
"github": {
"username": "stevie",
"password": "albertistheman"
},
"foo": {
"bar": {
"key": "qwerty"
}
}
};
- Add encrypt and decrypt scripts to your package.json scripts section:
"encrypt": "aws-secrets encrypt-file .secrets.json secrets.txt -k $npm_package_kmsKey && rm .secrets.json",
"decrypt": "aws-secrets decrypt-file secrets.txt .secrets.json"
- Put the ARN of your encryption key in package.json:
"kmsKey": "<YOUR KEY HERE>"
- Encrypt the secrets file using the cli:
npm run encrypt
- Include the encrypted file (secrets.json in this example) in your source control project as a versioned file. For example:
git add secrets.json
-
Ignore the unencrypted file so that you do not accidentally add and commit it to your repo. If you are using git, this means adding .secrets.js to the
.gitignore
file. -
Put your non-sensitive configuration into an object. For sensitive data, refer to the object path in the secrets object, preceded by 'secrets@':
// config.js
module.exports = {
githubEndpoint: {
uri: 'https://www.github.com',
username: '[email protected]',
password: '[email protected]'
}
foobarkey: '[email protected]'
}
Use the AwsSecrets object to decrypt and apply the secrets to your configuration object:
const AwsSecrets = require('aws-secrets');
const config = require('./config');
const P = require('bluebird');
const fs = P.promisifyAll(require('fs'));
...
const awsSecrets = new AwsSecrets()
return fs.readFileAsync('secrets.json')
.then(secrets => {
return awsSecrets.applySecrets(secrets, config);
})
...
If you aren't using JSON, you can supply your own parser function as an option:
const yaml = require('js-yaml');
...
return fs.readFileAsync('secrets.yaml')
.then(secrets => {
return awsSecrets.applySecrets(secrets, config, { parseFunction: yaml.safeLoad });
})
The return value has this value:
// config.js
module.exports = {
githubEndpoint: {
uri: 'https://www.github.com',
username: 'stevie',
password: 'albert-is-the-man'
},
foobarkey: 'qwerty'
}
The only time you need to decrypt the secrets and save to a file is when you need to change them. To do that, use the command line:
npm decrypt-file secrets.json .secrets.json
.secrets.json
will now contain the unencrypted version of your secrets. Make your changes and then run the encrypt-file
command as you did when you initially created the secrets.
See the example project for a concrete usage example.
Secrets are encrypted and stored in base64 format. At runtime, this file is decrypted in memory and referenced by the configuration values.
Encryption keys are managed by AWS Key Management Store and all authentication/authorization happens through that. As a consequence, any operation requiring encryption or decryption (i.e., runtime, developer edits) will require you to provide credentials to access the AWS KMS master key.
Note that KMS keys can only be used to encrypt up to 4KiB of data. If your config file is longer than that, you will need to use envelope encryption, which is not currently supported by aws-secrets.
We are using semantic-release with AngularJS Git Commit Message conventions. Please ensure you use that commit message format so that publishing happens as needed. We recommend using commitizen for that.