When using a Continuous Integration workflow using Docker there is often the need to automatically install packages. On Debian and its derivatives like Ubuntu this is usually done using the apt command. Unfortunately that command is meant to be used interactively by the user behind the keyboard. Hopefully this is not the case in a CI workflow. If you try to use this command in a script it will print a warning that this is not supported.
To fix this issue we have to use the slightly lower level apt-get utility. In contrast to the
apt-get supports being used from the command line.
Updating the Package Repositories
Our first hurdle is updating the package repositories. Where we normally would use
apt update we instead use
apt-get update. This will still result in a lot of output we don't care about. To fix this we can use the
--quiet=<level> option. This results in the following command:
apt-get update --quiet=2.
Installing the Package
Instead of the usual
apt install <package> we have to start with
apt-get install <package>. This still won't install the package if there is not user present as it will prompt a
Y/n question on wether to install the listed packages. To automatically answer yes to that question we can add the
--yes option to our command line:
apt-get install --yes <package>.
This will cause it to progress a bit further but you might see that it'll sometimes hang after downloading the packages. This is the step where packages can ask the user questions on how they should be configured. Fortunately most packages have sensible defaults so we can decide to use those. If the defaults of the package you want to install aren't sensible enough you can set them beforehand using debconf-set-selections.
apt-get to not ask us any questions we have to set the frontend using an environment variable called
DEBIAN_FRONTEND. Specifically, we want to use the
noninteractive frontend. This results in the following command:
DEBIAN_FRONTEND=noninteractive apt-get install --yes <package>
Lets say we want to install the build-essential package. These would be the full CI statements we would have to run inside Docker. (Be sure not to run noninteractive --yes
apt-get install commands on machines you're not ready to reinstall)
# Make sure we don't silently continue when a command fails set -euo pipefail # Update the package repositories apt-get update --quiet=2 # Install the package DEBIAN_FRONTEND=noninteractive apt-get install --yes build-essential