From c957341ef5db943becde127bc05c2a74300ae6f9 Mon Sep 17 00:00:00 2001 From: Maximilian Bosch Date: Mon, 22 Apr 2019 17:42:45 +0200 Subject: [PATCH] nixos-container: allow setting custom local and host address I have a nixops network where I deploy containers using the `container` backend which uses `nixos-container` intenrally to deploy several containers to a certain host. During that time I removed and added new containers and while trying to deploy those to a different host I realized that it isn't guaranteed that each container gets the same IP address which is a problem as some parts of the deployment need to know which container is using which IP (i.e. to configure port forwarding on the host). With this change you can specify the container's IP like this (and don't have to use the arbitrarily used 10.233.0.0/16 subnet): ``` $ nixos-container create test --config-file test-container.nix \ --local-address 10.235.1.2 --host-address 10.235.1.1 ``` --- .../administration/imperative-containers.xml | 7 ++++ .../nixos-container/nixos-container.pl | 32 ++++++++++++------- 2 files changed, 28 insertions(+), 11 deletions(-) diff --git a/nixos/doc/manual/administration/imperative-containers.xml b/nixos/doc/manual/administration/imperative-containers.xml index 9bb62bc2ece..7ded0c11786 100644 --- a/nixos/doc/manual/administration/imperative-containers.xml +++ b/nixos/doc/manual/administration/imperative-containers.xml @@ -29,6 +29,13 @@ = true; users.users.root.openssh.authorizedKeys.keys = ["ssh-dss AAAAB3N…"]; ' + + By default the next free address in the 10.233.0.0/16 subnet will be chosen + as container IP. This behavior can be altered by setting --host-address and + --local-address: + +# nixos-container create test --config-file test-container.nix \ + --local-address 10.235.1.2 --host-address 10.235.1.1 diff --git a/pkgs/tools/virtualization/nixos-container/nixos-container.pl b/pkgs/tools/virtualization/nixos-container/nixos-container.pl index a210a65f431..b5ceb522e23 100755 --- a/pkgs/tools/virtualization/nixos-container/nixos-container.pl +++ b/pkgs/tools/virtualization/nixos-container/nixos-container.pl @@ -23,7 +23,7 @@ $ENV{"NIXOS_CONFIG"} = ""; sub showHelp { print < [--nixos-path ] [--system-path ] [--config-file ] [--config ] [--ensure-unique-name] [--auto-start] [--bridge ] [--port ] + nixos-container create [--nixos-path ] [--system-path ] [--config-file ] [--config ] [--ensure-unique-name] [--auto-start] [--bridge ] [--port ] [--host-address ] [--local-address ] nixos-container destroy nixos-container start nixos-container stop @@ -48,6 +48,8 @@ my $port; my $extraConfig; my $signal; my $configFile; +my $hostAddress; +my $localAddress; GetOptions( "help" => sub { showHelp() }, @@ -59,9 +61,15 @@ GetOptions( "signal=s" => \$signal, "nixos-path=s" => \$nixosPath, "config=s" => \$extraConfig, - "config-file=s" => \$configFile + "config-file=s" => \$configFile, + "host-address=s" => \$hostAddress, + "local-address=s" => \$localAddress, ) or exit 1; +if (defined $hostAddress and !defined $localAddress or defined $localAddress and !defined $hostAddress) { + die "With --host-address set, --local-address is required as well!"; +} + my $action = $ARGV[0] or die "$0: no action specified\n"; if (defined $configFile and defined $extraConfig) { @@ -149,16 +157,18 @@ if ($action eq "create") { $usedIPs{$1} = 1 if $s =~ /^LOCAL_ADDRESS=([0-9\.]+)$/m; } - my ($ipPrefix, $hostAddress, $localAddress); - for (my $nr = 1; $nr < 255; $nr++) { - $ipPrefix = "10.233.$nr"; - $hostAddress = "$ipPrefix.1"; - $localAddress = "$ipPrefix.2"; - last unless $usedIPs{$hostAddress} || $usedIPs{$localAddress}; - $ipPrefix = undef; - } + unless (defined $hostAddress) { + my $ipPrefix; + for (my $nr = 1; $nr < 255; $nr++) { + $ipPrefix = "10.233.$nr"; + $hostAddress = "$ipPrefix.1"; + $localAddress = "$ipPrefix.2"; + last unless $usedIPs{$hostAddress} || $usedIPs{$localAddress}; + $ipPrefix = undef; + } - die "$0: out of IP addresses\n" unless defined $ipPrefix; + die "$0: out of IP addresses\n" unless defined $ipPrefix; + } my @conf; push @conf, "PRIVATE_NETWORK=1\n";