/creds_env

A Ruby gem to support familiar dotenv ENV style, backed by the more secure Rails 6+ credentials approach

Primary LanguageRubyMIT LicenseMIT

CredsEnv

This little gem converts certain key/values pairs from Rails credentials to ENV variables for you before a Rails application loads.

creds_env aims to:

  • help you embrace Rails 6+ credentials management system (if you don't think it's better than sharing .env.* files outside Git, see if this this great article has a good point or two).
  • maintain the popular dotenv style coding with ENV["SOME_KEY"] because it's shorter (than Rails.application.credentials) and familiar with developers of most frameworks.

demo

Installation

Add to Gemfile

gem "creds_env", require: "creds_env/rails"

NOTE: the require: "creds_env/rails" part enables autoloading (inspired by dotenv). You can load manually instead with CredsEnv.load.

Then install

$ bundle install

Check past versions at https://rubygems.org/gems/creds_env

Usage

Any ALL_CAPS key names in your encrpted credentials will be copied over as ENV vars.

For example:

$ bin/rails credentials:edit

Use CAPS for variables reference as ENV var, such as ENV["SOME_KEY"]. For example, add AWS_ACCESS_KEY_ID, DATABASE_URL like this:

# content of config/credentials.yml.enc when decrypted:
---
secret_key_base: secret123 # generated by rails
AWS_ACCESS_KEY_ID: abc123
DATABASE_URL: postgres://localhost:5432/example_development

Check in bin/rails console:

ENV["secret_key_base"] # => nil it's not in CAPS
ENV["AWS_ACCESS_KEY_ID"] # => abc123
ENV["DATABASE_URL"] # => postgres://localhost:5432/example_development

FAQs

How does it help with the development environment?

Do you miss sharing files like .env.local or making devs fill out values from a .env.sample file? I guess not! How about using Rails 6 encrypted credentials and share a single key: the uncommitted master.key file. All API keys are encrypted and version controlled in Git.

How does it help with deployed apps in staging / production environments?

I missed the ENV style syntax, still made popular by libraries like dotenv. However, managing .env.* files on the server is an anti-pattern. Now, the only key needed is setting ENV["RAILS_MASTER_KEY"] or create a config/credentials/production.key file with the content of that key (the Rails Way™️)

Is this approach best practices though?

It brings two popular practices together:

  • The single-key credentials (vault) approach: it is safe to stick with the Rails way which will evolve over time. See https://www.envkey.com/ for a service that tries to do the same thing.
  • The ENV approach: developers (familiar with Rails or not) still find using Rails.application.credentials.dig(:aws, :access_key_id) too cumbersome. Why not reference like most apps with ENV["AWS_ACCESS_KEY_ID"], or even ENV.fetch("DATABASE_URL") for null checking.

Credits

This gem's test code was inspired by:

Development

  1. Clone from this repo or a forked one
  2. Run bin/setup to install dependencies
  3. Run bin/rake to run tests
  4. Optional: experiment with bin/console

Check out *_spec.rb files.

Contributing

Bug reports and pull requests are welcome on GitHub.com/harley/creds_env. This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the code of conduct.

License

The gem is available as open source under the terms of the MIT License.