Extend NixOS: Difference between revisions

imported>Mic92
imported>Mic92
Remove multiple daemons (I don't know how the systemd variant would look like)
Line 178: Line 178:
   
   
   # ... usual configuration ...
   # ... usual configuration ...
}
</syntaxhighlight>
== Multiple Daemons ==
Now, suppose your server has multiple people as users, and each wants the same IRC client running in background. One possibility is to replace the user name with a list of user names.  A better solution, for this tutorial, is to '''extend''' the <code>jobs</code> option. This will allow us to add "IRC jobs", each of which is for a specific user. This should create configuration options like this:
<syntaxhighlight lang="nix">
jobs.ircClient.user  = "User1";
jobs.ircClient.enable = true;
</syntaxhighlight>
The following code will add more options inside the <code>jobs.<name></code> option. This code is quite advanced, using many concepts from functional language paradigm.
<syntaxhighlight lang="nix">
{config, pkgs, ...}:
let
  # Function which indicates whether the configuration defines any ircClient.
  anyIrcClient = with pkgs.lib;
    fold (j: v: v || j.ircClient.enable) (attrValues config.jobs);
in
with pkgs.lib;
{
  options = {
    # Add options to "jobs".
    jobs.options = {config, ...}: let
      cfg = config.ircClient;
    in {
      # The attributes in this set will merge into "jobs" set.
      options = {
       
        # Add "ircClient.enable" to "jobs" set of options.
        ircClient.enable = mkOption {
          default = false;
          type = with types; bool;
          description = ''
            Start an irc client for a user.
          '';
        };
        # Add "ircClient.user" to "jobs" set of options.
        ircClient.user = mkOption {
          default = "username";
          type = with types; uniq string;
          description = ''
            Name of the user.
          '';
        };
      };
      config = mkIf cfg.enable {
        description = "Start the irc client of ${cfg.user}.";
        startOn = "started network-interfaces";
        exec = ''/var/setuid-wrappers/sudo -u ${cfg.user} -- ${pkgs.screen}/bin/screen -m -d -S irc ${pkgs.irssi}/bin/irssi'';
      };
    };
  };
  # Execute this code if this configuration defined any ircClient.
  config = mkIf anyIrcClient {
    environment.systemPackages = [ pkgs.screen ];
  };
  }
  }
</syntaxhighlight>
</syntaxhighlight>