1 { config, lib, pkgs, ... }:
3 cfg = config.services.rabbitmq;
5 inherit (builtins) concatStringsSep;
7 config_file_content = lib.generators.toKeyValue { } cfg.configItems;
8 config_file = pkgs.writeText "rabbitmq.conf" config_file_content;
10 advanced_config_file = pkgs.writeText "advanced.config" cfg.config;
16 (lib.mkRemovedOptionModule [ "services" "rabbitmq" "cookie" ] ''
17 This option wrote the Erlang cookie to the store, while it should be kept secret.
18 Please remove it from your NixOS configuration and deploy a cookie securely instead.
19 The renamed `unsafeCookie` must ONLY be used in isolated non-production environments such as NixOS VM tests.
26 enable = lib.mkOption {
27 type = lib.types.bool;
30 Whether to enable the RabbitMQ server, an Advanced Message
31 Queuing Protocol (AMQP) broker.
35 package = lib.mkPackageOption pkgs "rabbitmq-server" { };
37 listenAddress = lib.mkOption {
38 default = "127.0.0.1";
41 IP address on which RabbitMQ will listen for AMQP
42 connections. Set to the empty string to listen on all
43 interfaces. Note that RabbitMQ creates a user named
45 `guest` by default, so you should delete
46 this user if you intend to allow external access.
48 Together with 'port' setting it's mostly an alias for
49 configItems."listeners.tcp.1" and it's left for backwards
50 compatibility with previous version of this module.
58 Port on which RabbitMQ will listen for AMQP connections.
60 type = lib.types.port;
63 dataDir = lib.mkOption {
64 type = lib.types.path;
65 default = "/var/lib/rabbitmq";
67 Data directory for rabbitmq.
71 unsafeCookie = lib.mkOption {
75 Erlang cookie is a string of arbitrary length which must
76 be the same for several nodes to be allowed to communicate.
77 Leave empty to generate automatically.
79 Setting the cookie via this option exposes the cookie to the store, which
80 is not recommended for security reasons.
81 Only use this option in an isolated non-production environment such as
86 configItems = lib.mkOption {
88 type = lib.types.attrsOf lib.types.str;
89 example = lib.literalExpression ''
91 "auth_backends.1.authn" = "rabbit_auth_backend_ldap";
92 "auth_backends.1.authz" = "rabbit_auth_backend_internal";
96 Configuration options in RabbitMQ's new config file format,
97 which is a simple key-value format that can not express nested
98 data structures. This is known as the `rabbitmq.conf` file,
99 although outside NixOS that filename may have Erlang syntax, particularly
100 prior to RabbitMQ 3.7.0.
102 If you do need to express nested data structures, you can use
103 `config` option. Configuration from `config`
104 will be merged into these options by RabbitMQ at runtime to
105 form the final configuration.
107 See https://www.rabbitmq.com/configure.html#config-items
108 For the distinct formats, see https://www.rabbitmq.com/configure.html#config-file-formats
112 config = lib.mkOption {
114 type = lib.types.str;
116 Verbatim advanced configuration file contents using the Erlang syntax.
117 This is also known as the `advanced.config` file or the old config format.
119 `configItems` is preferred whenever possible. However, nested
120 data structures can only be expressed properly using the `config` option.
122 The contents of this option will be merged into the `configItems`
123 by RabbitMQ at runtime to form the final configuration.
125 See the second table on https://www.rabbitmq.com/configure.html#config-items
126 For the distinct formats, see https://www.rabbitmq.com/configure.html#config-file-formats
130 plugins = lib.mkOption {
132 type = lib.types.listOf lib.types.str;
133 description = "The names of plugins to enable";
136 pluginDirs = lib.mkOption {
138 type = lib.types.listOf lib.types.path;
139 description = "The list of directories containing external plugins";
143 enable = lib.mkEnableOption "the management plugin";
144 port = lib.mkOption {
146 type = lib.types.port;
148 On which port to run the management plugin
156 ###### implementation
157 config = lib.mkIf cfg.enable {
159 # This is needed so we will have 'rabbitmqctl' in our PATH
160 environment.systemPackages = [ cfg.package ];
162 services.epmd.enable = true;
164 users.users.rabbitmq = {
165 description = "RabbitMQ server user";
166 home = "${cfg.dataDir}";
169 uid = config.ids.uids.rabbitmq;
172 users.groups.rabbitmq.gid = config.ids.gids.rabbitmq;
174 services.rabbitmq.configItems = {
175 "listeners.tcp.1" = lib.mkDefault "${cfg.listenAddress}:${toString cfg.port}";
176 } // lib.optionalAttrs cfg.managementPlugin.enable {
177 "management.tcp.port" = toString cfg.managementPlugin.port;
178 "management.tcp.ip" = cfg.listenAddress;
181 services.rabbitmq.plugins = lib.optional cfg.managementPlugin.enable "rabbitmq_management";
183 systemd.services.rabbitmq = {
184 description = "RabbitMQ Server";
186 wantedBy = [ "multi-user.target" ];
187 after = [ "network.target" "epmd.socket" ];
188 wants = [ "network.target" "epmd.socket" ];
192 pkgs.coreutils # mkdir/chown/chmod for preStart
196 RABBITMQ_MNESIA_BASE = "${cfg.dataDir}/mnesia";
199 RABBITMQ_CONFIG_FILE = config_file;
200 RABBITMQ_PLUGINS_DIR = lib.concatStringsSep ":" cfg.pluginDirs;
201 RABBITMQ_ENABLED_PLUGINS_FILE = pkgs.writeText "enabled_plugins" ''
202 [ ${lib.concatStringsSep "," cfg.plugins} ].
204 } // lib.optionalAttrs (cfg.config != "") { RABBITMQ_ADVANCED_CONFIG_FILE = advanced_config_file; };
207 ExecStart = "${cfg.package}/sbin/rabbitmq-server";
208 ExecStop = "${cfg.package}/sbin/rabbitmqctl shutdown";
211 LogsDirectory = "rabbitmq";
212 WorkingDirectory = cfg.dataDir;
214 NotifyAccess = "all";
216 LimitNOFILE = "100000";
217 Restart = "on-failure";
219 TimeoutStartSec = "3600";
223 ${lib.optionalString (cfg.unsafeCookie != "") ''
224 install -m 600 <(echo -n ${cfg.unsafeCookie}) ${cfg.dataDir}/.erlang.cookie