如何部署含敏感配置的Rails项目到Heroku?(使用Settingslogic gem)
Hey there! Let's work through getting your Settingslogic setup running smoothly on Heroku without committing your sensitive application.yml to Git. Here are two solid solutions:
Option 1: Use Heroku Config Vars to Replace Local YAML Values
Heroku doesn't persist files you create via Bash (each deployment spins up a fresh container, so those files vanish). Instead, we can map your application.yml values to Heroku's environment variables, then tweak Settingslogic to prioritize these vars.
Push your sensitive values to Heroku Config Vars
For every key in yourproductionsection ofapplication.yml, run this command locally:heroku config:set PRODUCTION_API_KEY=your_secret_key PRODUCTION_DB_URL=your_db_connection_stringMatch the variable names to your YAML keys (adding a
PRODUCTION_prefix helps avoid conflicts).Update your Settingslogic config to read from env vars
Open your Settingslogic definition file (usuallyconfig/settings.rb) and override the values to pull from environment variables first, falling back to your local YAML for development:class Settings < Settingslogic source Rails.root.join('config', 'application.yml') namespace Rails.env # Override individual keys to use env vars in production def api_key ENV["PRODUCTION_API_KEY"] || super end def database_url ENV["PRODUCTION_DB_URL"] || super end # Repeat for all sensitive keys in your YAML endThis way, local development uses your
application.yml, while Heroku pulls directly from its secure config vars.
Option 2: Dynamically Generate application.yml During Deployment
If you prefer keeping the YAML structure, you can generate the file on Heroku during each deploy using your config vars.
Add all sensitive values to Heroku Config Vars
Same as step 1 in Option 1—get all your production YAML keys into Heroku's environment variables.Create a deployment script to generate the YAML
Make a new filebin/generate_application_yml.rbwith this content:#!/usr/bin/env ruby require 'yaml' production_config = { api_key: ENV['PRODUCTION_API_KEY'], database_url: ENV['PRODUCTION_DB_URL'] # Add all your YAML keys here } config_content = { Rails.env => production_config }.to_yaml File.write(Rails.root.join('config', 'application.yml'), config_content)Make the script executable and set it to run on deploy
Run this locally to set permissions:chmod +x bin/generate_application_yml.rbThen update your
Procfileto include a release phase that runs the script:release: bin/generate_application_yml.rb web: bundle exec puma -C config/puma.rbCommit this script and updated
Procfileto Git—since it only reads env vars, there's no sensitive data in it.
Why Your Previous Attempt Failed
When you created application.yml via Heroku Bash, that file lived only in the temporary container you were connected to. Heroku rebuilds its containers from scratch on every git push, so any files not tracked in your Git repo get wiped. This is intentional behavior to keep deployments consistent.
内容的提问来源于stack exchange,提问作者Ruslan Valeev

