[Nix-dev] NixOS require attribute

Nicolas Pierron nicolas.b.pierron at gmail.com
Mon May 9 23:49:08 CEST 2011


Hi,

On Mon, May 9, 2011 at 14:37, Sander van der Burg - EWI
<S.vanderBurg at tudelft.nl> wrote:
> I have already thought about splitting the database and webserver parts into
> separate files, but I need some function arguments that I can pass to those
> portions, such as the administrator address and authentication stuff.

A module correspond to one concern, of course you need some parameters
to setup the webserver or the database.  The value of the parameters
depends on how the service would be used, but the presence of the
parameter is inherent to the service.  Thus, each parameter has to be
part of the interface provided by the service.  Parameters are later
configured inside another module.webserver or the database

With option declarations, you can declare that an option (parameter)
exists, and assume its value when you are configuring your service.

> Basically, the function I'm writing looks like this (I've simplified it a
> bit):
>
> {adminAddr, ...}:
>
> let
>   webserver = {pkgs, ...}:
>
>   {
>     services.httpd.enable = true;
>     services.httpd.
>   };
>   in
> {
>   machine1 = {pkgs, ...}:
>
>   {
>     require = [ webserver ];
>   };
>
>   machine2 = {pkgs, ...}:
>
>   {
>     require = [ webserver ];
>   };
> }
>
> Any ideas/suggestions, how I can pass the adminAddr to the webserver portion
> and include them into each configuration?

------------------ webserver.nix
{config, pkgs, ...}:

let cfg = config.services.webserver; in
with pkgs.lib;

{
  options = {
    services.webserver.enable = mkOption { /* ... */ };
    services.webserver.adminAddr = mkOption {
      # ...
    };
  };

  config = mkIf cfg.enable {
    services.httpd.enable = true;
    services.httpd.adminAddr = cfg.AdminAddr;
  };
}

----------------- machine1.nix
{
  # not enabled, but needed because we define option declared in it.
  require = [ ./webserver.nix ];

  services.webserver.adminAddr = "a.a at a.a";
}

----------------- machine2.nix
{
  require = [ ./webserver.nix ];

  services.webserver.enable = true;
  services.webserver.adminAddr = "a.a at a.a";
}


> -----Original Message-----
> From: Nicolas Pierron [mailto:nicolas.b.pierron at gmail.com]
> Sent: Mon 5/9/2011 1:15 PM
> To: Sander van der Burg - EWI
> Cc: nix-dev at cs.uu.nl
> Subject: Re: [Nix-dev] NixOS require attribute
>
> Hi,
>
> On Mon, May 9, 2011 at 12:19, Sander van der Burg - EWI
> <S.vanderBurg at tudelft.nl> wrote:
>> It seems that it is only possible to specify files in the require
>> attribute
>> of a Nix module, e.g.:
>>
>> {pkgs, ...}:
>>
>> {
>>   require = [ /some/nixos/module/file.nix ]; # Works fine
>>
>>   services.openssh.enable = true;
>> }
>>
>> But it seems that it is impossible to specify functions or attribute sets,
>> e.g.:
>>
>> {pkgs, ...}:
>>
>> {
>>   require = [ { services.httpd.enable = true; } ]; # Triggers an error
>>
>>   services.openssh.enable = true;
>> }
>
> This is a feature, in fact the error message you are getting should
> look like "Option definitions used inside option declaration section".
>  The reason was to accept old modules which are still written in the
> syntax of the previous module system.  The syntax was to declare
> options as a separated attribute set which was added in the require
> list.  The code which unifies module syntax makes the assumption that
> only one attribute set is used in the require attribute and that it
> contains only option declarations.
>
> The plan was to remove such possibilities in the future because this
> we cannot provide good error messages out of such expression due to:
>
> {pkgs, ...}:
>
> {
>   require = [ (import /some/nixos/module/file.nix) ];
>
>   services.openssh.enable = true;
> }
>
>> I'm curious whether it is possible to also require functions or attribute
>> sets. The reason I'm asking this is, that I'm working on a function that
>> generates a network of NixOS configurations running web applications. In
>> some cases you may want to run a database server and web server on a
>> single
>> machine, in other cases you may want to run a database and web server on
>> separate machines.
>
> It could be possible, but doing so will prevent the usage of good file
> location in the error messages.
>
>> I think using the require attribute is the best way to combine certain
>> properties into a single NixOS configuration.
>
> The require is indeed the best and only way to combine separated
> concerns into a NixOS configuration, but you cannot use attribute sets
> in them, and even if you would be able, the error reports would get
> worst.
>
> {pkgs, ...}:
>
> {
>   require = [ ./database.nix ./webserver.nix ];
>
>   services.openssh.enable = true;
> }
>
> So the question is how hard is it to generate multiple files, and
> should we accept attribute sets even if we get poor error messages?  I
> don't think this goes to the right direction.
>
> --
> Nicolas Pierron
> http://www.linkedin.com/in/nicolasbpierron - http://nbp.name/
>
>



-- 
Nicolas Pierron
http://www.linkedin.com/in/nicolasbpierron - http://nbp.name/



More information about the nix-dev mailing list