Skip to content

Instantly share code, notes, and snippets.

@kjkuan
Created June 25, 2020 17:56
Show Gist options
  • Save kjkuan/5c9af5b2592048551654bf0c35d48616 to your computer and use it in GitHub Desktop.
Save kjkuan/5c9af5b2592048551654bf0c35d48616 to your computer and use it in GitHub Desktop.
An alternative implementation of heroku's start-stunnel script that works for rails console
#!/usr/bin/env bash
#
# This script builds on top of Heroku's stunnel wrapper script [1]
# and provides a simplified implementation with fewer moving parts,
# fewer processes, and most importantly, one that works well with
# any commands being wrapped.
#
# To use this wrapper, make sure you've installed the stunnel redis buildpack,
# then simply prefix the command you wish to run with it.
#
# 'Procfile' example:
#
# web: bin/with-stunnel bundle exec puma
#
# 'heroku run' example:
#
# $ heroku run -a myapp-staging 'export REDIS_STUNNEL_URLS="MY_REDIS_URL"; bin/with-stunnel rails console'
#
# NOTE: It's recommended that you set the REDIS_STUNNEL_URLS config
# var for your Heroku app to ensure that the correct Redis URLs
# will be proxied.
#
# [1](https://github.com/heroku/heroku-buildpack-redis/blob/master/bin/start-stunnel)
#
# Re-use Heroku's start-stunnel script.
# We only care about the config-gen() and the main() functions there.
#
if [[ -e bin/start-stunnel ]]; then
source bin/start-stunnel
else # assume the stunnel redis buildpack is not installed.
exec "$@"
fi
# Re-define the run-stunnel function to work around the issue with
# running commands that reads from stdin (e.g., 'rails console'),
# and to simplify the implementation.
#
run-stunnel () {
# Generate stunnel config files and update redis url env vars
config-gen
# Start stunnel in a subshell and wait for it to terminate, after which
# we kill the wrapped command process.
(
stunnel4 vendor/stunnel/stunnel.conf < /dev/null
kill -SIGTERM -$$
# NOTE: $$ expands to the PID of this process (with-stunnel)
) &
exec "$@"
#
# NOTE: If the wrapped command (this process) exits, then Heroku sends
# SIGTERM to all processes, and the dyno terminates.
#
}
main "$@"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment