This post is basically a note to the future me and describes the software I install on a fresh linux machine. My linux boxes are usually Ubuntu or Mint, sometimes Debian for servers, but in all cases, they are Debian-based.
Before starting, don’t forget to update the repositories in order to install the latest versions:
and after having installed all what you need, purge what is not necessary anymore:
The bare minimum to survive
Editing text
By default there is vim, but personally I just can’t. I’ve been
using emacs for more than 30 years. I also use jed on the console
as it is a very acceptable emacs clone. jed is a small (~375KB
where vim is ~1.7MB) emacs-like editor customisable in a language
called S-Lang. jed had been around since about 30 years and I’ve
used it on an OS/2 Warp machine because emacs was unstable. See
John E. Davis Software page. If size is
really an issue, zile or nano are smaller Yet, zile lacks some
nice features Jed offers, and nano is really basic and has a
totally different keyboard layout.
1sudo apt install jed emacs # zile
To get spellchecking in various languages, you need to install
aspell and the languages’ dictionaries, for example aspell-fr and
aspell-en for French and English.
You also need to configure emacs:
1;; spell checking
2(setq ispell-program-name "aspell")
3(add-hook 'text-mode-hook 'flyspell-mode) ;; spell text modes
4(add-hook 'prog-mode-hook 'flyspell-prog-mode) ;; spell comment in programs
5(ispell-change-dictionary "english")
6;; (ispell-change-dictionary "francais")
Terminal tools
Linux is equipped with almost all tooling that is required for regular administration. Yet, sometimes, those tools can be replaced with more ergonomic counterparts.
In the early dark days, we had
ps. Then arrivedtopwhich showed the most resource consuming processes as a self updating list in terminal. A much nicer alternative isbtopwhich shows CPU, RAM, etwork usage and processes with UTF8 graphics in the terminal. Another one ishtop, simpler but much smaller.treeoffers an elegant pseudo-graphical view of directories.For a quick rendering of HTML files (for example documentations) in a terminal
lynxorlinksare the right tools to use. Personally,lynxis my favorite.
1sudo apt install btop htop tree lynx
Network services access
sshis nice to access some remote server is fine, as long as you keep typing and as long as there is no networks issues to avoid disconnections and remote work crash. Otherwise, use a terminal multiplexer, likescreenortmux. I personally usetmux. Here is nive a beginer’s guide.httpieprovideshttpandhttpsCLI utilities to query HTTP services and getting replies in a user-friendly format. Sure,curlandwgetexist and I use them too, buthttpandhttpsare nice alternatives.lftpis an FTP terminal client which can be used in scripts and which proposed nicer interactive features over basicftp. Not the only one but it’s the one I use.shhfs auser@my.domain.com:/home/auser ~/mntmounts the auser’s home directory on the local machine on~/mnt. Useful for scripts that already work locally, for example.
1sudo apt install tmux httpie curl wget lftp sshfs
Programming
My main activity on my machine is programming (today as a hobby) and
documenting what I develop, exploring some ideas, etc. The two basic
tools are emacs for programming and git for version controlling,
already discussed above.
Programming tools
git, of course for version controlling.Whenever I deal with JSON, typically for APIs, I love using
jqwhich cleanly displays, filters, transforms, etc. JSON files.yqis another Swiss army knife to deal with YAML, JSON, INI and XML. For JSON, it usesjqunder the hood.
1sudo apt install jq yq git
Programming languages
ASDF: the The Multiple Runtime Version Manager
For years, I was fighting with languages’ versions until I discovered
asdf. asdf is a version manager: it manages different versions of
the same application’s runtimes, for example, but not limited to,
languages.
There is no asdf Debian/Ubuntu package (or at least I didn’t find
it), but pre-compiled binaries are available for main architectures
on Github. Once
downloaded, the archive contains one executable, asdf, that should
be moved in a directory in the PATH. Finally, let’s add the
directory where asdf will store the applications’ executables to
the PATH: add the line export PATH="${ASDF_DATA_DIR:-$HOME/.asdf}/shims:$PATH" to ~/.bashrc
asdf works with plugins where each plugin knows how to install a
given version of the application it manages. To list all what asdf
can manage type asdf plugin list all. This will list 845 (as of
today) plugins.
Installing Java and Groovy
As a first example let’s install the Groovy language. I use it to run a CLI podcast downloader I wrote years, years ago and that I’m too lazy to rewrite. Groovy being based on Java, let’s install Java first.
To install an app (or a language) with asdf, we first need to add
the right plugin. Type asdf plugin list all | grep java to get the
name of the plugin, and add it:
1asdf plugin list all | grep java
2 java https://github.com/halcyon/asdf-java.git
3asdf plugin add java
4asdf list
5java
6 No versions installed
asdf list lists all installed applications. Here it says we have
installed the java plugin but not the Java language runtime
itself. We could have also typed asdf plugin list to only get
information about installed plugins. To install an application, we
need to specify a version. To get all the versions of the Java
programming language, type asdf list all java (spoiler alert,
there are more than 6000 possibilities…). Let’s get the latest
openjdk:
1# what openjdk versions are available
2asdf list all java | grep openjdk
3 openjdk-9
4 ...
5 openjdk-27
6# Install version 27
7asdf install java openjdk-27 # This will take some time
8
9# Check it had been installed
10asdf list
11 java
12 openjdk-27 # The correct version is installed
13
14# Make it the default version
15asdf set -u java openjdk-27
16
17# Check if installed:
18java -version
19 openjdk version "27" 2026-09-15
20 ...
With the same procedure, you may want to install another version and test it:
1asdf install java openjdk-12
2asdf list java
3 openjdk-12 # Installed
4 *openjdk-27 # The star shows which one is active
5asdf set -u java openjdk-12
6asdf list java
7 *openjdk-12 # Looks good
8 openjdk-27
9java -version
10 openjdk version "12" 2019-03-19
We are now ready to install Groovy
1asdf plugin list all | grep groovy
2 groovy https://github.com/weibemoura/asdf-groovy.git
3asdf plugin add groovy
4asdf list all groovy
5 2.4.4
6 ...
7 6.0.0-beta-3
8asdf install groovy 5.1.2 # the last stable version
9asdf set -u groovy 5.1.2
10asdf list groovy
11 *5.1.2 # Great!
12groovy -version
13 Groovy Version: 5.1.2 JVM: 12 Vendor: Oracle Corporation OS: Linux
And voilĂ !
Installing Erlang and Elixir
Since some years, my favorite language is Elixir. Elixir is based on another monument which is Erlang. As for Groovy and Java, Erlang needs to be installed first.
A small difficulty here is that the straight installation as we did
for Java will omit two important features: cryptography (ssl will not
work) and wxWidgets (observer, dedugger and other X applications
will not work).
The first part is to install some libraries at system level:
1sudo apt install -y \
2 build-essential autoconf m4 libncurses-dev libssh-dev \
3 unixodbc-dev libgl1-mesa-dev libglu1-mesa-dev libpng-dev \
4 libssl-dev \
5 libwxgtk3.2-dev libwxgtk-webview3.2-dev \
6 fop xsltproc libxml2-utils \
7 curl git
Then we can install the asdf plugins for Erlang and Elixir:
For its installation, Erlang will be compiled by asdf. We need to
force the compilation with ssl and wx:
1export KERL_CONFIGURE_OPTIONS="--with-ssl --with-wx"
2# latest version found with 'asdf list all erlang'
3version="29.0.6"
4
5asdf install erlang $version
6asdf set -u erlang $version
7
8# Check the version
9erl -v
10 Erlang/OTP 29 [erts-17.0.6] [source] [64-bit] ...
Now we are ready to do the same with Elixir:
1# latest version found with 'asdf list all elixir'
2version="1.20.4-otp-29"
3
4asdf install elixir $version
5asdf set -u elixir $version
6
7# Check the version
8elixir -v
9 ...
10 Elixir 1.20.4 (compiled with Erlang/OTP 29)
Other useful stuff managed by ASDF
I use ASDF to make easily tests with some programming languages. ASDF has plugins to most of them: Ruby, Lua, SWIProlog, SBCL (Steel Bank Common Lisp), Rust, Go, Clojure, V, Zig, C3, Odin and of course (and unfortunately), Javascript as NodeJS or Deno.
It’s always the same procedure:
1asdf plugin add golang
2asdf list all golang
3asdf install golang 1.27.1
4asdf set -u golang 1.27.1
Office
WYSIWYG
You like it or not, Microsoft Office is the de facto document standard in the professional word. You may want to run Office in Wine, but there are Linux native alternatives to be considered. Libre Office is one such alternatives. It usually comes preinstalled on desktop distributions. My experience is that it’s interface is outdated and formatting if definitely not perfect.
Free Office is another alternative. OK, it’s not open source, but the interface id much closer to Microsoft’s (which I have to use at work…) and the rendering is just fine. To install it:
You will have to install a licence, but it’s free for personnal use and the professional 2026 licence costs 150USD for 5 licences.
Drawing
DrawIO is probably one of the best vector drawing application around. It’s available online and as a desktop Java-based application.
Unfortunately, it’s not in Debian/Ubuntu/Mint repositories, but a
.debpackage is available on Github. Once downloaded fromhttps://github.com/jgraph/drawio-desktop/releases/)., simply install it withsudo dpkg -i ~/Downloads/drawio-amd64-31.4.5.debFor quick manipulations (resize, crop, color to black and white, etc.) of bitmaps I use
mtpaint. If I could, I would reinstallxvthat I used in the 90’s on Sun workstations and early linuxes but I couldn’t find it.mtpaintis basic, but it does quickly what I need without the need to read tutorials and documentations for hours.To install:
sudo apt install mtpaintgraphvizis a great tool to draw graphs of many kinds from their textual definition. SimplyTo install
sudo apt install graphvizplantumlis another Java-based tool to generate diagrams from text. As it’s name suggests, it was first designed for UML diagrams (sequence, class, activity, etc), but it is constantly being extended with other types of diagrams like Gantt, RegEx, MindMap, network, and many more.To install:
sudo apt install plantuml
Typesetting and generating HTML or PDF
Long ago I discovered LaTeX. It was like an electroshock: I didn’t need any more to style a document while I was writing it!
typstis the modern successor of LaTeX. It doesn’t have as much libraries and styles a LaTeX (yet, the situation is improving almost every day), but it’s fast (really fast), it has an embedded language for extensions and customisations and it generates PDF and HTML files. It is also available via ASDF.A more trivial tool is Markdown. There are dozens of versions and the tool that tries to gather all versions along with many other formats (Typst, LaTeX, Word, Roff, …) is PanDoc.
1sudo apt install pandoc
Publishing on the web
This blog, but also my personal documentation on my home server are powered by Hugo. Hugo is a static web site generator. Hugo is available with apt or ASDF.
To install: sudo apt install hugo
Virtualization
Containers
Containers are probably the bigest recent (well, not that recent anymore) revolution in the way applications are distributed and ran. Here we’ll be installing Docker, but keep in mind that there are good and robust alternatives as for example Podman, a Docker alternative that probably is safer and faster (One day, I’ll have to give it a try), or LXC.
Docker
To install Docker with apt we need to install the Docker
repository. What follows comes from Docker Docs:
First add Docker’s GPG key
Then add the repository to Apt sources
1sudo tee /etc/apt/sources.list.d/docker.sources <<EOF 2Types: deb 3URIs: https://download.docker.com/linux/ubuntu 4Suites: $(. /etc/os-release && echo "${UBUNTU_CODENAME:-$VERSION_CODENAME}") 5Components: stable 6Architectures: $(dpkg --print-architecture) 7Signed-By: /etc/apt/keyrings/docker.asc 8EOF 9 10sudo apt updateAnd eventually, install Docker
Verifying installation and running test container
We first need to check that Docker daemon is running and if not start it:
To verify the installation there is a hello-world image that
displays a welcome message if all goes fine:
1sudo docker run hello-world
2Unable to find image 'hello-world:latest' locally
3latest: Pulling from library/hello-world
44f55086f7dd0: Pull complete
5...
6Hello from Docker!
7This message shows that your installation appears to be working correctly.
8...
Notice that to run a container, you need to belong to group
docker. So either you need to run sudo docker ... or to make
yourself belong to the docker group. This second solution is much
more convenient, but is a way to gain root privileges. For my
home machine that stays on my desk, I chose that option:
1sudo usermod -aG docker $USER # add docker group to my profile
2newgrp docker # change my group ID
3groups # validate I belong to that group
4docker run hello-world # check it works
Notice also that this works only in the terminal where you typed
newgrp docker. For a definitive solution, you need to logout and
login again.
Running MariaDB
One of main usage I do of Docker is to build and run database architectures that are as close as possible to the future production and that do not perturb the database configurations of other projects. I mostly use MariaDB.
To run a DB named mydb:
1export db_name="mydb"
2export db_user=${db_name}_user
3export db_pass=${db_name}_pass
4export db_root=${db_name}_r00t_p@sswOrd
5
6docker run -i --rm --name ${db_name} \
7-v "$(pwd)/data:/var/lib/mysql/" \
8-p "3306:3306" \
9-e MARIADB_DATABASE=${db_name} \
10-e MARIADB_USER=${db_user} \
11-e MARIADB_PASSWORD=${db_pass} \
12-e MARIADB_ROOT_PASSWORD=${db_root} \
13-d mariadb:10.10-jammy
To access the database we need a client. mycli is good at it but the
good old mysql works also fine:
1sudo apt install mycli mysql-client
An eventually:
1mycli -h 127.0.0.1 -u ${db_user} --password=${db_pass} ${db_name}
2MariaDB mydb_user@127.0.0.1:mydb> show databases
3+--------------------+
4| Database |
5+--------------------+
6| information_schema |
7| mydb |
8+--------------------+
9...
Looks like it works!
x86 virtual machines
The straight forward way is VirtualBox. You get a GUI to create and execute virtual machines. Yet, I don’t like it a lot.
The native Linux solution is to use KVM and QEMU. All dependencies are
automatically pulled if you install bridge-utils and virt-manager:
1sudo apt install bridge-utils virt-manager libosinfo-bin
Once done, start virt-manager to get the management GUI which allows
to create, configure, run, destroy and manage the VMs. If you get
authorization errors, you may need to add yourself to libvirt and
kvm: sudo usermod -aG libvirt,kvm $USER and restart the session.
To create a VM on the command line, use virt-install. For example a NetBSD VM:
1virt-install --name netbsd-10.1 \
2 --ram 4096 --vcpus 2 \
3 --disk path=/var/lib/libvirt/images/netbsd-10.1.qcow2,size=20 \
4 --os-variant netbsd10.0 \
5 --network bridge=virbr0 \
6 --graphics spice \
7 --cdrom ~/Downloads/ISOs/NetBSD-10.1-amd64.iso
Then you can play with virsh:
1virsh list --all # List all available VMs
2virsh start netbsd-10.1 # Start the VM we just created
3virt-viewer netbsd-10.1 # Displays the graphical window
4virsh shutdown netbsd-10.1 # To cleanely stop the VM
Conclusion
Hi my future me. All we have installed so far makes a fresh machine usable for your needs. It has the basic CLI tools, our favourite languages and the simple virtualization methods.
Go and get yourself a beer to thank me to have spent all this time on this document. And never forget to have fun