Jump to content

Docker: Difference between revisions

→‎Using Nix in containers: - NixOS in containers using Arion
imported>Vater
(→‎Using Nix in containers: - NixOS in containers using Arion)
 
(33 intermediate revisions by 20 users not shown)
Line 1: Line 1:
{{Expansion|This article is incomplete.}}
[https://docker.com Docker] is a utility to pack, ship and run any application as a lightweight container.  


== Enabling the docker service ==
= Docker on NixOS =


Inside your <code>configuration.nix</code>:
== Installation ==
 
To install docker, add the following to your your NixOS configuration:


<syntaxHighlight lang=nix>
<syntaxHighlight lang=nix>
{
virtualisation.docker.enable = true;
  ...
  virtualisation.docker.enable = true;
  ...
}
</syntaxHighlight>
</syntaxHighlight>


Line 16: Line 14:


Adding users to the <code>docker</code> group will provide them access to the socket:
Adding users to the <code>docker</code> group will provide them access to the socket:
<syntaxHighlight lang=nix>
users.users.<myuser>.extraGroups = [ "docker" ];
</syntaxHighlight>
If you prefer, you could achieve the same with this:
<syntaxHighlight lang=nix>
users.extraGroups.docker.members = [ "username-with-access-to-socket" ];
</syntaxHighlight>
If you're still unable to get access to the socket, you might have to re-login or reboot.
{{Warning|Beware that the docker group membership is effectively [https://github.com/moby/moby/issues/9976 equivalent to being root]! <br> Consider using rootless mode below.}}
Note: If you use the [[btrfs]] filesystem, you might need to set the storageDriver option:
<syntaxHighlight lang=nix>
virtualisation.docker.storageDriver = "btrfs";
</syntaxHighlight>
=== Rootless docker ===
To use docker in [https://docs.docker.com/engine/security/rootless/ rootless mode], you can activate the <code>rootless</code> option:
<syntaxHighlight lang=nix>
virtualisation.docker.rootless = {
  enable = true;
  setSocketVariable = true;
};
</syntaxHighlight>
The <code>setSocketVariable</code> option sets the <code>DOCKER_HOST</code> variable to the rootless Docker instance for normal users by default.
=== Changing Docker Daemon's Data Root ===
By default, the Docker daemon will store images, containers, and build context on the root filesystem.
If you want to change the location that Docker stores its data, you can configure a new <code>data-root</code> for the daemon by setting the <code>data-root</code> property of the [https://search.nixos.org/options?show=virtualisation.docker.daemon.settings&from=0&size=50&sort=alpha_asc&type=packages&query=virtualisation.docker <code>virtualisation.docker.daemon.settings</code>].
<syntaxHighlight lang=nix>
virtualisation.docker.daemon.settings = {
  data-root = "/some-place/to-store-the-docker-data";
};
</syntaxHighlight>
== Docker Containers as systemd Services ==
To make sure some docker containers are running as systemd services, you can use 'oci-containers':
<syntaxHighlight lang=nix>
virtualisation.oci-containers = {
  backend = "docker";
  containers = {
    foo = {
      # ...
    };
  };
};
</syntaxHighlight>
See https://mynixos.com/options/virtualisation.oci-containers.containers.%3Cname%3E for further options
=  Creating images =
== Building a docker image with nixpkgs ==
There is an entry for [https://nixos.org/nixpkgs/manual/#sec-pkgs-dockerTools dockerTools] in the nixpkgs manual for reference.
In the linked page they give the following example config:
<syntaxHighlight lang=nix>
<syntaxHighlight lang=nix>
{
buildImage {
   users.users.<myuser>.extraGroups = [ "docker" ];
   name = "redis";
  tag = "latest";
 
  fromImage = someBaseImage;
  fromImageName = null;
  fromImageTag = "latest";
 
  copyToRoot = pkgs.buildEnv {
    name = "image-root";
    paths = [ pkgs.redis ];
    pathsToLink = [ "/bin" ];
  };
 
  runAsRoot = ''
    #!${pkgs.runtimeShell}
    mkdir -p /data
  '';
 
  config = {
    Cmd = [ "/bin/redis-server" ];
    WorkingDir = "/data";
    Volumes = { "/data" = { }; };
  };
 
  diskSize = 1024;
  buildVMMemorySize = 512;
}
}
</syntaxHighlight>
</syntaxHighlight>
{{note|
'''BEWARE''' that the docker group membership is effectively [https://github.com/moby/moby/issues/9976 equivalent to being root]!
}}


== Building a docker image with nixpkgs ==
More examples can be found in the [https://github.com/NixOS/nixpkgs/blob/master/pkgs/build-support/docker/examples.nix nixpkgs] repo.
 
Also check out the excellent article by [https://lucabrunox.github.io/2016/04/cheap-docker-images-with-nix_15.html lethalman] about building minimal docker images with nix.
 
=== Reproducible image dates ===


There is [https://nixos.org/nixpkgs/manual/#sec-pkgs-dockerTools an entry for dockerTools in the nixpkgs manual] for reference.
The manual advises against using <code>created = "now"</code>, as that prevents images from being reproducible.
In the nixpkgs repo some [https://github.com/NixOS/nixpkgs/blob/master/pkgs/build-support/docker/examples.nix examples] can be found.


Also check out the excellent article by lethalman about [http://lethalman.blogspot.de/2016/04/cheap-docker-images-with-nix_15.html building minimal docker images with nix].  
An alternative, if using [[flakes]], is to do <code>created = builtins.substring 0 8 self.lastModifiedDate</code>, which uses the commit date, and is therefore reproducible.


== How to calculate the <code>sha256</code> of a pulled image ==
=== How to calculate the <code>sha256</code> of a pulled image ===


The <code>sha256</code> argument of the <code>dockerTools.pullImage</code> function is the checksum of the archive generated by Skopeo. Since the archive contains the name and the tag of the image, Skopeo arguments used to fetch the image have to be identical to those used by the <code>dockerTools.pullImage</code> function.
The <code>sha256</code> argument of the <code>dockerTools.pullImage</code> function is the checksum of the archive generated by Skopeo. Since the archive contains the name and the tag of the image, Skopeo arguments used to fetch the image have to be identical to those used by the <code>dockerTools.pullImage</code> function.
Line 59: Line 149:
</syntaxHighlight>
</syntaxHighlight>


== Container images with nix ==
=== Directly Using Nix in Image Layers ===


While [https://nixos.org/manual/nixpkgs/stable/#sec-pkgs-dockerTools <code>dockerTools</code>] allows to build lightweight containers, it requires <code>nix</code> to be installed on the host system. An alternative are [https://github.com/LnL7/nix-docker docker images] with nix preinstalled, maintained by LnL7.
Instead of copying Nix packages into Docker image layers, Docker can be configured to directly utilize the <code>nix-store</code> by integrating with [https://github.com/pdtpartners/nix-snapshotter nix-snapshotter].
 
This will significantly reduce data duplication and the time it takes to pull images.


== Docker Compose with Nix ==
== Docker Compose with Nix ==


[https://docs.hercules-ci.com/arion/ Arion] is optimized for running Nix-based projects in Docker Compose. It uses the NixOS module system for configuration, it can bypass <code>docker build</code> and lets you use dockerTools or use the store directly in the containers. The images/containers can be typical dockerTools style images or full NixOS configs.
[https://docs.hercules-ci.com/arion/ Arion] is created for running Nix-based projects in Docker Compose. It uses the NixOS module system for configuration, it can bypass <code>docker build</code> and lets you use dockerTools or use the store directly in the containers. The images/containers can be typical dockerTools style images or full NixOS configs.
 
To use Arion, you first need to add its module to you NixOS configuration:
 
<syntaxHighlight lang=nix>
modules = [ arion.nixosModules.arion ];
</syntaxHighlight>
 
After that you can access its options under
<syntaxHighlight lang=nix>
virtualisation.arion = {}
</syntaxHighlight>
 
A config for a simple container could look like this:
 
<syntaxHighlight lang=nix>
virtualisation.arion = {
  backend = "docker";
  projects = {
    "db".settings.services."db".service = {
      image = "";
      restart = "unless-stopped";
      environment = { POSTGRESS_PASSWORD = "password"; };
    };
  };
};
</syntaxHighlight>
 
= Using Nix in containers =
 
While [https://nixos.org/manual/nixpkgs/stable/#sec-pkgs-dockerTools dockerTools] allows to build lightweight containers, it requires <code>nix</code> to be installed on the host system. An alternative are docker images with nix preinstalled:
 
* [https://hub.docker.com/r/nixos/nix/tags nixos/nix] (official)
* [https://hub.docker.com/r/nixpkgs/nix nixpkgs/nix] (built from https://github.com/nix-community/docker-nixpkgs)
NixOS can be run in containers [https://docs.hercules-ci.com/arion/#_nixos_run_full_os using Arion].


== See also ==
= See also =


[[Workgroup:Container]]
[[Workgroup:Container]]


For rootless docker containers : https://nixos.wiki/wiki/Podman
Alternatively you can use [[Podman | podman]].


[[Category:Cookbook]]
[[Category:Cookbook]]
[[Category:NixOS]]
[[Category:Software]]
[[Category:nixpkgs]]
[[Category:Server]]
[[Category:incomplete]]
[[Category:Container]]
[[Category:Applications]]
3

edits