How to use Erlang application release with multiple configurations

On my opinion configuring and building releases for an Erlang applications has always been the most obscure and mis-understood part of Erlang ecosystem. For me personally, to build a release would always take a day or two because I could never set all the settings correctly in reltool.config and erlang release invariably failed with the most un-helpful error message.

The only Erlang book which explained in details how Erlang releases were supposed to work was Erlang and OTP in Action

Fortunately, one of the authors of this book, Eric Merritt, wrote a great tool relax and building releases became much simpler. Eric gave a talk about it. If you use Erlang you definitely need to check Relx, it will make you life much easier.

But some issues still remained. Relx.config allows you to specify sys.config and vm.args files for your release that set the configurations for VM (e.g. a name of the node , -sname or -name, cookie, etc) and some of these settings were not possible to change if you wanted to run multiple instances of your release. E.g. overriding -name parameter via command line argument wasn’t possible.

This was massively inconvenient  as you would need to build multiple releases of your application if, for example, you needed to run a cluster of several nodes. In this case you would use overlays in rebar.config to override some params of the release and generate a separate release for each node. Example of such configuration you can find here.

Tristan Sloughter fixed this issue with one of his many additions to relx.

His solution (which is unfortunately not documented in relx official documentation yet) makes use of additional env var $RELX_REPLACE_OS_VARS. If this var is set to true, the application start up script generated with relx will replace placeholders in vm.args and sys.config files with values of env variables which match the values of placeholders. It will then create vm2.args and sys2.config (with replaced placeholders values) and start your application with these config files instead of original ones. This allows you to run the same release with multiple configs and override settings for PROD and QA for example.

for example if you want to override the name of the node and the cookie:

in your relx.config you need to have the following option:

{extended_start_script, true}.

is your vm.args you add placeholders that you want to replace:

-name ${NODE_NAME}
-cookie ${COOKIE}

then in your start-prod.sh file

export RELX_REPLACE_OS_VARS=true
export NODE_NAME=node_prod
export COOKIE=prod
exec _rel/your_app/bin/your_app foreground "$@"

and in start-qa.sh file

export RELX_REPLACE_OS_VARS=true
export NODE_NAME=node_qa
export COOKIE=qa
exec _rel/your_app/bin/your_app foreground "$@"

make sure you generate your release with at least 1.1.0 version of relx.

Kudos to Tristan for this great solution, I asked the question on this Issue, otherwise I might’ve never found this override.

Advertisements
This entry was posted in Uncategorized. Bookmark the permalink.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s