About me: My name is Solène Rapenne, pronouns she/her. I like learning and sharing knowledge. Hobbies: '(BSD OpenBSD Qubes OS Lisp cmdline gaming security QubesOS internet-stuff). I love percent and lambda characters. Qubes OS core team member, former OpenBSD developer solene@. No AI is involved in this blog.

Contact me: solene at dataswamp dot org or @solene@bsd.network (mastodon).

I'm a freelance OpenBSD, FreeBSD, Linux and Qubes OS consultant, this includes DevOps, DevSecOps, technical writing or documentation work. If you enjoy this blog, you can sponsor my open source work financially so I can write this blog and contribute to Free Software as my daily job.

Guix: fetch packages from other Guix in the LAN

Written by Solène, on 07 June 2021.
Tags: #guix

Comments on Fediverse/Mastodon

1. Introduction §

In this how-to I will explain how to configure two Guix system to share packages from one to another. The idea is that most of the time packages are downloaded from ci.guix.gnu.org but sometimes you can compile local packages too, in both case you will certainly prefer computers from your network to get the same packages from a computer that already had them to save some bandwidth. This is quite easy to achieve in Guix.

We need at least two Guix systems, I'll name the one with the package "server" and the system that will install packages the "client".

2. Prepare the server §

On the server, edit your /etc/config.scm file and add this service:

(service guix-publish-service-type
         (guix-publish-configuration
             (host "0.0.0.0")
             (port 8080)
             (advertise? #t))))

Guix Manual: guix-publish service

Run "guix archive --generate-key" as root to create a public key and then reconfigure the system. Your system is now publishing packages on port 8080 and advertising it with mDNS (involving avahi).

Your port 8080 should be reachable now with a link to a public key.

3. Prepare the client §

On the client, edit your /etc/config.scm file and modify the "%desktop-services" or "%base-services" if any.

(guix-service-type
  config =>
    (guix-configuration
      (inherit config)
      (discover? #t)
      (authorized-keys
        (append (list (local-file "/etc/key.pub"))
                %default-authorized-guix-keys)))))))

Guix Manual: Getting substitutes from other servers

Download the public key from the server (visiting its ip on port 8080 you will get a link) and store it in "/etc/key.pub", reconfigure your system.

Now, when you install a package, you should see from where the substitution (name for packages) are downloaded from.

4. Declaring a repository (not dynamic) §

In the previous example, we are using advertising on the server and discovery on the client, this may not be desired and won't work from a different network.

You can manually register a remote substitute server instead of using discovery by using "substitute-urls" like this:

(guix-service-type
  config =>
    (guix-configuration
      (inherit config)
      (discover? #t)
      (substitute-urls
        (append (list "http://192.168.1.66:8080")
                %default-substitute-urls))
      (authorized-keys
        (append (list (local-file "/etc/key.pub"))
                %default-authorized-guix-keys)))))))

5. Conclusion §

I'm doing my best to avoid wasting bandwidth and resources in general, I really like this feature because this doesn't require much configuration or infrastructure and work in a sort of peer-to-peer.

Other projects like Debian prefer using a proxy that keep in cache the packages downloaded and act as a repository provider itself to proxyfi the service.

In case of doubts of the validity of the substitutions provided by an url, the challenge feature can be used to check if reproducible builds done locally match the packages provided by a source.

Guix Manual: guix challenge documentation

Guix Manual: guix weather, a command to get information from a repository