Crafting happiness with Free Software & Hardware

How to package software for #Guix (1)

Logo Guix

This serie of blog posts is an invitation to see how one can learn how to package software for Guix. Without prior knowledge about Guix or even software packaging, I show you what resources are needed and how to use them. My method is driven by doing. The commands execution rhythms my iterations and its return guides the code to produce and the use of external resources (documentation, source code, community). At the end of this serie, I would have packaged a simple piece of free software : ac-geiser, an extension of Emacs that brings a hint of self-completion to Geiser when I hack with the Guile language.

Before we get started, I want to talk to you about my style, yeah baby. I'm lazy. I like to do as little as possible. So I have a penchant for sobriety. I also like things tidy and clear. I only read documentation when I know what I'm looking for. Also, I like to do things on my own. Even when I find a shortcut, I will always take a step back to see how I could have figure it out by myself. But I don't like to waste my time. So I don't hesitate to approach the Guixters community once I admit my failure (not a pleasant feeling). Well, enough coming out. Let's get started !

To understand the following, you will need to be familiar with the syntax of the Guile programming language. I can suggest you to start with Mu Lei's Scheme tutorial as Guile is a Scheme implementation.
To reproduce manipulations, you will need to have Guix installed. Here is a way to do so :

$ cd /tmp
$ wget https://git.savannah.gnu.org/cgit/guix.git/plain/etc/guix-install.sh
$ chmod +x guix-install.sh
$ sudo ./guix-install.sh

Done, you think ? Hell no, haha. Because we are going to hack Guix itself, we need to download the Guix's source code and compile it. Then use the result as our main toolkit. Follow the guide ! (All these steps are decribed here)

$ git clone https://git.savannah.gnu.org/git/guix.git
$ cd guix
$ guix environment --pure guix
[dev]$ ./bootstrap # for [dev]$ see https://guix.gnu.org/manual/en/html_node/Invoking-guix-environment.html
[dev]$ ./configure --localstatedir=/var
[dev]$ make # coffee? tea? workout? meditation? poo?

If you encounter errors while executing these commands, you may need to ask for help to the Guixters Community, don't hesitate!

Fair enough.

What is a package, for Guix point of view ? According to the documentation, a Guix package is represented by an instanciation of the package Guile object.

How do I build a package definition ? Using... guix build ! It won't install anything on my system (good to know as I am pretty sure I will make a lot of mistakes). With the —file option, I can specify a package definition file as an input.

Remember to use the Guix binary (previously compiled) through the pre-inst-env script freshly generated. Lets try it once, to see what happen :

What if I just execute this :

$ ./pre-inst-env guix build

Well, nothing. What about :

$ ./pre-inst-env guix build -f
guix build: error: invalid argument: Missing required argument after `-f'

As expected, and now, I give it a filename :

$ ./pre-inst-env guix build -f /tmp/dummy-package-definition.scm
guix build: error: failed to load '/tmp/dummy-package-definition.scm': No such file or directory

Here, Guix is telling me the file in location /tmp/dummy-package-definition.scm doesn't exist. It is true, I didn't create that file yet. So what if I create the file and re-execute the guix build -f command :

$ touch /tmp/dummy-package-definition.scm
$ ./pre-inst-env guix build -f /tmp/dummy-package-definition.scm
guix build: error: #<unspecified>: not something we can build

Now there is a file, Guix tells me it is not buildable. Could be because the file doesn't have a package definition, I mean, a package object. Lets try that :

$ echo "(package)" > /tmp/dummy-package-definition.scm
$ ./pre-inst-env guix build -f /tmp/dummy-package-definition.scm 
/tmp/dummy-package-definition.scm:1:0: error: package: unbound variable
hint: Did you forget `(use-modules (guix packages))'?

Guix points out to me the variable package is unbound and suggest to me I how I can fix this error (so kind).

$ echo "(use-modules (guix packages)) (package)" > /tmp/dummy-package-definition.scm
$ ./pre-inst-env guix build -f /tmp/dummy-package-definition.scm
/tmp/dummy-package-definition.scm:1:30: error: (package): missing field initializers (name version source build-system synopsis description license home-page)

Another attempt, another mistake (but that's how you learn, isn't it?).

So, here, Guix tells me that the initialization of several fields is missing from (package) and tells me which ones. Did I mention that Guix is nice? I add the requested fields in my definition and I retry.

$ echo "(use-modules (guix packages)) (package name version source build-system synopsis description license home-page)" > /tmp/dummy-package-definition.scm
$ ./pre-inst-env guix build -f /tmp/dummy-package-definition.scm
/tmp/dummy-package-definition.scm:1:30: error: name: invalid field specifier

Ah, we're making progress (yeah, in my world, another error is what I call a new step) ! Now, Guix tells me that the name field is misspecified. Since I have no idea how name should be specified, I'm going to look up some information in the Guix documentation. It is so well done that there is a whole package reference page. I learn there that the name field is waiting for a string. OK !

$ echo '(use-modules (guix packages)) (package (name "") version source build-system synopsis description license home-page)' > /tmp/dummy-package-definition.scm
$ ./pre-inst-env guix build -f /tmp/dummy-package-definition.scm
/tmp/dummy-package-definition.scm:1:30: error: version: invalid field specifier

For version, same punishment!

$ echo '(use-modules (guix packages)) (package (name "") (version "") source build-system synopsis description license home-page)' > /tmp/dummy-package-definition.scm
$ ./pre-inst-env guix build -f /tmp/dummy-package-definition.scm
/tmp/dummy-package-definition.scm:1:30: error: source: invalid field specifier

I'll stop here for today. I'll look into the source field in the next article. Here is the definition obtained at this point:

(use-modules
 (guix packages))
(package
 (name "")
 (version "")
 source
 build-system
 synopsis
 description
 license
 home-page)

Thank you so much for reading this article !

Don't hesitate to give me your opinion, leave a comment, or ask a question via :
E-mail: jeremy AT korwin-zmijowski DOT fr
Mastodon: @jeko@framapiaf.org
Peertube: @jeko@video.tedomum.net
Twitter: @JeremyKorwin

Subscribe so you don't miss the next ones :
blog via Mastodon @jeko@write.as et RSS
screencast via Peertube jeko@video.tedomum.net et RSS

And most importantly, share the blog and tell your friends it's the best blog in the history of Free Software! No shit!

#guix #package #english