[neon/backports-jammy/distrobox/Neon/unstable] /: New upstream version 1.4.0
Michel Alexandre Salim
null at kde.org
Fri Jul 14 11:42:05 BST 2023
Git commit a9e3b9df646a49733beb4d405d1abd9ffd17968c by Michel Alexandre Salim.
Committed on 12/09/2022 at 08:55.
Pushed by jriddell into branch 'Neon/unstable'.
New upstream version 1.4.0
M +6 -0 .github/ISSUE_TEMPLATE/bug_report.md
M +12 -11 .github/workflows/compatibility.yml
M +23 -2 .github/workflows/main.yml
A +20 -0 .shellcheckrc
M +15 -3 distrobox
M +49 -46 distrobox-create
M +72 -47 distrobox-enter
A +136 -0 distrobox-ephemeral
M +40 -11 distrobox-export
A +282 -0 distrobox-generate-entry
M +108 -61 distrobox-host-exec
M +184 -84 distrobox-init
M +43 -26 distrobox-list
M +75 -62 distrobox-rm
M +12 -5 distrobox-stop
C +55 -66 distrobox-upgrade [from: distrobox-stop - 065% similarity]
M +75 -20 docs/README.md
M +72 -39 docs/compatibility.md
M +1 -1 docs/distrobox_gentoo.md
M +5 -0 docs/featured_articles.md
M +50 -70 docs/posts/execute_commands_on_host.md
M +11 -17 docs/posts/integrate_vscode_distrobox.md
M +40 -28 docs/usage/distrobox-create.md
M +36 -17 docs/usage/distrobox-enter.md
A +42 -0 docs/usage/distrobox-ephemeral.md
M +108 -44 docs/usage/distrobox-export.md
A +24 -0 docs/usage/distrobox-generate-entry.md
M +25 -14 docs/usage/distrobox-host-exec.md
M +16 -12 docs/usage/distrobox-init.md
M +22 -12 docs/usage/distrobox-list.md
M +22 -13 docs/usage/distrobox-rm.md
M +22 -13 docs/usage/distrobox-stop.md
A +24 -0 docs/usage/distrobox-upgrade.md
M +5 -0 docs/usage/usage.md
M +75 -1 docs/useful_tips.md
A +158 -0 extras/install-podman
M +42 -35 install
M +1 -0 man/gen-man
M +79 -76 man/man1/distrobox-compatibility.1
M +53 -41 man/man1/distrobox-create.1
M +48 -21 man/man1/distrobox-enter.1
A +81 -0 man/man1/distrobox-ephemeral.1
M +151 -65 man/man1/distrobox-export.1
A +51 -0 man/man1/distrobox-generate-entry.1
M +30 -18 man/man1/distrobox-host-exec.1
M +24 -19 man/man1/distrobox-init.1
M +27 -16 man/man1/distrobox-list.1
M +27 -17 man/man1/distrobox-rm.1
M +27 -17 man/man1/distrobox-stop.1
A +50 -0 man/man1/distrobox-upgrade.1
M +625 -267 man/man1/distrobox.1
A +- -- terminal-distrobox-icon.png
D +0 -109 tests/compatibility-test
M +14 -23 uninstall
https://invent.kde.org/neon/backports-jammy/distrobox/-/commit/a9e3b9df646a49733beb4d405d1abd9ffd17968c
diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md
index 155614e..a007b14 100644
--- a/.github/ISSUE_TEMPLATE/bug_report.md
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -7,6 +7,12 @@ assignees: ''
---
+Please, before opening a bug:
+
+- make sure you've read the documentation.
+- Ensure there isn't already an open issue about this.
+- Ensure there isn't already a closed/resolved issue about this.
+
**Describe the bug**
A clear and concise description of what the bug is.
diff --git a/.github/workflows/compatibility.yml b/.github/workflows/compatibility.yml
index 51db8be..9674d1d 100644
--- a/.github/workflows/compatibility.yml
+++ b/.github/workflows/compatibility.yml
@@ -38,7 +38,7 @@ jobs:
# Fetch from compatibility table all the distros supported
- id: check_file_changed
run: |
- if git diff --name-only HEAD^ HEAD | grep -E "^distrobox|compatibility.md"; then
+ if git diff --name-only HEAD^ HEAD | grep -v host-exec | grep -E "^distrobox|compatibility.md"; then
echo "::set-output name=distrobox_changed::True"
else
echo "::set-output name=distrobox_changed::False"
@@ -91,15 +91,16 @@ jobs:
image=${{ matrix.distribution }}
container_name="$(basename "${image}" | sed -E 's/[:.]/-/g')"
${DBX_CONTAINER_MANAGER} pull "${image}"
- case "${container_name}" in
- *init*)
- echo "SYSTEMD DETECTED: creating container with --init..."
- ./distrobox create --yes -i "${image}" --name "${container_name}" --init
- ;;
- *)
- ./distrobox create --yes -i "${image}" --name "${container_name}"
- ;;
- esac
+ ./distrobox create --yes -i "${image}" --name "${container_name}"
+ #case "${container_name}" in
+ # *init*)
+ # echo "SYSTEMD DETECTED: creating container with --init..."
+ # ./distrobox create --yes -i "${image}" --name "${container_name}" --init
+ # ;;
+ # *)
+ # ./distrobox create --yes -i "${image}" --name "${container_name}"
+ # ;;
+ # esac
# Ensure distrobox enter and init works:
- name: Distrobox enter - init
@@ -208,4 +209,4 @@ jobs:
run: |
image=${{ matrix.distribution }}
container_name="$(basename "${image}" | sed -E 's/[:.]/-/g')"
- ./distrobox rm --force --name "${container_name}"
+ ./distrobox rm --force "${container_name}"
diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml
index 9b6fae2..42a7c66 100644
--- a/.github/workflows/main.yml
+++ b/.github/workflows/main.yml
@@ -67,15 +67,36 @@ jobs:
run: |
result=0
podman pull docker.io/koalaman/shellcheck:stable
- for file in $(find . -type f -not -path "*.git*"); do
+ for file in $(find . -type f -name ".*" -prune -o -print | grep -v '.git'); do
if file "$file" | grep -qi shell; then
echo "### Checking file $file..."
- podman run --rm -v "$PWD:/mnt" docker.io/koalaman/shellcheck:stable -s sh -a -o all -Sstyle -Calways -x -e SC2310,SC2311,SC2312 $file
+ # Should read the .shellcheckrc file to behave like -s sh -a -o all -Sstyle -Calways -x -e SC2310,SC2311,SC2312
+ podman run --rm -v "$PWD:/mnt" docker.io/koalaman/shellcheck:stable -a -Sstyle -Calways $file
result=$(( result + $? ))
fi
done
exit $result
+ differential-shellcheck:
+ if: github.event_name == 'pull_request'
+ runs-on: ubuntu-latest
+
+ permissions:
+ contents: read
+ security-events: write
+ pull-requests: write
+
+ steps:
+ - uses: actions/checkout at v2
+ with:
+ fetch-depth: 0
+
+ - name: Run Differential ShellCheck
+ uses: redhat-plumbers-in-action/differential-shellcheck at v3
+ with:
+ severity: style
+ token: ${{ secrets.GITHUB_TOKEN }}
+
bashate:
runs-on: ubuntu-latest
diff --git a/.shellcheckrc b/.shellcheckrc
new file mode 100644
index 0000000..0eba7ab
--- /dev/null
+++ b/.shellcheckrc
@@ -0,0 +1,20 @@
+# Overrides the shell detected from the shebang. This is useful for files meant to be included (and thus lacking a shebang), or possibly as a more targeted alternative to 'disable=SC2039'.
+shell=sh
+
+# Always allow ShellCheck to open arbitrary files from 'source' statements.
+external-sources=true
+
+# Enable all optional checks
+enable=all
+
+# This function is invoked in an 'if' condition so set -e will be disabled. Invoke separately if failures should cause the script to exit.
+# - We don't want to exit if errors happen inside a check, that's why we have a check...
+disable=SC2310
+
+# Bash implicitly disabled set -e for this function invocation because it's inside a command substitution. Add set -e; before it or enable inherit_errexit.
+# - Don't care if we inherit errexit inside substitutions, we do checks for that.
+disable=SC2311
+
+# Consider invoking this command separately to avoid masking its return value (or use '|| true' to ignore).
+# - We already check errors and adding "|| true" everywhere hinders readability.
+disable=SC2312
diff --git a/distrobox b/distrobox
index 5cbb6de..0f83b54 100755
--- a/distrobox
+++ b/distrobox
@@ -24,7 +24,7 @@ set -o nounset
trap '[ "$?" -ne 0 ] && printf "\nAn error occurred\n"' EXIT
-version="1.3.1"
+version="1.4.0"
# Print usage to stdout.
# Arguments:
@@ -39,8 +39,11 @@ Choose one of the available commands:
create
enter
list
- stop
rm
+ stop
+ upgrade
+ ephemeral
+ generate-entry
version
EOF
}
@@ -72,13 +75,22 @@ case "${distrobox_command}" in
rm)
"${distrobox_path}"/distrobox-rm "$@"
;;
+ upgrade)
+ "${distrobox_path}"/distrobox-upgrade "$@"
+ ;;
+ generate-entry)
+ "${distrobox_path}"/distrobox-generate-entry "$@"
+ ;;
+ ephemeral)
+ "${distrobox_path}"/distrobox-ephemeral "$@"
+ ;;
-V | --version | version)
printf "distrobox: %s\n" "${version}"
exit 0
;;
help | --help | -h)
if command -v man > /dev/null; then
- man distrobox
+ man distrobox || show_help
exit 0
fi
show_help
diff --git a/distrobox-create b/distrobox-create
index b0bb0e9..2f111d0 100755
--- a/distrobox-create
+++ b/distrobox-create
@@ -29,6 +29,7 @@
# DBX_CONTAINER_MANAGER
# DBX_CONTAINER_NAME
# DBX_NON_INTERACTIVE
+# DBX_SUDO_PROGRAM
trap '[ "$?" -ne 0 ] && printf "\nAn error occurred\n"' EXIT
@@ -55,35 +56,27 @@ container_user_gid="$(id -rg)"
container_user_home="${HOME:-"/"}"
container_user_name="${USER}"
container_user_uid="$(id -ru)"
-non_interactive=0
-# Use cd + dirname + pwd so that we do not have relative paths in mount points
-# We're not using "realpath" here so that symlinks are not resolved this way
-# "realpath" would break situations like Nix or similar symlink based package
-# management.
-distrobox_entrypoint_path="$(cd "$(dirname "${0}")" && pwd)/distrobox-init"
-distrobox_export_path="$(cd "$(dirname "${0}")" && pwd)/distrobox-export"
-distrobox_hostexec_path="$(cd "$(dirname "${0}")" && pwd)/distrobox-host-exec"
-# In case init or export are not in the same path as create, let's search
-# in PATH for them.
-[ ! -e "${distrobox_entrypoint_path}" ] && distrobox_entrypoint_path="$(command -v distrobox-init)"
-[ ! -e "${distrobox_export_path}" ] && distrobox_export_path="$(command -v distrobox-export)"
-[ ! -e "${distrobox_hostexec_path}" ] && distrobox_hostexec_path="$(command -v distrobox-hostexec)"
+distrobox_sudo_program="sudo"
dryrun=0
init=0
+non_interactive=0
rootful=0
verbose=0
-version="1.3.1"
+version="1.4.0"
# Source configuration files, this is done in an hierarchy so local files have
# priority over system defaults
# leave priority to environment variables.
config_files="
/usr/share/distrobox/distrobox.conf
+ /usr/etc/distrobox/distrobox.conf
/etc/distrobox/distrobox.conf
- ${HOME}/.config/distrobox/distrobox.conf
+ ${XDG_CONFIG_HOME:-"${HOME}/.config"}/distrobox/distrobox.conf
${HOME}/.distroboxrc
"
for config_file in ${config_files}; do
+ # Shellcheck will give error for sourcing a variable file as it cannot follow
+ # it. We don't care so let's disable this linting for now.
# shellcheck disable=SC1090
[ -e "${config_file}" ] && . "${config_file}"
done
@@ -97,6 +90,7 @@ done
[ -n "${DBX_CONTAINER_MANAGER}" ] && container_manager="${DBX_CONTAINER_MANAGER}"
[ -n "${DBX_CONTAINER_NAME}" ] && container_name="${DBX_CONTAINER_NAME}"
[ -n "${DBX_NON_INTERACTIVE}" ] && non_interactive="${DBX_NON_INTERACTIVE}"
+[ -n "${DBX_SUDO_PROGRAM}" ] && distrobox_sudo_program="${DBX_SUDO_PROGRAM}"
# Print usage to stdout.
# Arguments:
@@ -127,7 +121,8 @@ Options:
--pull/-p: pull the image even if it exists locally (implies --yes)
--yes/-Y: non-interactive, pull images without asking
--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
--clone/-c: name of the distrobox container to use as base for a new container
this will be useful to either rename an existing distrobox or have multiple copies
of the same environment.
@@ -336,9 +331,9 @@ if [ "${verbose}" -ne 0 ]; then
container_manager="${container_manager} --log-level debug"
fi
-# prepend sudo if we want podman or docker to be rootful
+# prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
if [ "${rootful}" -ne 0 ]; then
- container_manager="sudo ${container_manager}"
+ container_manager="${distrobox_sudo_program} ${container_manager}"
fi
# Clone a container as a snapshot.
@@ -366,7 +361,7 @@ clone_container() {
# for the new container.
container_source_id="$(${container_manager} inspect --type container \
"${container_clone}" --format '{{.Id}}')"
- container_commit_tag="${container_clone}:$(date +%F)"
+ container_commit_tag="$(echo "${container_clone}:$(date +%F)" | tr '[:upper:]' '[:lower:]')"
# Commit current container state to a new image tag
printf >&2 "Duplicating %s...\n" "${container_clone}"
@@ -416,16 +411,14 @@ generate_command() {
# Also mount in the container the distrobox-export and distrobox-host-exec
# utilities.
result_command="${result_command}
+ --label \"manager=distrobox\"
--env \"SHELL=${SHELL:-"/bin/bash"}\"
--env \"HOME=${container_user_home}\"
- --volume \"${container_user_home}\":\"${container_user_home}\":rslave
- --volume \"${distrobox_entrypoint_path}\":/usr/bin/entrypoint:ro
- --volume \"${distrobox_export_path}\":/usr/bin/distrobox-export:ro
- --volume \"${distrobox_hostexec_path}\":/usr/bin/distrobox-host-exec:ro
--volume /:/run/host:rslave
--volume /dev:/dev:rslave
--volume /sys:/sys:rslave
- --volume /tmp:/tmp:rslave"
+ --volume /tmp:/tmp:rslave
+ --volume \"${container_user_home}\":\"${container_user_home}\":rslave"
# This fix is needed as on Selinux systems, the host's selinux sysfs directory
# will be mounted inside the rootless container.
@@ -463,14 +456,21 @@ generate_command() {
--volume $(realpath /dev/shm):$(realpath /dev/shm)"
fi
- # If you are using NixOS, or have Nix installed, /nix is a volume containing
+ # If you are using NixOS, or have Nix or Guix installed, /nix and /gnu are volumes containing
# you binaries and many configs.
- # /nix needs to be mounted if you want to execute those binaries from within
- # the container. Therefore we need to mount /nix as a volume, but only if it exists.
- if [ -d "/nix" ]; then
- result_command="${result_command}
- --volume /nix:/nix"
- fi
+ # They be mounted if you want to execute those binaries from within
+ # the container. Therefore we need to mount as a volume, but only if they exists.
+ nix_dirs="
+ /nix
+ /gnu
+ /run/current-system/sw
+ "
+ for nix_dir in ${nix_dirs}; do
+ if [ -d "${nix_dir}" ]; then
+ result_command="${result_command}
+ --volume ${nix_dir}:${nix_dir}"
+ fi
+ done
# If we have a custom home to use,
# 1- override the HOME env variable
@@ -478,9 +478,9 @@ generate_command() {
# 3- mount the custom home inside the container.
if [ -n "${container_user_custom_home}" ]; then
result_command="${result_command}
- --env \"HOME=${container_user_custom_home}\"
- --env \"DISTROBOX_HOST_HOME=${container_user_home}\"
- --volume ${container_user_custom_home}:${container_user_custom_home}:rslave"
+ --env \"HOME=${container_user_custom_home}\"
+ --env \"DISTROBOX_HOST_HOME=${container_user_home}\"
+ --volume ${container_user_custom_home}:${container_user_custom_home}:rslave"
fi
# Mount also the /var/home dir on ostree based systems
@@ -489,13 +489,13 @@ generate_command() {
[ -d "/var/home/${container_user_name}" ]; then
result_command="${result_command}
- --volume \"/var/home/${container_user_name}\":\"/var/home/${container_user_name}\":rslave"
+ --volume \"/var/home/${container_user_name}\":\"/var/home/${container_user_name}\":rslave"
fi
# Mount also the XDG_RUNTIME_DIR to ensure functionality of the apps.
if [ -d "/run/user/${container_user_uid}" ]; then
result_command="${result_command}
- --volume /run/user/${container_user_uid}:/run/user/${container_user_uid}:rslave"
+ --volume /run/user/${container_user_uid}:/run/user/${container_user_uid}:rslave"
fi
# These are dynamic configs needed by the container to function properly
@@ -533,6 +533,11 @@ generate_command() {
result_command="${result_command} ${container_manager_additional_flags}"
# Now execute the entrypoint, refer to `distrobox-init -h` for instructions
+ #
+ # Be aware that entrypoint corresponds to distrobox-init, the copying of it
+ # inside the container is moved to distrobox-enter, in the start phase.
+ # This is done to make init, export and host-exec location independent from
+ # the host, and easier to upgrade.
result_command="${result_command} ${container_image}
/usr/bin/entrypoint -v --name \"${container_user_name}\"
--user ${container_user_uid}
@@ -548,13 +553,6 @@ generate_command() {
printf "%s" "${result_command}"
}
-# Check that we have a complete distrobox installation or
-# entrypoint and export will not work.
-if [ -z "${distrobox_entrypoint_path}" ] || [ -z "${distrobox_export_path}" ]; then
- printf >&2 "Error: no distrobox-init found in %s\n" "${PATH}"
- exit 127
-fi
-
# dry run mode, just generate the command and print it. No creation.
if [ "${dryrun}" -ne 0 ]; then
if [ -n "${container_clone}" ]; then
@@ -620,18 +618,23 @@ if [ "${container_always_pull}" -eq 1 ] ||
fi
# Generate the create command and run it
-printf "Creating '%s' using image %s\t" "${container_name}" "${container_image}"
+printf >&2 "Creating '%s' using image %s\t" "${container_name}" "${container_image}"
cmd="$(generate_command)"
# Eval the generated command. If successful display an helpful message.
# shellcheck disable=SC2086
if eval ${cmd} > /dev/null; then
printf >&2 "\033[32m [ OK ]\n\033[0mDistrobox '%s' successfully created.\n" "${container_name}"
- printf "To enter, run:\n\n"
+ printf >&2 "To enter, run:\n\n"
if [ "${rootful}" -ne 0 ]; then
printf "distrobox enter --root %s\n\n" "${container_name}"
else
printf "distrobox enter %s\n\n" "${container_name}"
fi
- exit 0
+
+ # We've created the box, let's also create the entry
+ if [ "${rootful}" -eq 0 ]; then
+ "$(dirname "$(realpath "${0}")")/distrobox-generate-entry" "${container_name}"
+ fi
+ exit $?
fi
printf >&2 "\033[31m [ ERR ]\n\033[0m"
diff --git a/distrobox-enter b/distrobox-enter
index 138446c..54be888 100755
--- a/distrobox-enter
+++ b/distrobox-enter
@@ -22,13 +22,13 @@
# Expected env variables:
# HOME
# USER
-# SHELL
# Optional env variables:
# DBX_CONTAINER_MANAGER
# DBX_CONTAINER_NAME
# DBX_SKIP_WORKDIR
+# DBX_SUDO_PROGRAM
-trap '[ "$?" -ne 0 ] && printf "\nAn error occurred\n" && rm -f "/tmp/.*.fifo"' EXIT
+trap '[ "$?" -ne 0 ] && printf "\nAn error occurred\n" && rm -f $HOME/.cache/.*.fifo $HOME/.cache/.*.status' EXIT
# Dont' run this command as sudo.
if [ "$(id -u)" -eq 0 ]; then
@@ -38,19 +38,24 @@ if [ "$(id -u)" -eq 0 ]; then
exit 1
fi
+# Finx components we need to copy inside the container.
+distrobox_entrypoint_path="$(dirname "$(realpath "${0}")")/distrobox-init"
+distrobox_export_path="$(dirname "$(realpath "${0}")")/distrobox-export"
+distrobox_hostexec_path="$(dirname "$(realpath "${0}")")/distrobox-host-exec"
+# In case init or export are not in the same path as create, let's search
+# in PATH for them.
+[ ! -e "${distrobox_entrypoint_path}" ] && distrobox_entrypoint_path="$(command -v distrobox-init)"
+[ ! -e "${distrobox_export_path}" ] && distrobox_export_path="$(command -v distrobox-export)"
+[ ! -e "${distrobox_hostexec_path}" ] && distrobox_hostexec_path="$(command -v distrobox-hostexec)"
# Defaults
container_command=""
-container_shell="${SHELL:-"bash"}"
-# Work around for shells that are not in the container's file system, nor PATH.
-# For example in hosts that do not follow FHS, like NixOS or for shells in custom
-# exotic paths.
-container_shell="$(basename "${container_shell}") -l"
container_image=""
container_image_default="registry.fedoraproject.org/fedora-toolbox:36"
container_manager="autodetect"
container_name="my-distrobox"
container_manager_additional_flags=""
non_interactive=0
+distrobox_sudo_program="sudo"
# Use cd + dirname + pwd so that we do not have relative paths in mount points
# We're not using "realpath" here so that symlinks are not resolved this way
@@ -62,18 +67,21 @@ headless=0
rootful=0
skip_workdir=0
verbose=0
-version="1.3.1"
+version="1.4.0"
# Source configuration files, this is done in an hierarchy so local files have
# priority over system defaults
# leave priority to environment variables.
config_files="
/usr/share/distrobox/distrobox.conf
+ /usr/etc/distrobox/distrobox.conf
/etc/distrobox/distrobox.conf
- ${HOME}/.config/distrobox/distrobox.conf
+ ${XDG_CONFIG_HOME:-"${HOME}/.config"}/distrobox/distrobox.conf
${HOME}/.distroboxrc
"
for config_file in ${config_files}; do
+ # Shellcheck will give error for sourcing a variable file as it cannot follow
+ # it. We don't care so let's disable this linting for now.
# shellcheck disable=SC1090
[ -e "${config_file}" ] && . "${config_file}"
done
@@ -86,6 +94,7 @@ done
[ -n "${DBX_CONTAINER_NAME}" ] && container_name="${DBX_CONTAINER_NAME}"
[ -n "${DBX_SKIP_WORKDIR}" ] && skip_workdir="${DBX_SKIP_WORKDIR}"
[ -n "${DBX_NON_INTERACTIVE}" ] && non_interactive="${DBX_NON_INTERACTIVE}"
+[ -n "${DBX_SUDO_PROGRAM}" ] && distrobox_sudo_program="${DBX_SUDO_PROGRAM}"
# Print usage to stdout.
# Arguments:
@@ -113,7 +122,8 @@ Options:
--additional-flags/-a: additional flags to pass to the container manager command
--help/-h: show this message
--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
--dry-run/-d: only print the container manager command generated
--verbose/-v: show more verbosity
--version/-V: show version
@@ -233,28 +243,15 @@ if ! command -v "${container_manager}" > /dev/null && [ "${dryrun}" -eq 0 ]; the
printf >&2 "\thttps://github.com/89luca89/distrobox/blob/main/docs/compatibility.md\n"
exit 127
fi
-# Small performance optimization, using podman socket shaves
-# about half the time to access informations.
-#
-# Accessed file is /run/user/USER_ID/podman/podman.sock
-#
-# This is not necessary on docker as it is already handled
-# in this way.
-if [ -z "${container_manager#*podman*}" ] &&
- [ "${rootful}" -eq 0 ] &&
- [ -S "/run/user/$(id -ru)/podman/podman.sock" ] &&
- systemctl --user status podman.socket > /dev/null; then
-
- container_manager="${container_manager} --remote"
-fi
+
# add verbose if -v is specified
if [ "${verbose}" -ne 0 ]; then
container_manager="${container_manager} --log-level debug"
fi
-# prepend sudo if we want podman or docker to be rootful
+# prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
if [ "${rootful}" -ne 0 ]; then
- container_manager="sudo ${container_manager}"
+ container_manager="${distrobox_sudo_program} ${container_manager}"
fi
# Generate Podman or Docker command to execute.
@@ -276,7 +273,7 @@ generate_command() {
# Disable tty also if we're NOT in a tty (test -t 0).
if [ "${headless}" -eq 0 ] && [ -t 0 ]; then
result_command="${result_command}
- --tty"
+ --tty"
fi
# Entering container using our user and workdir.
@@ -290,7 +287,7 @@ generate_command() {
if [ "${skip_workdir}" -eq 0 ]; then
workdir="$(echo "${PWD:-${container_home:-"/"}}" | sed -e 's/"/\\\"/g')"
if [ -n "${workdir##*"${container_home}"*}" ]; then
- workdir="/run/host/${workdir}"
+ workdir="/run/host${workdir}"
fi
else
# Skipping workdir we just enter $HOME of the container.
@@ -298,18 +295,18 @@ generate_command() {
fi
result_command="${result_command}
--workdir=\"${workdir}\"
- --env=\"DISTROBOX_ENTER_PATH=${distrobox_enter_path}\""
+ --env \"DISTROBOX_ENTER_PATH=${distrobox_enter_path}\""
# Loop through all the environment vars
# and export them to the container.
set +o xtrace
# disable logging fot this snippet, or it will be too talkative.
for i in $(printenv | grep '=' | grep -Ev ' |"' |
- grep -Ev '^(HOST|HOSTNAME|HOME|PATH|SHELL|USER|XDG_.*_DIRS|_)'); do
+ grep -Ev '^(HOST|HOSTNAME|HOME|PATH|SHELL|XDG_.*_DIRS|^_)|`'); do
# We filter the environment so that we do not have strange variables,
# multiline or containing spaces.
# We also NEED to ignore the HOME variable, as this is set at create time
# and needs to stay that way to use custom home dirs.
- result_command="${result_command} --env=\"${i}\""
+ result_command="${result_command} --env \"${i}\""
done
# Start with the $PATH set in the container's config
@@ -328,7 +325,7 @@ generate_command() {
container_paths="${container_paths}:${standard_path}"
fi
done
- result_command="${result_command} --env=\"PATH=${container_paths}\""
+ result_command="${result_command} --env \"PATH=${container_paths}\""
# Ensure the standard FHS program paths are in XDG_DATA_DIRS environment
standard_paths="/usr/local/share /usr/share"
@@ -339,7 +336,7 @@ generate_command() {
container_paths="${container_paths}:${standard_path}"
fi
done
- result_command="${result_command} --env=\"XDG_DATA_DIRS=${container_paths}\""
+ result_command="${result_command} --env \"XDG_DATA_DIRS=${container_paths}\""
# Ensure the standard FHS program paths are in XDG_CONFIG_DIRS environment
standard_paths="/etc/xdg"
@@ -350,7 +347,7 @@ generate_command() {
container_paths="${container_paths}:${standard_path}"
fi
done
- result_command="${result_command} --env=\"XDG_CONFIG_DIRS=${container_paths}\""
+ result_command="${result_command} --env \"XDG_CONFIG_DIRS=${container_paths}\""
# re-enable logging if it was enabled previously.
if [ "${verbose}" -ne 0 ]; then
@@ -361,7 +358,15 @@ generate_command() {
result_command="${result_command} ${container_manager_additional_flags}"
# Run selected container with specified command.
- result_command="${result_command} ${container_name} ${container_command:-${container_shell}}"
+ result_command="${result_command} ${container_name}"
+
+ if [ -n "${container_command}" ]; then
+ result_command="${result_command} ${container_command}"
+ else
+ # if no command was specified, let's execute a command that will find
+ # and run the default shell for the user
+ result_command="${result_command} sh -c \"\\\$(getent passwd ${USER} | cut -f 7 -d :) -l"\"
+ fi
# Return generated command.
printf "%s" "${result_command}"
@@ -382,10 +387,7 @@ container_status="unknown"
eval "$(${container_manager} inspect --type container "${container_name}" --format \
'container_status={{.State.Status}};
{{range .Config.Env}}{{if slice . 0 5 | eq "HOME="}}container_home={{slice . 5 | printf "%q"}};{{end}}{{end}}
- {{range .Config.Env}}{{if slice . 0 6 | eq "SHELL="}}container_shell={{slice . 6 | printf "%q"}};{{end}}{{end}}
{{range .Config.Env}}{{if slice . 0 5 | eq "PATH="}}container_path={{slice . 5 | printf "%q"}}{{end}}{{end}}')"
-# Set SHELL as a login shell
-container_shell="$(basename "${container_shell}") -l"
# Check if the container is even there
if [ "${container_status}" = "unknown" ]; then
@@ -407,10 +409,15 @@ if [ "${container_status}" = "unknown" ]; then
case "${response}" in
y | Y | Yes | yes | YES)
# Ok, let's create the container with just 'distrobox create $container_name
+ create_command="$(dirname "${0}")/distrobox-create"
+ if [ "${rootful}" -ne 0 ]; then
+ create_command="${create_command} --root"
+ fi
+ create_command="${create_command} -i ${container_image} -n ${container_name}"
printf >&2 "Creating the container with command:\n"
- printf >&2 " distrobox create -i %s %s\n" "${container_image}" "${container_name}"
+ printf >&2 " %s\n" "${create_command}"
if [ "${dryrun}" -ne 1 ]; then
- "$(dirname "${0}")"/distrobox-create -i "${container_image}" -n "${container_name}"
+ eval "${create_command}"
fi
;;
n | N | No | no | NO)
@@ -437,6 +444,15 @@ if [ "${container_status}" != "running" ]; then
printf >&2 "run this command to follow along:\n\n"
printf >&2 " %s logs -f %s\n\n" "${container_manager}" "${container_name}"
+ # IMPORTANT STEP:
+ #
+ # Before starting, ensure we copy the entrypoint, the export and the host-exec utilities.
+ # This approach should solve the location-dependency, on systems like NixOS, or
+ # If one wants to change the installation path of distrobox (eg: from /usr/bin to ~/.local/bin).
+ ${container_manager} cp "${distrobox_entrypoint_path}" "${container_name}":/usr/bin/entrypoint
+ ${container_manager} cp "${distrobox_export_path}" "${container_name}":/usr/bin/distrobox-export
+ ${container_manager} cp "${distrobox_hostexec_path}" "${container_name}":/usr/bin/distrobox-host-exec
+
log_timestamp="$(date +%FT%T.%N%:z)"
${container_manager} start "${container_name}" > /dev/null
# Check if the container is going in error status earlier than the
@@ -453,23 +469,32 @@ if [ "${container_status}" != "running" ]; then
fi
printf >&2 "%-40s\t" " Starting container..."
+ mkdir -p "${HOME}/.cache/"
+ touch "${HOME}/.cache/.${container_name}.fifo"
+ touch "${HOME}/.cache/.${container_name}.status"
while true; do
# save starting loop timestamp in temp variable, we'll use it
# after to let logs command minimize possible holes
log_timestamp_new="$(date +%FT%T.%N%:z)"
- ${container_manager} logs --since "${log_timestamp}" "${container_name}" 2> /dev/null > "/tmp/.${container_name}.fifo"
+ ${container_manager} logs \
+ --since "${log_timestamp}" "${container_name}" 2> /dev/null > "${HOME}/.cache/.${container_name}.fifo"
# read logs from log_timestamp to now, line by line
while IFS= read -r line; do
case "${line}" in
- *"Error"*)
+ *"Error:"*)
printf >&2 "\033[31m %s\n\033[0m" "${line}"
exit 1
;;
- *"Warning"*)
+ *"Warning:"*)
printf >&2 "\n\033[33m %s\033[0m" "${line}"
;;
*"distrobox:"*)
- printf >&2 "\033[32m [ OK ]\n\033[0m%-40s\t" "$(echo "${line}" | cut -d':' -f2-)"
+ current_line="$(echo "${line}" | cut -d':' -f2-)"
+ # Save current line in the status, to avoid printing the same line multiple times
+ if ! grep -q "${current_line}" "${HOME}/.cache/.${container_name}.status"; then
+ printf >&2 "\033[32m [ OK ]\n\033[0m%-40s\t" "${current_line}"
+ printf "%s\n" "${current_line}" > "${HOME}/.cache/.${container_name}.status"
+ fi
;;
*"container_setup_done"*)
printf >&2 "\033[32m [ OK ]\n\033[0m"
@@ -477,14 +502,14 @@ if [ "${container_status}" != "running" ]; then
;;
*) ;;
esac
- done < "/tmp/.${container_name}.fifo"
+ done < "${HOME}/.cache/.${container_name}.fifo"
# Register new timestamp where to start logs from.
log_timestamp="${log_timestamp_new}"
- sleep 1
done
# cleanup fifo
- rm -f "/tmp/.${container_name}.fifo"
+ rm -f "${HOME}/.cache/.${container_name}.fifo"
+ rm -f "${HOME}/.cache/.${container_name}.status"
printf >&2 "\nContainer Setup Complete!\n"
fi
diff --git a/distrobox-ephemeral b/distrobox-ephemeral
new file mode 100755
index 0000000..a308a65
--- /dev/null
+++ b/distrobox-ephemeral
@@ -0,0 +1,136 @@
+#!/bin/sh
+# SPDX-License-Identifier: GPL-3.0-only
+#
+# This file is part of the distrobox project:
+# https://github.com/89luca89/distrobox
+#
+# Copyright (C) 2021 distrobox contributors
+#
+# distrobox is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License version 3
+# as published by the Free Software Foundation.
+#
+# distrobox is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with distrobox; if not, see <http://www.gnu.org/licenses/>.
+
+# POSIX
+# Optional env variables:
+# DBX_CONTAINER_MANAGER
+# DBX_CONTAINER_NAME
+# DBX_NON_INTERACTIVE
+# DBX_SUDO_PROGRAM
+
+# Dont' run this command as sudo.
+if [ "$(id -u)" -eq 0 ]; then
+ printf >&2 "Running %s as sudo is not supported.\n" "$(basename "${0}")"
+ printf >&2 " try instead running:\n"
+ printf >&2 " %s --root %s\n" "$(basename "${0}")" "$*"
+ exit 1
+fi
+
+container_command=""
+create_flags=""
+distrobox_path="$(dirname "${0}")"
+extra_flags=""
+rootful=0
+verbose=0
+version="1.4.0"
+
+# Print usage to stdout.
+# Arguments:
+# None
+# Outputs:
+# print usage with examples.
+show_help() {
+ cat << EOF
+distrobox version: ${version}
+
+Usage:
+
+ distrobox-ephemeral --name container-name [--force]
+
+Options:
+
+ --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
+ --verbose/-v: show more verbosity
+ --help/-h: show this message
+ --/-e: end arguments execute the rest as command to execute at login default: bash -l
+ --version/-V: show version
+
+See also:
+
+ distrobox-create --help
+
+ for a list of additional flags to specify during the creation.
+ distrobox-ephemeral can use all flags from distrobox-create.
+
+EOF
+}
+
+# Parse arguments
+while :; do
+ case $1 in
+ -h | --help)
+ # Call a "show_help" function to display a synopsis, then exit.
+ show_help
+ exit 0
+ ;;
+ -r | --root)
+ shift
+ rootful=1
+ ;;
+ -v | --verbose)
+ verbose=1
+ shift
+ ;;
+ -V | --version)
+ printf "distrobox: %s\n" "${version}"
+ exit 0
+ ;;
+ -e | --exec | --)
+ shift
+ container_command="-- $*"
+ break
+ ;;
+ *) # Default case: If no more options then break out of the loop.
+ # If we have a flagless option and container_name is not specified
+ # then let's accept argument as container_name
+ if [ -n "$1" ]; then
+ create_flags="${create_flags} $1"
+ shift
+ else
+ break
+ fi
+ ;;
+ esac
+done
+
+set -o errexit
+set -o nounset
+# set verbosity
+if [ "${verbose}" -ne 0 ]; then
+ set -o xtrace
+ extra_flags="${extra_flags} --verbose"
+fi
+
+# prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
+if [ "${rootful}" -ne 0 ]; then
+ extra_flags="${extra_flags} --root"
+fi
+
+name=$(mktemp -u distrobox-XXXXXXXXXX)
+# shellcheck disable=SC2086
+"${distrobox_path}"/distrobox-create --name ${name} --yes ${create_flags} ${extra_flags}
+# shellcheck disable=SC2086
+"${distrobox_path}"/distrobox-enter "${name}" ${container_command} ${extra_flags}
+# shellcheck disable=SC2086
+"${distrobox_path}"/distrobox-stop "${name}" --yes ${extra_flags}
+# shellcheck disable=SC2086
+"${distrobox_path}"/distrobox-rm --force "${name}" --yes ${extra_flags}
diff --git a/distrobox-export b/distrobox-export
index 5ecf168..eb49228 100755
--- a/distrobox-export
+++ b/distrobox-export
@@ -43,7 +43,7 @@ host_home="${DISTROBOX_HOST_HOME:-"${HOME}"}"
is_sudo=""
rootful=""
verbose=0
-version="1.3.1"
+version="1.4.0"
# We depend on some commands, let's be sure we have them
base_dependencies="basename grep sed find"
@@ -79,7 +79,7 @@ Options:
Defaults to (on \$container_name)
--export-path/-ep: path where to export the binary
--extra-flags/-ef: extra flags to add to the command
- --sudo/-S: specify if the exported item should be ran as sudo
+ --sudo/-S: specify if the exported item should be run as sudo
--help/-h: show this message
--verbose/-v: show more verbosity
--version/-V: show version
@@ -215,7 +215,17 @@ if [ -n "${exported_bin}" ] && [ -z "${dest_path}" ]; then
fi
# We can assume this as we set it the same as container name during creation.
-container_name=$(uname -n | cut -d'.' -f1)
+if [ -e /.dockerenv ]; then
+ # we're in docker, let's use this trick
+ container_name=$(grep "memory:/" < /proc/self/cgroup | sed 's|.*/||')
+elif [ -e /run/.containerenv ]; then
+ # we're in podman, use this other trick
+ container_name=$(grep "name=" /run/.containerenv | cut -d'=' -f2- | tr -d '"')
+else
+ # fallback to a more simple way but error prone
+ container_name=$(uname -n | cut -d'.' -f1)
+fi
+
# Prefix to add to an existing command to work throught the container
container_command_prefix="${DISTROBOX_ENTER_PATH:-"distrobox-enter"} ${rootful} -n ${container_name} -- '${is_sudo} "
if [ -z "${exported_app_label}" ]; then
@@ -234,9 +244,9 @@ generate_script() {
# name: ${container_name}
if [ ! -f /run/.containerenv ] && [ ! -f /.dockerenv ]; then
${DISTROBOX_ENTER_PATH:-"distrobox-enter"} ${rootful} -n ${container_name} -- \
- ${is_sudo} ${exported_bin} ${extra_flags} \$@
+${is_sudo} ${exported_bin} ${extra_flags} "\$@"
else
- ${exported_bin} \$@
+ ${exported_bin} "\$@"
fi
EOF
return $?
@@ -303,10 +313,29 @@ export_binary() {
# or error code.
export_application() {
- # Find desktop file for the application to export
- desktop_files=$(grep -ril "Exec=.*${exported_app}" \
- /usr/share/applications/* \
- /var/lib/flatpak/exports/share/applications/* 2> /dev/null || :)
+ [ -d /usr/share/applications ] && canon_dirs="/usr/share/applications"
+ [ -d /usr/local/share/applications ] && canon_dirs="${canon_dirs} /usr/local/share/applications"
+ [ -d /var/lib/flatpak/exports/share/applications ] &&
+ canon_dirs="${canon_dirs} /var/lib/flatpak/exports/share/applications"
+ [ -d "${HOME}/.local/share/applications" ] && canon_dirs="${canon_dirs} ${HOME}/.local/share/applications"
+
+ # In this phase we search for applications to export.
+ # First find command will grep throught all files in the canonical directories
+ # and only list files that contain the $exported_app, excluding those that
+ # already contains a distrobox-enter command. So skipping already exported apps.
+ # Second find will list all files that contain the name specified, so that
+ # it is possible to export an app not only by its executable name but also
+ # by its launcher name.
+ desktop_files=$(
+ # shellcheck disable=SC2086
+ find ${canon_dirs} \
+ -type f \
+ -exec grep -qle "Exec=.*${exported_app}.*" {} \; \
+ -exec grep -Le "Exec=.*${DISTROBOX_ENTER_PATH:-"distrobox-enter"}.*" {} \;
+ # shellcheck disable=SC2086
+ find ${canon_dirs} \
+ -name "${exported_app}*"
+ )
# Ensure the app we're exporting is installed
# Check that we found some desktop files first.
@@ -394,8 +423,8 @@ export_application() {
# in the end we add the final quote we've opened in the "container_command_prefix"
if ! grep -q "StartupWMClass" "/run/host${host_home}/.local/share/applications/${desktop_home_file}"; then
- printf "StartupWMClass=%s\n" "${exported_app}" >> \
- "/run/host${host_home}/.local/share/applications/${desktop_home_file}"
+ printf "StartupWMClass=%s\n" "${exported_app}" >> "\
+/run/host${host_home}/.local/share/applications/${desktop_home_file}"
fi
# In case of an icon in a non canonical path, we need to replace the path
# in the desktop file.
diff --git a/distrobox-generate-entry b/distrobox-generate-entry
new file mode 100755
index 0000000..b5f9c60
--- /dev/null
+++ b/distrobox-generate-entry
@@ -0,0 +1,282 @@
+#!/bin/sh
+# SPDX-License-Identifier: GPL-3.0-only
+#
+# This file is part of the distrobox project:
+# https://github.com/89luca89/distrobox
+#
+# Copyright (C) 2021 distrobox contributors
+#
+# distrobox is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License version 3
+# as published by the Free Software Foundation.
+#
+# distrobox is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with distrobox; if not, see <http://www.gnu.org/licenses/>.
+
+# POSIX
+trap '[ "$?" -ne 0 ] && printf "\nAn error occurred\n"' EXIT
+
+all=0
+container_manager="autodetect"
+container_name="my-distrobox"
+delete=0
+icon="auto"
+icon_default="${HOME}/.local/share/icons/terminal-distrobox-icon.png"
+verbose=0
+version="1.4.0"
+
+# Source configuration files, this is done in an hierarchy so local files have
+# priority over system defaults
+# leave priority to environment variables.
+config_files="
+ /usr/share/distrobox/distrobox.conf
+ /usr/etc/distrobox/distrobox.conf
+ /etc/distrobox/distrobox.conf
+ ${XDG_CONFIG_HOME:-"${HOME}/.config"}/distrobox/distrobox.conf
+ ${HOME}/.distroboxrc
+"
+for config_file in ${config_files}; do
+ # Shellcheck will give error for sourcing a variable file as it cannot follow
+ # it. We don't care so let's disable this linting for now.
+ # shellcheck disable=SC1090
+ [ -e "${config_file}" ] && . "${config_file}"
+done
+[ -n "${DBX_CONTAINER_MANAGER}" ] && container_manager="${DBX_CONTAINER_MANAGER}"
+[ -n "${DBX_CONTAINER_NAME}" ] && container_name="${DBX_CONTAINER_NAME}"
+
+# Print usage to stdout.
+# Arguments:
+# None
+# Outputs:
+# print usage with examples.
+show_help() {
+ cat << EOF
+distrobox version: ${version}
+
+Usage:
+
+ distrobox-generate-entry container-name [--delete] [--icon [auto,/path/to/icon]]
+
+Options:
+
+ --help/-h: show this message
+ --all/-a: perform for all distroboxes
+ --delete/-d: delete the entry
+ --icon/-i: specify a custom icon [/path/to/icon] (default auto)
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+EOF
+}
+
+if [ $# -eq 0 ]; then
+ show_help
+ exit
+fi
+
+# Parse arguments
+while :; do
+ case $1 in
+ -h | --help)
+ # Call a "show_help" function to display a synopsis, then exit.
+ show_help
+ exit 0
+ ;;
+ -v | --verbose)
+ verbose=1
+ shift
+ ;;
+ -V | --version)
+ printf "distrobox: %s\n" "${version}"
+ exit 0
+ ;;
+ -d | --delete)
+ delete=1
+ shift
+ ;;
+ -a | --all)
+ all=1
+ shift
+ ;;
+ -i | --icon)
+ if [ -n "$2" ]; then
+ icon="$2"
+ shift
+ shift
+ fi
+ ;;
+ --) # End of all options.
+ shift
+ break
+ ;;
+ -*) # Invalid options.
+ printf >&2 "ERROR: Invalid flag '%s'\n\n" "$1"
+ show_help
+ exit 1
+ ;;
+ *) # Default case: If no more options then break out of the loop.
+ # If we have a flagless option and container_name is not specified
+ # then let's accept argument as container_name
+ if [ -n "$1" ]; then
+ container_name="$1"
+ shift
+ else
+ break
+ fi
+ ;;
+ esac
+done
+
+set -o errexit
+set -o nounset
+# set verbosity
+if [ "${verbose}" -ne 0 ]; then
+ set -o xtrace
+fi
+
+if [ -z "${container_name}" ]; then
+ printf >&2 "Please specify the name of the container.\n"
+ exit 1
+fi
+
+if [ "${all}" -ne 0 ]; then
+ container_names="$(distrobox list --no-color | tail -n +2 | cut -d'|' -f2 | tr -d ' ')"
+ for container_name in ${container_names}; do
+ if [ "${delete}" -ne 0 ]; then
+ "${0}" "${container_name}" --delete
+ continue
+ fi
+ "${0}" "${container_name}"
+ done
+ exit
+fi
+
+# If we delete, just ask confirmation and exit.
+if [ "${delete}" -ne 0 ]; then
+ rm -f "${HOME}/.local/share/applications/${container_name}.desktop"
+ printf "%s\n" "${container_name}"
+ exit
+fi
+
+# We depend on a container manager let's be sure we have it
+# First we use podman, else docker
+case "${container_manager}" in
+ autodetect)
+ if command -v podman > /dev/null; then
+ container_manager="podman"
+ container_manager_cp_command="podman cp"
+ elif command -v docker > /dev/null; then
+ container_manager="docker"
+ container_manager_cp_command="docker cp -L"
+ fi
+ ;;
+ podman)
+ container_manager="podman"
+ container_manager_cp_command="podman cp"
+ ;;
+ docker)
+ container_manager="docker"
+ container_manager_cp_command="docker cp -L"
+ ;;
+ *)
+ printf >&2 "Invalid input %s.\n" "${container_manager}"
+ printf >&2 "The available choices are: 'autodetect', 'podman', 'docker'\n"
+ ;;
+esac
+
+# Be sure we have a container manager to work with.
+if ! command -v "${container_manager}" > /dev/null; then
+ # Error: we need at least one between docker or podman.
+ printf >&2 "Missing dependency: we need a container manager.\n"
+ printf >&2 "Please install one of podman or docker.\n"
+ printf >&2 "You can follow the documentation on:\n"
+ printf >&2 "\tman distrobox-compatibility\n"
+ printf >&2 "or:\n"
+ printf >&2 "\thttps://github.com/89luca89/distrobox/blob/main/docs/compatibility.md\n"
+ exit 127
+fi
+
+# add verbose if -v is specified
+if [ "${verbose}" -ne 0 ]; then
+ container_manager="${container_manager} --log-level debug"
+fi
+
+if ! ${container_manager} inspect --type container "${container_name}" > /dev/null; then
+ printf >&2 "Cannot find container %s. Please create it first.\n" "${container_name}"
+ exit 1
+fi
+
+# Ensure the destination dir exists.
+mkdir -p "${HOME}/.local/share/applications"
+mkdir -p "${HOME}/.local/share/icons/distrobox"
+
+distrobox_path="$(dirname "$(realpath "${0}")")"
+entry_name="$(echo "${container_name}" | cut -c1 | tr "[:lower:]" "[:upper:]")$(echo "${container_name}" | cut -c2-)"
+
+if [ "${icon}" = "auto" ]; then
+ # Set icon to the generic terminal as a fallback.
+ icon="${icon_default}"
+ # This is a NON comprehensive list of logos of the most popular distirbutions. If you find logos for
+ # other supported distros, add it here.
+ DISTRO_ICON_MAP="
+ alma:https://upload.wikimedia.org/wikipedia/commons/e/ec/AlmaLinux_Icon_Logo.png
+ alpine:https://d1q6f0aelx0por.cloudfront.net/product-logos/library-alpine-logo.png
+ arch:https://upload.wikimedia.org/wikipedia/commons/thumb/b/bb/Archlogo900.png/640px-Archlogo900.png
+ centos:https://upload.wikimedia.org/wikipedia/commons/6/63/CentOS_color_logo.svg
+ clear--os:https://d1q6f0aelx0por.cloudfront.net/product-logos/library-clearlinux-logo.png
+ debian:https://free-astro.org/images/0/04/Debian_logo.png
+ fedora:https://upload.wikimedia.org/wikipedia/commons/4/41/Fedora_icon_%282021%29.svg
+ gentoo:https://upload.wikimedia.org/wikipedia/commons/e/e2/Logo-gentoo.png
+ opensuse-leap:https://en.opensuse.org/images/4/44/Button-filled-colour.png
+ opensuse-tumbleweed:https://en.opensuse.org/images/4/44/Button-filled-colour.png
+ rhel:https://avatars.githubusercontent.com/u/12718395?.png
+ rocky:https://raw.githubusercontent.com/rocky-linux/rocky-logos/r9/pixmaps/fedora-logo-sprite.png
+ slackware:https://distrowatch.com/images/yvzhuwbpy/slackware.png
+ ubuntu:https://upload.wikimedia.org/wikipedia/commons/a/ab/Logo-ubuntu_cof-orange-hex.svg
+ void:https://voidlinux.org/assets/img/void_bg.png
+ "
+ # Try to detect container's distribution by using /etc/os-release
+ ${container_manager_cp_command} "${container_name}":/etc/os-release /tmp/"${container_name}".os-release
+ container_distro="$(grep "^ID=" /tmp/"${container_name}".os-release |
+ cut -d'=' -f2- |
+ sed "s|linux||g" |
+ tr -d ' ' |
+ tr -d '"')"
+ rm -f /tmp/"${container_name}".os-release
+
+ icon_url="$(echo "${DISTRO_ICON_MAP}" | grep "${container_distro}:" | cut -d':' -f2-)"
+ if [ -n "${icon_url}" ]; then
+ icon_extension="${icon_url##*.}"
+
+ if wget -c -q "${icon_url}" -O "${HOME}/.local/share/icons/distrobox/${container_distro}.${icon_extension}"; then
+ icon="${HOME}/.local/share/icons/distrobox/${container_distro}.${icon_extension}"
+ else
+ # Wget failed for some reasons. Default to generic terminal icon as declared at the beginning.
+ printf >&2 "Warning: Failed to download icon. Defaulting to generic one.\n"
+ fi
+ else
+ # Distribution not found in the list. Default to generic terminal icon as declared at the beginning.
+ printf >&2 "Warning: Distribution not found in default icon set. Defaulting to generic one.\n"
+ fi
+fi
+
+cat << EOF > "${HOME}/.local/share/applications/${container_name}.desktop"
+[Desktop Entry]
+Name=${entry_name}
+GenericName=Terminal entering ${entry_name}
+Comment=Terminal entering ${entry_name}
+Category=Distrobox;System;Utility"
+Exec=${distrobox_path}/distrobox enter ${container_name}
+Icon=${icon}
+Keywords=distrobox;
+NoDisplay=false
+Terminal=true
+TryExec=${distrobox_path}/distrobox
+Type=Application
+EOF
+
+printf "%s\n" "${container_name}"
diff --git a/distrobox-host-exec b/distrobox-host-exec
index 2c208c8..d35af4d 100755
--- a/distrobox-host-exec
+++ b/distrobox-host-exec
@@ -18,13 +18,17 @@
# You should have received a copy of the GNU General Public License
# along with distrobox; if not, see <http://www.gnu.org/licenses/>.
-trap '[ "$?" -ne 0 ] && printf "\nAn error occurred\n"' EXIT
-
# Defaults
-distrobox_host_exec_default_command="/bin/sh"
-
+host_command=""
+non_interactive=0
+# If we're in a non-interactive shell, let's act accordingly
+if [ ! -t 1 ]; then
+ non_interactive=1
+fi
+distrobox_host_exec_default_command="${SHELL:-/bin/sh}"
+host_spawn_version="1.2.1"
verbose=0
-version="1.3.1"
+version="1.4.0"
# Print usage to stdout.
# Arguments:
@@ -49,43 +53,57 @@ Options:
--help/-h: show this message
--verbose/-v: show more verbosity
--version/-V: show version
+ --yes/-Y: Automatically answer yes to prompt:
+ host-spawn will be installed on the guest system
+ if host-spawn is not detected.
+ This behaviour is default when running in a non-interactive shell.
EOF
}
+# If we're a symlink to a command, use that as command to exec, and skip arg parsing.
+if [ "$(basename "${0}")" != "distrobox-host-exec" ]; then
+ host_command="$(basename "${0}")"
+fi
# Parse arguments
-while :; do
- case $1 in
- -h | --help)
- # Call a "show_help" function to display a synopsis, then exit.
- show_help
- exit 0
- ;;
- -v | --verbose)
- verbose=1
- shift
- ;;
- -V | --version)
- printf "distrobox: %s\n" "${version}"
- exit 0
- ;;
- --) # End of all options.
- shift
- ;;
- -*) # Invalid options.
- printf >&2 "ERROR: Invalid flag '%s'\n\n" "$1"
- show_help
- exit 1
- ;;
- *)
- command=${distrobox_host_exec_default_command}
- if [ -n "$1" ]; then
- command=$1
+if [ -z "${host_command}" ]; then
+ # Skip argument parsing if we're a symlink
+ while :; do
+ case $1 in
+ -h | --help)
+ # Call a "show_help" function to display a synopsis, then exit.
+ show_help
+ exit 0
+ ;;
+ -v | --verbose)
+ verbose=1
shift
- fi
- break
- ;;
- esac
-done
+ ;;
+ -V | --version)
+ printf "distrobox: %s\n" "${version}"
+ exit 0
+ ;;
+ -Y | --yes)
+ non_interactive=1
+ shift
+ ;;
+ --) # End of all options.
+ shift
+ ;;
+ -*) # Invalid options.
+ printf >&2 "ERROR: Invalid flag '%s'\n\n" "$1"
+ show_help
+ exit 1
+ ;;
+ *)
+ if [ -n "$1" ]; then
+ host_command=$1
+ shift
+ fi
+ break
+ ;;
+ esac
+ done
+fi
set -o errexit
set -o nounset
@@ -100,26 +118,42 @@ if [ ! -f /run/.containerenv ] && [ ! -f /.dockerenv ]; then
exit 126
fi
-mode=flatpak
-result_command="flatpak-spawn --host --forward-fd=1 --forward-fd=2 "
-
-if ! command -v flatpak-spawn > /dev/null; then
- printf "WARNING: flatpak-spawn not found!\n"
- printf "We recommend installing it and then trying distrobox-host-exec again.\n\n"
- printf "Alternatively, we can try an different (chroot-based) approach, but please\n"
- printf "be aware that it has severe limitations and some commands will not work!\n\n"
- printf "Do you really want to continue without installing flatpak-spawn? [y/N] "
- read -r response
- response=${response:-"N"}
+if [ -z "${host_command}" ]; then
+ host_command="${distrobox_host_exec_default_command}"
+fi
+# Setup host-spawn as a way to execute commands back on the host
+if ! command -v host-spawn > /dev/null ||
+ [ "$(host-spawn --version)" != "${host_spawn_version}" ]; then
+
+ # if non-interactive flag flag hasn't been set
+ if [ "${non_interactive}" -eq 0 ]; then
+ # Prompt to download it.
+ printf "Warning: host-spawn not found or version is too old!\n"
+ printf "Do you want to install host-spawn utility? [Y/n] "
+ read -r response
+ response=${response:-"Y"}
+ else
+ response="yes"
+ fi
# Accept only y,Y,Yes,yes,n,N,No,no.
case "${response}" in
y | Y | Yes | yes | YES)
- mode=chroot
- result_command="sudo -E chroot --userspec=$(id -u):$(id -g) /run/host/ /usr/bin/env "
+ # Download matching version with current distrobox
+ if ! curl -L \
+ "https://github.com/1player/host-spawn/releases/download/${host_spawn_version}/host-spawn-$(uname -m)" \
+ -o /tmp/host-spawn; then
+
+ printf "Error: Cannot download host-spawn\n"
+ exit 1
+ fi
+ if [ -e /tmp/host-spawn ]; then
+ sudo mv /tmp/host-spawn /usr/bin/
+ sudo chmod +x /usr/bin/host-spawn
+ fi
;;
n | N | No | no | NO)
- printf "Good choice! Go get flatpak-spawn.\n"
+ printf "Installation aborted, please install host-spawn.\n"
exit 0
;;
*) # Default case: If no more options then break out of the loop.
@@ -128,16 +162,29 @@ if ! command -v flatpak-spawn > /dev/null; then
exit 1
;;
esac
+
fi
-# Let's also pass back the environment
-for i in $(printenv | grep "=" | grep -Ev ' |"' | grep -Ev "^(_)"); do
- if [ "${mode}" = "chroot" ]; then
- result_command="${result_command} ${i}"
- else
- result_command="${result_command} --env=${i} "
- fi
-done
+###
+# This workaround is needed because of a bug in gio (used by xdg-open) where
+# a race condition happens when allocating a pty, leading to the command
+# being killed before having time to be executed.
+#
+# https://gitlab.gnome.org/GNOME/glib/-/issues/2695
+# https://github.com/1player/host-spawn/issues/7
+#
+# As an (ugly) workaround, we will not allocate a pty for those commands.
+###
+# Also, we don't initialize a pty, if we're not in a tty.
+if [ "$(basename "${host_command}")" = "xdg-open" ] ||
+ [ "$(basename "${host_command}")" = "gio" ] ||
+ [ ! -t 1 ]; then
+
+ host-spawn --no-pty "${host_command}" "$@"
+ # Exit here, we don't continue execution
+ exit $?
+fi
-# Eval the generated command.
-exec ${result_command} sh -c " cd ${PWD} && ${command} $* "
+host-spawn "${host_command}" "$@"
+# Exit here, we don't continue execution
+exit $?
diff --git a/distrobox-init b/distrobox-init
index df431c9..1a2bea6 100755
--- a/distrobox-init
+++ b/distrobox-init
@@ -29,9 +29,10 @@ trap '[ "$?" -ne 0 ] && printf "Error: An error occurred\n"' EXIT
# Defaults
init=0
init_hook=""
+upgrade=0
pre_init_hook=""
verbose=0
-version="1.3.1"
+version="1.4.0"
# Print usage to stdout.
# Arguments:
# None
@@ -54,6 +55,7 @@ Options:
--help/-h: show this message
--init/-I: whether to use or not init
--pre-init-hooks: commands to execute prior to init
+ --upgrade/-U: run init in upgrade mode
--verbose/-v: show more verbosity
--version/-V: show version
--: end arguments execute the rest as command to execute during init
@@ -76,6 +78,10 @@ while :; do
printf "distrobox: %s\n" "${version}"
exit 0
;;
+ -U | --upgrade)
+ shift
+ upgrade=1
+ ;;
-n | --name)
if [ -n "$2" ]; then
container_user_name="$2"
@@ -133,13 +139,6 @@ while :; do
esac
done
-set -o errexit
-set -o nounset
-# set verbosity
-if [ "${verbose}" -ne 0 ]; then
- set -o xtrace
-fi
-
# Check we're running inside a container and not on the host
if [ ! -f /run/.containerenv ] && [ ! -f /.dockerenv ]; then
printf >&2 "You must run %s inside a container!\n" " $(basename "$0")"
@@ -151,10 +150,18 @@ fi
# Ensure the foundamental variables are set and not empty, we will not proceed if
# they are not all set.
-[ -z "${container_user_gid}" ] && printf "Error: Invalid arguments, missing user gud\n" && exit 2
-[ -z "${container_user_home}" ] && printf "Error: Invalid argument, missing user home\n" && exit 2
-[ -z "${container_user_name}" ] && printf "Error: Invalid arguments, missing username\n" && exit 2
-[ -z "${container_user_uid}" ] && printf "Error: Invalid arguments, missing user uid\n" && exit 2
+if [ "${upgrade}" -eq 0 ]; then
+ [ -z "${container_user_gid}" ] && printf "Error: Invalid arguments, missing user gud\n" && exit 2
+ [ -z "${container_user_home}" ] && printf "Error: Invalid argument, missing user home\n" && exit 2
+ [ -z "${container_user_name}" ] && printf "Error: Invalid arguments, missing username\n" && exit 2
+ [ -z "${container_user_uid}" ] && printf "Error: Invalid arguments, missing user uid\n" && exit 2
+fi
+set -o errexit
+set -o nounset
+# set verbosity
+if [ "${verbose}" -ne 0 ]; then
+ set -o xtrace
+fi
# Bind mount or error.
# Arguments:
@@ -212,6 +219,7 @@ if [ -n "${pre_init_hook}" ]; then
eval ${pre_init_hook}
fi
+###############################################################################
printf "distrobox: Installing basic packages...\n"
# Extract shell name from the $SHELL environment variable
# If not present as package in the container, we want to install it.
@@ -223,7 +231,7 @@ if [ "${shell_pkg}" = "ash" ]; then
fi
# Check if dependencies are met for the script to run.
-if ! command -v find || ! command -v mount || ! command -v passwd ||
+if [ "${upgrade}" -ne 0 ] || ! command -v find || ! command -v mount || ! command -v passwd ||
! command -v sudo || ! command -v useradd || ! command -v diff ||
! command -v pinentry || ! command -v wget || ! command -v curl ||
! command -v less || ! command -v bc ||
@@ -235,6 +243,11 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
# sudo, mount, find
# passwd, groupadd and useradd
if command -v apk; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ apk upgrade
+ exit
+ fi
# Check if shell_pkg is available in distro's repo. If not we
# fall back to bash, and we set the SHELL variable to bash so
# that it is set up correctly for the user.
@@ -259,6 +272,12 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
vte3
elif command -v apt-get; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ apt update
+ apt upgrade -y
+ exit
+ fi
# In Ubuntu official images, dpkg is configured to ignore locale and docs
# This however, results in a rather poor out-of-the-box experience
# So, let's enable them.
@@ -275,8 +294,10 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
fi
apt-get install -y \
"${shell_pkg}" \
+ apt-utils \
bc \
curl \
+ dialog \
diffutils \
findutils \
less \
@@ -291,6 +312,11 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
util-linux
elif command -v dnf; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ dnf upgrade -y
+ exit
+ fi
# In dnf family official images, dnf is configured to ignore locale and docs
# This however, results in a rather poor out-of-the-box experience
# So, let's enable them.
@@ -345,6 +371,11 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
vte
elif command -v microdnf; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ microdnf upgrade -y
+ exit
+ fi
# Check if shell_pkg is available in distro's repo. If not we
# fall back to bash, and we set the SHELL variable to bash so
# that it is set up correctly for the user.
@@ -369,10 +400,16 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
# vte-profile
elif command -v pacman; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ pacman -Syyu --noconfirm
+ exit
+ fi
# In archlinux official images, pacman is configured to ignore locale and docs
# This however, results in a rather poor out-of-the-box experience
# So, let's enable them.
sed -i "s|NoExtract.*||g" /etc/pacman.conf
+ sed -i "s|NoProgressBar.*||g" /etc/pacman.conf
# Check if shell_pkg is available in distro's repo. If not we
# fall back to bash, and we set the SHELL variable to bash so
@@ -399,6 +436,11 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
vte-common
elif command -v slackpkg; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ yes | slackpkg upgrade-all -default_answer=yes -batch=yes
+ exit
+ fi
slackpkg update
# Check if shell_pkg is available in distro's repo. If not we
# fall back to bash, and we set the SHELL variable to bash so
@@ -424,6 +466,11 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
util-linux
elif command -v swupd; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ swupd update
+ exit
+ fi
# Here we do not handle shell_pkg as shells are already all bundled
# together in "shells"
swupd bundle-add \
@@ -436,6 +483,13 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
wget
elif command -v xbps-install; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ xbps-install -Syu
+ exit
+ fi
+ # Ensure we avoid errors by keeping xbps updated
+ xbps-install -Syu xbps
# Check if shell_pkg is available in distro's repo. If not we
# fall back to bash, and we set the SHELL variable to bash so
# that it is set up correctly for the user.
@@ -458,6 +512,11 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
util-linux
elif command -v yum; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ yum upgrade -y
+ exit
+ fi
# In yum family official images, yum is configured to ignore locale and docs
# This however, results in a rather poor out-of-the-box experience
# So, let's enable them.
@@ -488,6 +547,11 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
vte-profile
elif command -v zypper; then
+ # If we need to upgrade, do it and exit, no further action required.
+ if [ "${upgrade}" -ne 0 ]; then
+ zypper dup -y
+ exit
+ fi
if ! zypper install -y "${shell_pkg}"; then
SHELL="/bin/bash"
shell_pkg="bash"
@@ -528,9 +592,10 @@ if ! command -v find || ! command -v mount || ! command -v passwd ||
# Exit as command not found
exit 127
fi
-
fi
+###############################################################################
+###############################################################################
printf "distrobox: Setting up read-only mounts...\n"
# We'll also bind mount in READ-ONLY useful directories from the host
HOST_MOUNTS_RO="
@@ -540,7 +605,9 @@ HOST_MOUNTS_RO="
for host_mount_ro in ${HOST_MOUNTS_RO}; do
mount_bind /run/host"${host_mount_ro}" "${host_mount_ro}" ro
done
+###############################################################################
+###############################################################################
printf "distrobox: Setting up read-write mounts...\n"
# We'll also bind mount READ-WRITE useful mountpoints to pass external drives and libvirt from
# the host to the container
@@ -568,6 +635,7 @@ for host_mount in ${HOST_MOUNTS}; do
done
HOST_MOUNTS_RO_INIT="
+ /etc/localtime
/run/systemd/journal
/run/systemd/resolve
/run/systemd/seats
@@ -580,11 +648,13 @@ HOST_MOUNTS_RO_INIT="
# it to be in /home. In the hosts systems this is fixed by using a symlink.
# Do something similar here with a bind mount.
if [ -e "/var/home/${container_user_name}" ] && [ ! -e "/home/${container_user_name}" ]; then
- if ! mount_bind /run/host/var/home /home rw; then
+ if ! mount_bind "/run/host/var/home/${container_user_name}" "/home/${container_user_name}" rw; then
printf "Warning: Cannot bind mount %s to /run/host%s\n" "/var/home" "/home"
fi
fi
+###############################################################################
+###############################################################################
printf "distrobox: Setting up host's sockets integration...\n"
# Find all the user's socket and mount them inside the container
# this will allow for continuity of functionality between host and container
@@ -611,7 +681,9 @@ for host_socket in ${host_sockets}; do
fi
fi
done
+###############################################################################
+###############################################################################
printf "distrobox: Integrating host's themes, icons, fonts...\n"
# Themes and icons integration works using a bind mount inside the container
# of the host's themes and icons directory. This ensures that the host's home will
@@ -628,14 +700,17 @@ if ! mount_bind "/run/host/usr/share/fonts" "/usr/local/share/fonts" rw; then
printf "Warning: Cannot bind mount /run/host/usr/share/fonts to /usr/local/share/fonts\n"
printf "Warning: Fonts integration with the host is disabled.\n"
fi
+###############################################################################
printf "distrobox: Setting up package manager exceptions...\n"
+
+###############################################################################
# In case of an RPM distro, we can specify that our bind_mount directories
# are in fact net shares. This prevents conflicts during package installations.
if [ -d "/usr/lib/rpm/macros.d/" ]; then
+ printf "distrobox: Setting up rpm exceptions...\n"
# Loop through all the environment vars
# and export them to the container.
- set +o xtrace
net_mounts=""
for net_mount in \
${HOST_MOUNTS_RO} ${HOST_MOUNTS} \
@@ -646,36 +721,30 @@ if [ -d "/usr/lib/rpm/macros.d/" ]; then
net_mounts="${net_mount}:${net_mounts}"
done
- # re-enable logging if it was enabled previously.
- if [ "${verbose}" -ne 0 ]; then
- set -o xtrace
- fi
net_mounts=${net_mounts%?}
cat << EOF > /usr/lib/rpm/macros.d/macros.distrobox
%_netsharedpath ${net_mounts}
EOF
fi
+###############################################################################
+###############################################################################
# In case of an DEB distro, we can specify that our bind_mount directories
# have to be ignored. This prevents conflicts during package installations.
if [ -d "/etc/dpkg/dpkg.cfg.d/" ]; then
# Loop through all the environment vars
# and export them to the container.
- set +o xtrace
+ printf "distrobox: Setting up dpkg exceptions...\n"
printf "" > /etc/dpkg/dpkg.cfg.d/00_distrobox
for net_mount in ${HOST_MOUNTS_RO} ${HOST_MOUNTS}; do
printf "path-exclude %s/*\n" "${net_mount}" >> /etc/dpkg/dpkg.cfg.d/00_distrobox
done
- # re-enable logging if it was enabled previously.
- if [ "${verbose}" -ne 0 ]; then
- set -o xtrace
- fi
# Also we put a hook to clear some critical paths that do not play well
# with read only filesystems, like systemd.
if [ -d "/etc/apt/apt.conf.d/" ]; then
-
+ printf "distrobox: Setting up apt hooks...\n"
printf "" > /etc/apt/apt.conf.d/00_distrobox
for init_mount in ${HOST_MOUNTS_RO_INIT}; do
printf 'DPkg::Pre-Invoke {"if mountpoint %s; then umount %s; fi";};\n' \
@@ -685,73 +754,50 @@ if [ -d "/etc/dpkg/dpkg.cfg.d/" ]; then
done
fi
fi
+###############################################################################
+###############################################################################
+# Workarounds for pacman. We need to exclude the paths by using a pre-hook to umount them and a
+# post-hook to remount them. Additionally we neutralize the systemd-post-hooks as they do not
+# work on a rootless container system.
if [ -d "/usr/share/libalpm/scripts" ]; then
- set +o xtrace
+ printf "distrobox: Setting up pacman exceptions...\n"
printf "#!/bin/sh\n" > /usr/share/libalpm/scripts/00_distrobox_pre_hook.sh
+ printf "#!/bin/sh\n" > /usr/share/libalpm/scripts/01_distrobox_post_hook.sh
printf "#!/bin/sh\n" > /usr/share/libalpm/scripts/02_distrobox_post_hook.sh
+ chmod +x /usr/share/libalpm/scripts/*distrobox*.sh
for net_mount in ${HOST_MOUNTS_RO}; do
- printf "if mountpoint %s; then umount %s; fi\n" "${net_mount}" "${net_mount}" >> \
- /usr/share/libalpm/scripts/00_distrobox_pre_hook.sh
+ printf "if mountpoint %s; then umount %s; fi\n" \
+ "${net_mount}" "${net_mount}" >> /usr/share/libalpm/scripts/00_distrobox_pre_hook.sh
printf "if [ -e /run/host/%s ]; then mount --rbind -o ro /run/host/%s %s; fi\n" \
"${net_mount}" "${net_mount}" "${net_mount}" >> /usr/share/libalpm/scripts/02_distrobox_post_hook.sh
done
- # re-enable logging if it was enabled previously.
- if [ "${verbose}" -ne 0 ]; then
- set -o xtrace
- fi
# in case we're not using an init image, neutralize systemd post installation hooks
# so that we do not encounter problems along the way.
- cat << EOF > /usr/share/libalpm/scripts/01_distrobox_post_hook.sh
-#!/bin/sh
-if [ ! -e /run/systemd/system ]; then
+ # This will be removed if we're using --init.
+ cat << EOF >> /usr/share/libalpm/scripts/01_distrobox_post_hook.sh
echo -e '#!/bin/sh\nexit 0' > /usr/share/libalpm/scripts/systemd-hook;
-fi
-EOF
- chmod +x /usr/share/libalpm/scripts/00_distrobox_pre_hook.sh
- chmod +x /usr/share/libalpm/scripts/01_distrobox_post_hook.sh
- chmod +x /usr/share/libalpm/scripts/02_distrobox_post_hook.sh
-
- cat << EOF > /usr/share/libalpm/hooks/00-distrobox-pre.hook
-[Trigger]
-Operation = Install
-Operation = Upgrade
-Type = Package
-Target = *
-
-[Action]
-Description = Distrobox pre-hooks...
-When = PreTransaction
-Exec = /usr/share/libalpm/scripts/00_distrobox_pre_hook.sh
-EOF
-
- cat << EOF > /usr/share/libalpm/hooks/00-distrobox-post.hook
-[Trigger]
-Operation = Install
-Operation = Upgrade
-Type = Package
-Target = *
-
-[Action]
-Description = Distrobox post-hooks 1...
-When = PostTransaction
-Exec = /usr/share/libalpm/scripts/01_distrobox_post_hook.sh
EOF
-
- cat << EOF > /usr/share/libalpm/hooks/99-distrobox-post.hook
+ # create hooks files for them
+ printf "distrobox: Setting up pacman hooks...\n"
+ rm -f /usr/share/libalpm/hooks/*distrobox*
+ for hook in 00_distrobox_pre_hook 01_distrobox_post_hook 02_distrobox_post_hook; do
+ when="PostTransaction"
+ [ -z "${hook##*pre*}" ] && when="PreTransaction"
+ cat << EOF > "/usr/share/libalpm/hooks/${hook}.hook"
[Trigger]
Operation = Install
Operation = Upgrade
Type = Package
Target = *
-
[Action]
-Description = Distrobox post-hooks 2...
-When = PostTransaction
-Exec = /usr/share/libalpm/scripts/02_distrobox_post_hook.sh
+Description = Distrobox hook ${hook}...
+When = ${when}
+Exec = /usr/share/libalpm/scripts/${hook}.sh
EOF
-
+ done
fi
+###############################################################################
printf "distrobox: Setting up sudo...\n"
mkdir -p /etc/sudoers.d
@@ -761,7 +807,7 @@ if ! grep -q 'Defaults !fqdn' /etc/sudoers.d/sudoers; then
fi
# Ensure passwordless sudo is set up for user
if ! grep -q "${container_user_name} ALL = (root) NOPASSWD:ALL" /etc/sudoers.d/sudoers; then
- printf "%s ALL = (root) NOPASSWD:ALL\n" "${container_user_name}" >> /etc/sudoers.d/sudoers
+ printf "\"%s\" ALL = (root) NOPASSWD:ALL\n" "${container_user_name}" >> /etc/sudoers.d/sudoers
fi
printf "distrobox: Setting up groups...\n"
@@ -775,8 +821,22 @@ if ! grep -q "^${container_user_name}:" /etc/group; then
fi
printf "distrobox: Setting up users...\n"
+
+# Setup kerberos integration with the host
+if [ -d "/etc/krb5.conf.d" ] && [ ! -e "/etc/krb5.conf.d/kcm_default_ccache" ]; then
+ cat << EOF > "/etc/krb5.conf.d/kcm_default_ccache"
+# # To disable the KCM credential cache, comment out the following lines.
+[libdefaults]
+ default_ccache_name = KCM:
+EOF
+fi
+
# Let's add our user to the container. if the user already exists, enforce properties.
-if ! grep -q "^${container_user_name}:" /etc/passwd; then
+#
+# In case of AD or LDAP usernames, it is possible we will have a backslach in the name.
+# In that case grep would fail, so we replace the backslash with a point to make the regex work.
+# shellcheck disable=SC1003
+if ! grep -q "^$(printf '%s' "${container_user_name}" | tr '\\' '.'):" /etc/passwd; then
if ! useradd \
--home-dir "${container_user_home}" \
--no-create-home \
@@ -842,11 +902,10 @@ printf "distrobox: Executing init hooks...\n"
# shellcheck disable=SC2086
eval ${init_hook}
-printf "container_setup_done\n"
-
# If init support is disabled, let's do our routine to keep the container
# up, running and in sync with host.
if [ "${init}" -eq 0 ]; then
+ printf "container_setup_done\n"
# Keepalive loop
HOST_WATCH="
/etc/hosts
@@ -863,13 +922,24 @@ if [ "${init}" -eq 0 ]; then
# - bindmount will need a container restart on changes
for file_watch in ${HOST_WATCH}; do
# do stuff, only if we need to.
- if ! diff "${file_watch}" "/run/host${file_watch}" > /dev/null; then
- # We only do this, if the file is a bind mount in the first place.
- # This could be useful for init-hooks that involve umounting those
- # files so that can be separated from the host.
- mountpoint "${file_watch}" &&
- umount "${file_watch}" &&
- mount_bind "/run/host${file_watch}" "${file_watch}" rw
+ file_watch_src="/run/host${file_watch}"
+ # check if the target file is a symlink and take the source
+ if [ -e "${file_watch_src}" ]; then
+ if [ -L "${file_watch_src}" ]; then
+ file_watch_src="$(readlink -f "/run/host${file_watch}")"
+ # if it's an absolute link, we need to append /run/host ourselves.
+ if ! echo "${file_watch_src}" | grep -q "/run/host"; then
+ file_watch_src="/run/host${file_watch_src}"
+ fi
+ fi
+ if ! diff "${file_watch}" "${file_watch_src}" > /dev/null; then
+ # We only do this, if the file is a bind mount in the first place.
+ # This could be useful for init-hooks that involve umounting those
+ # files so that can be separated from the host.
+ mountpoint "${file_watch}" &&
+ umount "${file_watch}" &&
+ mount_bind "/run/host${file_watch}" "${file_watch}" rw
+ fi
fi
done
sleep 15
@@ -884,6 +954,36 @@ printf "distrobox: Setting up init system...\n"
for host_mount in ${HOST_MOUNTS_RO_INIT}; do
if mountpoint "${host_mount}"; then umount "${host_mount}"; fi
done
+if command -v systemctl 2> /dev/null; then
+ # Cleanup systemd to not interfere with the host
+ UNIT_TARGETS="
+ /etc/systemd/system/*.wants/*
+ /usr/lib/systemd/system/basic.target.wants/*
+ /usr/lib/systemd/system/local-fs.target.wants/*
+ /usr/lib/systemd/system/multi-user.target.wants/*
+ /usr/lib/systemd/system/plymouth*
+ /usr/lib/systemd/system/sockets.target.wants/*initctl*
+ /usr/lib/systemd/system/sockets.target.wants/*udev*
+ /usr/lib/systemd/system/sysinit.target.wants/*
+ /usr/lib/systemd/system/systemd-update-utmp*
+ "
+ for unit in $(find "${UNIT_TARGETS}" 2> /dev/null | grep -v systemd-tmpfiles-setup); do
+ systemctl mask "$(basename "${unit}")"
+ done
+fi
+# We don't want these workarounds anymore
+rm -f /run/systemd/coredump
+rm -f /run/systemd/io.system.ManagedOOM
+rm -f /run/systemd/notify
+rm -f /run/systemd/private
+rm -f /etc/apt/apt.conf.d/00_distrobox
+rm -f /usr/share/libalpm/hooks/*distrobox*.hook
+rm -f /usr/share/libalpm/scripts/*distrobox*.sh
+# Remove /dev/console when using init systems, this will confuse host system if
+# we use rootful containers
+touch /var/container-console
+mount --rbind /var/container-console /dev/console
# Now we can launch init
printf "distrobox: Firing up init system...\n"
+printf "container_setup_done\n"
exec /sbin/init
diff --git a/distrobox-list b/distrobox-list
index f62da97..e74b30d 100755
--- a/distrobox-list
+++ b/distrobox-list
@@ -21,6 +21,7 @@
# POSIX
# Optional env variables:
# DBX_CONTAINER_MANAGER
+# DBX_SUDO_PROGRAM
# Dont' run this command as sudo.
if [ "$(id -u)" -eq 0 ]; then
@@ -31,26 +32,31 @@ if [ "$(id -u)" -eq 0 ]; then
fi
# Defaults
+no_color=0
rootful=0
-size=0
verbose=0
-version="1.3.1"
+version="1.4.0"
container_manager="autodetect"
+distrobox_sudo_program="sudo"
# Source configuration files, this is done in an hierarchy so local files have
# priority over system defaults
# leave priority to environment variables.
config_files="
/usr/share/distrobox/distrobox.conf
+ /usr/etc/distrobox/distrobox.conf
/etc/distrobox/distrobox.conf
- ${HOME}/.config/distrobox/distrobox.conf
+ ${XDG_CONFIG_HOME:-"${HOME}/.config"}/distrobox/distrobox.conf
${HOME}/.distroboxrc
"
for config_file in ${config_files}; do
+ # Shellcheck will give error for sourcing a variable file as it cannot follow
+ # it. We don't care so let's disable this linting for now.
# shellcheck disable=SC1090
[ -e "${config_file}" ] && . "${config_file}"
done
[ -n "${DBX_CONTAINER_MANAGER}" ] && container_manager="${DBX_CONTAINER_MANAGER}"
+[ -n "${DBX_SUDO_PROGRAM}" ] && distrobox_sudo_program="${DBX_SUDO_PROGRAM}"
# Print usage to stdout.
# Arguments:
@@ -68,8 +74,10 @@ Usage:
Options:
--help/-h: show this message
+ --no-color: disable color formatting
--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
--verbose/-v: show more verbosity
--version/-V: show version
EOF
@@ -83,13 +91,13 @@ while :; do
show_help
exit 0
;;
- -r | --root)
+ --no-color)
shift
- rootful=1
+ no_color=1
;;
- -s | --size)
- size=1
+ -r | --root)
shift
+ rootful=1
;;
-v | --verbose)
verbose=1
@@ -158,25 +166,30 @@ if [ "${verbose}" -ne 0 ]; then
container_manager="${container_manager} --log-level debug"
fi
-# prepend sudo if we want podman or docker to be rootful
+# prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
if [ "${rootful}" -ne 0 ]; then
- container_manager="sudo ${container_manager}"
+ container_manager="${distrobox_sudo_program} ${container_manager}"
fi
# List containers using custom format that inclused MOUNTS
# we do this as we can detect the custom mounts done by distrobox to distringuish
# between a normal podman or docker container and a distrobox one.
-if [ "${size}" -ne 0 ]; then
- container_list=$(${container_manager} ps -a --no-trunc --size --format \
- "{{.ID}}|{{.Image}}|{{.Names}}|{{.State}}|{{.Mounts}}|{{.Size}}")
- printf " %-12s | %-25s | %-30s | %-40s | %-30s\n" "ID" "NAME" "STATUS" "IMAGE" "SIZE"
-else
- container_list=$(${container_manager} ps -a --no-trunc --format \
- "{{.ID}}|{{.Image}}|{{.Names}}|{{.State}}|{{.Mounts}}")
- printf " %-12s | %-25s | %-30s | %-30s\n" "ID" "NAME" "STATUS" "IMAGE"
-fi
+container_list=$(${container_manager} ps -a --no-trunc --format \
+ "{{.ID}}|{{.Image}}|{{.Names}}|{{.State}}|{{.Labels}}{{.Mounts}}")
+printf "%-12s | %-20s | %-30s | %-30s\n" "ID" "NAME" "STATUS" "IMAGE"
IFS='
'
+
+# if we're in not a tty, don't use colors
+GREEN=""
+YELLOW=""
+CLEAR=""
+if [ -t 0 ] && [ "${no_color}" -ne 1 ]; then
+ # we're in a tty, use colors
+ GREEN='\033[32m'
+ YELLOW='\033[33m'
+ CLEAR='\033[0m'
+fi
# Header of the output
for container in ${container_list}; do
# Check if the current container has a custom mount point for distrobox.
@@ -187,17 +200,21 @@ for container in ${container_list}; do
container_image="$(printf "%s" "${container}" | cut -d'|' -f2)"
container_name="$(printf "%s" "${container}" | cut -d'|' -f3)"
container_status="$(printf "%s" "${container}" | cut -d'|' -f4)"
- container_size="$(printf "%s" "${container}" | cut -d'|' -f6)"
# If the container is Up and Running, print it in green and go next.
if [ -z "${container_status##*Up*}" ] || [ -z "${container_status##*running*}" ]; then
- printf "\033[32m %-12s | %-25s | %-30s | %-40s | %-30s\n\033[0m" \
- "${container_id}" "${container_name}" "${container_status}" "${container_image}" "${container_size}"
- continue
+ # echo -e is not defined in posix, and printing with %s will not work
+ # for colors, so we're disabling this lint for color prints.
+ # shellcheck disable=SC2059
+ printf "${GREEN}"
+ else
+ # shellcheck disable=SC2059
+ printf "${YELLOW}"
fi
# print it in yellow if not Running
- printf "\033[33m %-12s | %-25s | %-30s | %-40s | %-30s\n\033[0m" \
- "${container_id}" "${container_name}" "${container_status}" "${container_image}" "${container_size}"
-
+ printf "%-12s | %-20s | %-30s | %-40s\n" \
+ "${container_id}" "${container_name}" "${container_status}" "${container_image}"
fi
+ # shellcheck disable=SC2059
+ printf "${CLEAR}"
done
diff --git a/distrobox-rm b/distrobox-rm
index 4d6b0a8..ddfc149 100755
--- a/distrobox-rm
+++ b/distrobox-rm
@@ -23,6 +23,7 @@
# DBX_CONTAINER_MANAGER
# DBX_CONTAINER_NAME
# DBX_NON_INTERACTIVE
+# DBX_SUDO_PROGRAM
# Dont' run this command as sudo.
if [ "$(id -u)" -eq 0 ]; then
@@ -34,23 +35,26 @@ fi
# Defaults
container_manager="autodetect"
-container_name="my-distrobox"
force=0
non_interactive=0
rootful=0
verbose=0
-version="1.3.1"
+distrobox_sudo_program="sudo"
+version="1.4.0"
# Source configuration files, this is done in an hierarchy so local files have
# priority over system defaults
# leave priority to environment variables.
config_files="
/usr/share/distrobox/distrobox.conf
+ /usr/etc/distrobox/distrobox.conf
/etc/distrobox/distrobox.conf
- ${HOME}/.config/distrobox/distrobox.conf
+ ${XDG_CONFIG_HOME:-"${HOME}/.config"}/distrobox/distrobox.conf
${HOME}/.distroboxrc
"
for config_file in ${config_files}; do
+ # Shellcheck will give error for sourcing a variable file as it cannot follow
+ # it. We don't care so let's disable this linting for now.
# shellcheck disable=SC1090
[ -e "${config_file}" ] && . "${config_file}"
done
@@ -59,8 +63,12 @@ done
[ "${non_interactive}" = "false" ] && non_interactive=0
[ -n "${DBX_CONTAINER_MANAGER}" ] && container_manager="${DBX_CONTAINER_MANAGER}"
-[ -n "${DBX_CONTAINER_NAME}" ] && container_name="${DBX_CONTAINER_NAME}"
[ -n "${DBX_NON_INTERACTIVE}" ] && non_interactive="${DBX_NON_INTERACTIVE}"
+[ -n "${DBX_SUDO_PROGRAM}" ] && distrobox_sudo_program="${DBX_SUDO_PROGRAM}"
+
+# Declare it AFTER config sourcing because we do not want a default name set for rm.
+container_name=""
+container_name_list=""
# Print usage to stdout.
# Arguments:
@@ -73,15 +81,14 @@ distrobox version: ${version}
Usage:
- distrobox-rm --name container-name [--force]
- distrobox-rm container-name [-f]
+ distrobox-rm [-f/--force] container-name [container-name1 container-name2 ...]
Options:
--name/-n: name for the distrobox
- --force/-f: force deletion
--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
--help/-h: show this message
--verbose/-v: show more verbosity
--version/-V: show version
@@ -112,13 +119,6 @@ while :; do
force=1
shift
;;
- -n | --name)
- if [ -n "$2" ]; then
- container_name="$2"
- shift
- shift
- fi
- ;;
-Y | --yes)
non_interactive=1
shift
@@ -136,7 +136,7 @@ while :; do
# If we have a flagless option and container_name is not specified
# then let's accept argument as container_name
if [ -n "$1" ]; then
- container_name="$1"
+ container_name_list="${container_name_list} $1"
shift
else
break
@@ -190,61 +190,74 @@ if [ "${verbose}" -ne 0 ]; then
container_manager="${container_manager} --log-level debug"
fi
-# prepend sudo if we want podman or docker to be rootful
+# prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
if [ "${rootful}" -ne 0 ]; then
- container_manager="sudo ${container_manager}"
+ container_manager="${distrobox_sudo_program} ${container_manager}"
fi
-# Inspect the container we're working with.
-container_status="$(${container_manager} inspect --type container \
- "${container_name}" --format '{{.State.Status}}')"
-container_exists="$?"
-# Does the container exist? check if inspect reported errors
-if [ "${container_exists}" -gt 0 ]; then
- # If not, prompt to create it first
- printf >&2 "Cannot find container %s, does it exist?\n" "${container_name}"
+# check if we have containers to delete
+if [ -z "${container_name_list}" ]; then
+ printf >&2 "Please specify a container name.\n"
exit 1
fi
-# If the container is not already running, we need to start if first
-if [ "${container_status}" = "running" ]; then
- if [ "${force}" -ne 0 ]; then
- printf >&2 "Stopping container %s\n" "${container_name}"
- if ! ${container_manager} stop "${container_name}"; then
- printf >&2 "Could not stop container %s\n" "${container_name}"
+for container_name in ${container_name_list}; do
+ # Inspect the container we're working with.
+ container_status="$(${container_manager} inspect --type container \
+ "${container_name}" --format '{{.State.Status}}')"
+ container_exists="$?"
+ # Does the container exist? check if inspect reported errors
+ if [ "${container_exists}" -gt 0 ]; then
+ # If not, prompt to create it first
+ printf >&2 "Cannot find container %s, does it exist?\n" "${container_name}"
+ exit 1
+ fi
+
+ # If the container is not already running, we need to start if first
+ if [ "${container_status}" = "running" ]; then
+ if [ "${force}" -ne 0 ]; then
+ printf >&2 "Stopping container %s\n" "${container_name}"
+ if ! ${container_manager} stop "${container_name}"; then
+ printf >&2 "Could not stop container %s\n" "${container_name}"
+ printf >&2 "Please stop container %s before deletion\n" "${container_name}"
+ printf >&2 "Run:\n\t%s stop %s" "${container_manager}" "${container_name}"
+ exit 1
+ fi
+ else
printf >&2 "Please stop container %s before deletion\n" "${container_name}"
- printf >&2 "Run:\n\t%s stop %s" "${container_manager}" "${container_name}"
+ printf >&2 "Run:\n\t%s stop %s\n" "${container_manager}" "${container_name}"
+ printf >&2 'or use the "--force" flag'
exit 1
fi
+ fi
+ if [ "${non_interactive}" -eq 0 ] && [ "${force}" -eq 0 ]; then
+ # Prompt to download it.
+ printf "Do you really want to delete %s? [Y/n]: " "${container_name}"
+ read -r response
+ response="${response:-"Y"}"
else
- printf >&2 "Please stop container %s before deletion\n" "${container_name}"
- printf >&2 "Run:\n\t%s stop %s\n" "${container_manager}" "${container_name}"
- printf >&2 'or use the "--force" flag'
- exit 1
+ response="yes"
fi
-fi
-if [ "${non_interactive}" -eq 0 ] && [ "${force}" -eq 0 ]; then
- # Prompt to download it.
- printf "Do you really want to delete %s? [Y/n]: " "${container_name}"
- read -r response
- response="${response:-"Y"}"
-else
- response="yes"
-fi
-# Accept only y,Y,Yes,yes,n,N,No,no.
-case "${response}" in
- y | Y | Yes | yes | YES)
- # Remove the container
- ${container_manager} rm "${container_name}"
- ;;
- n | N | No | no | NO)
- printf "Aborted.\n"
- exit 0
- ;;
- *) # Default case: If no more options then break out of the loop.
- printf >&2 "Invalid input.\n"
- printf >&2 "The available choices are: y,Y,Yes,yes,YES or n,N,No,no,NO.\nExiting.\n"
- exit 1
- ;;
-esac
+ # Accept only y,Y,Yes,yes,n,N,No,no.
+ case "${response}" in
+ y | Y | Yes | yes | YES)
+ # We're going to deleted the box, let's also delete the entry
+ if [ "${rootful}" -eq 0 ]; then
+ "$(dirname "$(realpath "${0}")")/distrobox-generate-entry" "${container_name}" --delete
+ fi
+
+ # Remove the container
+ ${container_manager} rm "${container_name}"
+ ;;
+ n | N | No | no | NO)
+ printf "Aborted.\n"
+ exit 0
+ ;;
+ *) # Default case: If no more options then break out of the loop.
+ printf >&2 "Invalid input.\n"
+ printf >&2 "The available choices are: y,Y,Yes,yes,YES or n,N,No,no,NO.\nExiting.\n"
+ exit 1
+ ;;
+ esac
+done
diff --git a/distrobox-stop b/distrobox-stop
index accfce0..c9549b2 100755
--- a/distrobox-stop
+++ b/distrobox-stop
@@ -23,6 +23,7 @@
# DBX_CONTAINER_MANAGER
# DBX_CONTAINER_NAME
# DBX_NON_INTERACTIVE
+# DBX_SUDO_PROGRAM
# Dont' run this command as sudo.
if [ "$(id -u)" -eq 0 ]; then
@@ -38,18 +39,22 @@ container_name="my-distrobox"
non_interactive=0
rootful=0
verbose=0
-version="1.3.1"
+distrobox_sudo_program="sudo"
+version="1.4.0"
# Source configuration files, this is done in an hierarchy so local files have
# priority over system defaults
# leave priority to environment variables.
config_files="
/usr/share/distrobox/distrobox.conf
+ /usr/etc/distrobox/distrobox.conf
/etc/distrobox/distrobox.conf
- ${HOME}/.config/distrobox/distrobox.conf
+ ${XDG_CONFIG_HOME:-"${HOME}/.config"}/distrobox/distrobox.conf
${HOME}/.distroboxrc
"
for config_file in ${config_files}; do
+ # Shellcheck will give error for sourcing a variable file as it cannot follow
+ # it. We don't care so let's disable this linting for now.
# shellcheck disable=SC1090
[ -e "${config_file}" ] && . "${config_file}"
done
@@ -60,6 +65,7 @@ done
[ -n "${DBX_CONTAINER_MANAGER}" ] && container_manager="${DBX_CONTAINER_MANAGER}"
[ -n "${DBX_CONTAINER_NAME}" ] && container_name="${DBX_CONTAINER_NAME}"
[ -n "${DBX_NON_INTERACTIVE}" ] && non_interactive="${DBX_NON_INTERACTIVE}"
+[ -n "${DBX_SUDO_PROGRAM}" ] && distrobox_sudo_program="${DBX_SUDO_PROGRAM}"
# Print usage to stdout.
# Arguments:
@@ -81,7 +87,8 @@ Options:
--yes/-Y: non-interactive, stop without asking
--help/-h: show this message
--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
--verbose/-v: show more verbosity
--version/-V: show version
EOF
@@ -185,9 +192,9 @@ if [ "${verbose}" -ne 0 ]; then
container_manager="${container_manager} --log-level debug"
fi
-# prepend sudo if we want podman or docker to be rootful
+# prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
if [ "${rootful}" -ne 0 ]; then
- container_manager="sudo ${container_manager}"
+ container_manager="${distrobox_sudo_program} ${container_manager}"
fi
# Inspect the container we're working with.
diff --git a/distrobox-stop b/distrobox-upgrade
similarity index 65%
copy from distrobox-stop
copy to distrobox-upgrade
index accfce0..dcf487b 100755
--- a/distrobox-stop
+++ b/distrobox-upgrade
@@ -19,11 +19,6 @@
# along with distrobox; if not, see <http://www.gnu.org/licenses/>.
# POSIX
-# Optional env variables:
-# DBX_CONTAINER_MANAGER
-# DBX_CONTAINER_NAME
-# DBX_NON_INTERACTIVE
-
# Dont' run this command as sudo.
if [ "$(id -u)" -eq 0 ]; then
printf >&2 "Running %s as sudo is not supported.\n" "$(basename "${0}")"
@@ -32,34 +27,35 @@ if [ "$(id -u)" -eq 0 ]; then
exit 1
fi
-# Defaults
+all=0
container_manager="autodetect"
-container_name="my-distrobox"
-non_interactive=0
+distrobox_path="$(dirname "$(realpath "${0}")")"
+distrobox_sudo_program="sudo"
rootful=0
verbose=0
-version="1.3.1"
+version="1.4.0"
# Source configuration files, this is done in an hierarchy so local files have
# priority over system defaults
# leave priority to environment variables.
config_files="
/usr/share/distrobox/distrobox.conf
+ /usr/etc/distrobox/distrobox.conf
/etc/distrobox/distrobox.conf
- ${HOME}/.config/distrobox/distrobox.conf
+ ${XDG_CONFIG_HOME:-"${HOME}/.config"}/distrobox/distrobox.conf
${HOME}/.distroboxrc
"
for config_file in ${config_files}; do
+ # Shellcheck will give error for sourcing a variable file as it cannot follow
+ # it. We don't care so let's disable this linting for now.
# shellcheck disable=SC1090
[ -e "${config_file}" ] && . "${config_file}"
done
-# Fixup non_interactive=[true|false], in case we find it in the config file(s)
-[ "${non_interactive}" = "true" ] && non_interactive=1
-[ "${non_interactive}" = "false" ] && non_interactive=0
-
[ -n "${DBX_CONTAINER_MANAGER}" ] && container_manager="${DBX_CONTAINER_MANAGER}"
-[ -n "${DBX_CONTAINER_NAME}" ] && container_name="${DBX_CONTAINER_NAME}"
-[ -n "${DBX_NON_INTERACTIVE}" ] && non_interactive="${DBX_NON_INTERACTIVE}"
+[ -n "${DBX_SUDO_PROGRAM}" ] && distrobox_sudo_program="${DBX_SUDO_PROGRAM}"
+
+# Declare it AFTER config sourcing because we do not want a default name set.
+container_name=""
# Print usage to stdout.
# Arguments:
@@ -72,21 +68,26 @@ distrobox version: ${version}
Usage:
- distrobox-stop --name container-name
- distrobox-stop container-name
+ distrobox-upgrade container-name
+ distrobox-upgrade --all
Options:
- --name/-n: name for the distrobox
- --yes/-Y: non-interactive, stop without asking
--help/-h: show this message
+ --all/-a: perform for all distroboxes
--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
--verbose/-v: show more verbosity
--version/-V: show version
EOF
}
+if [ $# -eq 0 ]; then
+ show_help
+ exit
+fi
+
# Parse arguments
while :; do
case $1 in
@@ -95,10 +96,6 @@ while :; do
show_help
exit 0
;;
- -r | --root)
- shift
- rootful=1
- ;;
-v | --verbose)
verbose=1
shift
@@ -107,16 +104,13 @@ while :; do
printf "distrobox: %s\n" "${version}"
exit 0
;;
- -n | --name)
- if [ -n "$2" ]; then
- container_name="$2"
- shift
- shift
- fi
+ -a | --all)
+ all=1
+ shift
;;
- -Y | --yes)
- non_interactive=1
+ -r | --root)
shift
+ rootful=1
;;
--) # End of all options.
shift
@@ -131,7 +125,7 @@ while :; do
# If we have a flagless option and container_name is not specified
# then let's accept argument as container_name
if [ -n "$1" ]; then
- container_name="$1"
+ container_name="${container_name} $1"
shift
else
break
@@ -147,6 +141,11 @@ if [ "${verbose}" -ne 0 ]; then
set -o xtrace
fi
+if [ -z "${container_name}" ] && [ "${all}" -eq 0 ]; then
+ printf >&2 "Please specify the name of the container.\n"
+ exit 1
+fi
+
# We depend on a container manager let's be sure we have it
# First we use podman, else docker
case "${container_manager}" in
@@ -180,46 +179,36 @@ if ! command -v "${container_manager}" > /dev/null; then
printf >&2 "\thttps://github.com/89luca89/distrobox/blob/main/docs/compatibility.md\n"
exit 127
fi
+
# add verbose if -v is specified
if [ "${verbose}" -ne 0 ]; then
container_manager="${container_manager} --log-level debug"
fi
-# prepend sudo if we want podman or docker to be rootful
+# prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
if [ "${rootful}" -ne 0 ]; then
- container_manager="sudo ${container_manager}"
+ container_manager="${distrobox_sudo_program} ${container_manager}"
fi
-# Inspect the container we're working with.
-container_exists="$?"
-# Does the container exist? check if inspect reported errors
-if [ "${container_exists}" -gt 0 ]; then
- printf >&2 "Cannot find container %s, does it exist?\n" "${container_name}"
- exit 1
-fi
+# If all, just set container_name to the list of names in distrobox-list
+if [ "${all}" -ne 0 ]; then
-if [ "${non_interactive}" -eq 0 ]; then
- # Prompt to stop the container.
- printf "Do you really want to stop %s? [Y/n]: " "${container_name}"
- read -r response
- response="${response:-"Y"}"
-else
- response="yes"
+ # prepend sudo (or the specified sudo program) if we want podman or docker to be rootful
+ if [ "${rootful}" -ne 0 ]; then
+ container_name="$("${distrobox_path}"/distrobox-list --root --no-color | tail -n +2 | cut -d'|' -f2 | tr -d ' ')"
+ else
+ container_name="$("${distrobox_path}"/distrobox-list --no-color | tail -n +2 | cut -d'|' -f2 | tr -d ' ')"
+ fi
fi
-# Accept only y,Y,Yes,yes,n,N,No,no.
-case "${response}" in
- y | Y | Yes | yes | YES)
- # Stop the container
- ${container_manager} stop "${container_name}"
- ;;
- n | N | No | no | NO)
- printf "Aborted.\n"
- exit 0
- ;;
- *) # Default case: If no more options then break out of the loop.
- printf >&2 "Invalid input.\n"
- printf >&2 "The available choices are: y,Y,Yes,yes,YES or n,N,No,no,NO.\nExiting.\n"
- exit 1
- ;;
-esac
+# Launch the entrypoint in upgrade mode
+for container in ${container_name}; do
+ printf >&2 "\033[1;31m Upgrading %s...\n\033[0m" "${container}"
+ if [ "${rootful}" -ne 0 ]; then
+ # shellcheck disable=SC2086
+ "${distrobox_path}"/distrobox-enter --root ${container} -- sudo /usr/bin/entrypoint --upgrade
+ else
+ # shellcheck disable=SC2086
+ "${distrobox_path}"/distrobox-enter ${container} -- sudo /usr/bin/entrypoint --upgrade
+ fi
+done
diff --git a/docs/README.md b/docs/README.md
index df00785..8ec20bf 100644
--- a/docs/README.md
+++ b/docs/README.md
@@ -38,6 +38,12 @@ graphical apps (X11/Wayland), and audio.
- [Why?](#why)
- [Aims](#aims)
- [Installation](#installation)
+ - [Alternative methods](#alternative-methods)
+ - [Curl](#curl)
+ - [Git](#git)
+ - [Flatpak](#flatpak)
+ - [Dependencies](#dependencies)
+ - [Install Podman without root](compatibility.md#install-podman-in-a-static-manner)
- [Uninstallation](#uninstallation)
- [Compatibility](compatibility.md)
- [Supported container managers](compatibility.md#supported-container-managers)
@@ -47,6 +53,7 @@ graphical apps (X11/Wayland), and audio.
- [Outside the distrobox](usage/usage.md#outside-the-distrobox)
- [distrobox-create](usage/distrobox-create.md)
- [distrobox-enter](usage/distrobox-enter.md)
+ - [distrobox-ephemeral](usage/distrobox-ephemeral.md)
- [distrobox-list](usage/distrobox-list.md)
- [distrobox-rm](usage/distrobox-rm.md)
- [distrobox-stop](usage/distrobox-stop.md)
@@ -84,15 +91,20 @@ graphical apps (X11/Wayland), and audio.
- [Articles](featured_articles.md#articles)
- [Run Distrobox on Fedora Linux - Fedora Magazine](https://fedoramagazine.org/run-distrobox-on-fedora-linux/)
- [DistroBox – Run Any Linux Distribution Inside Linux Terminal - TecMint](https://www.tecmint.com/distrobox-run-any-linux-distribution/)
+ - [Distrobox: Try Multiple Linux Distributions via the Terminal - It's FOSS](https://itsfoss.com/distrobox/)
- [Distrobox - How to quickly deploy a Linux distribution with GUI applications via a container](https://www.techrepublic.com/article/how-to-quickly-deploy-a-linux-distribution-with-gui-applications-via-a-container/)
- [Using Distrobox To Augment The Package Selection On Clear Linux - Phoronix](https://www.phoronix.com/scan.php?page=news_item&px=Distrobox-Clear-Linux)
- [Benchmark: benefits of Clear Linux containers (distrobox) - Phoronix](https://www.phoronix.com/forums/forum/phoronix/latest-phoronix-articles/1305326-clear-linux-container-performance-continues-showing-sizable-gains)
- [Distrobox - A great item in the Linux toolbelt - phmurphy's blog](https://phmurphy.com/posts/distrobox-toolbelt/)
- - [Running Other Linux Distros with Distrobox on Fedora Linux - bandithijo's blog](featured_articles.md)
+ - [Distrobox: Run (pretty much) any Linux distro under almost any other - TheRegister](https://www.theregister.com/2022/05/31/distrobox_130_released/)
- [Day-to-day differences between Fedora Silverblue and Ubuntu - castrojo's blog](https://www.ypsidanger.com/day-to-day-advantages-of-fedora-silverblue/)
- [Distrobox is Awesome - Running Window Manager and Desktop environments using Distrobox](https://cloudyday.tech.blog/2022/05/14/distrobox-is-awesome/)
+ - [Japanese input on Clear Linux with Mozc via Ubuntu container with Distrobox](https://impsbl.hatenablog.jp/entry/JapaneseInputOnClearLinuxWithMozc_en)
+ - [MID (MaXX Interactive Desktop) on Clear Linux via Ubuntu container with Distrobox](https://impsbl.hatenablog.jp/entry/MIDonClearLinuxWithDistrobox_en)
+ - [Running Other Linux Distros with Distrobox on Fedora Linux - bandithijo's blog](featured_articles.md)
- [Talks](featured_articles.md#talks)
- [Linux App Summit 2022 - Distrobox: Run Any App On Any Distro - BoF](https://github.com/89luca89/distrobox/files/8598433/distrobox-las-talk.pdf)
+ - [A "Box" Full of Tools and Distros - Dario Faggioli @ OpenSUSE Conference 2022](https://www.youtube.com/watch?v=_RzARte80SQ)
- [Podcasts](featured_articles.md#podcasts)
---
@@ -114,13 +126,15 @@ but in a simplified way using POSIX sh and aiming at broader compatibility.
All the props go to them as they had the great idea to implement this stuff.
-It is divided into 8 commands:
+It is divided into 10 commands:
- `distrobox-create` - creates the container
- `distrobox-enter` - to enter the container
- `distrobox-list` - to list containers created with distrobox
- `distrobox-rm` - to delete a container created with distrobox
- `distrobox-stop` - to stop a running container created with distrobox
+- `distrobox-upgrade` - to upgrade one or more running containers created with distrobox at once
+- `distrobox-generate-entry` - to create an entry of a created container in the applications list
- `distrobox-init` - the entrypoint of the container (not meant to be used manually)
- `distrobox-export` - it is meant to be used inside the container,
useful to export apps and services from the container to the host
@@ -143,8 +157,8 @@ Fedora Silverblue on his project [ublue](https://github.com/castrojo/ublue)
## Why
-- Provide a mutable environment on an immutable OS, like Endless OS,
- Fedora Silverblue, OpenSUSE MicroOS or SteamOS3
+- Provide a mutable environment on an immutable OS, like [Endless OS,
+ Fedora Silverblue, OpenSUSE MicroOS](compatibility.md#host-distros) or [SteamOS3](compatibility.md#install-podman-in-a-static-manner)
- Provide a locally privileged environment for sudoless setups
(eg. company-provided laptops, security reasons, etc...)
- To mix and match a stable base system (eg. Debian Stable, Ubuntu LTS, RedHat)
@@ -170,24 +184,15 @@ It also aims to enter the container **as fast as possible**, every millisecond
adds up if you use the container as your default environment for your terminal:
These are some sample results of `distrobox-enter` on the same container on my
-weak laptop from 2015 with 2 core cpu:
-
-```sh
-Total time for 100 container enters:
+weak laptop:
- ~$ time (for i in {1..100}; do distrobox-enter --name fedora-toolbox-35 -- whoami; done)
- real 0m36.209s
- user 0m6.520s
- sys 0m4.803s
-
-Mean:
-
-36.209s/100 = ~0.362ms mean time to enter the container
+```console
+~$ hyperfine --warmup 3 --runs 100 "distrobox enter bench -- whoami"
+Benchmark 1: distrobox enter bench -- whoami
+ Time (mean ± σ): 395.6 ms ± 10.5 ms [User: 167.4 ms, System: 62.4 ms]
+ Range (min … max): 297.3 ms … 408.9 ms 100 runs
```
-I would like to keep it always below the
-[Doherty Treshold](https://lawsofux.com/doherty-threshold/) of 400ms.
-
#### Security implications
Isolation and sandboxing is **not** the main aim of the project, on the contrary
@@ -196,7 +201,7 @@ The container will have complete access to your home, pen drives and so on,
so do not expect it to be highly sandboxed like a plain
docker/podman container or a flatpak.
-⚠️ **BE CAREFUL**: if you use docker, or you use podman with the `--root/-r` flag,
+⚠️ **BE CAREFUL**:⚠️ if you use docker, or you use podman with the `--root/-r` flag,
the containers will run as root, so **root inside the rootful container can modify
system stuff outside the container**,
if you have security concern for this, **use podman that runs in rootless mode**.
@@ -217,11 +222,20 @@ Create a new distrobox:
Enter created distrobox:
`distrobox enter test`
+
+Add [various](https://github.com/89luca89/distrobox/blob/main/docs/compatibility.md#host-distros)
+distroboxes, eg Ubuntu 20.04:
+
+`distrobox create -i ubuntu:20.04`
Execute a command in a distrobox:
`distrobox enter test -- command-to-execute`
+Upgrade all distroboxes at once:
+
+`distrobox upgrade --all`
+
List running distroboxes:
`distrobox list`
@@ -243,6 +257,7 @@ Configuration files can be placed in the following paths, from the least importa
to the most important:
- /usr/share/distrobox/distrobox.conf
+- /usr/etc/distrobox/distrobox.conf
- /etc/distrobox/distrobox.conf
- ${HOME}/.config/distrobox/distrobox.conf
- ${HOME}/.distroboxrc
@@ -282,6 +297,12 @@ Thanks to the maintainers for their work: [M0Rf30](https://github.com/M0Rf30),
[alcir](https://github.com/alcir), [dfaggioli](https://github.com/dfaggioli),
[AtilaSaraiva](https://github.com/AtilaSaraiva), [michel-slm](https://github.com/michel-slm)
+## Alternative methods
+
+Here is a list of alternative ways to install distrobox
+
+### Curl
+
Else, if you like to live your life dangerously, or you want the latest release,
you can trust me and simply run this in your terminal:
@@ -307,6 +328,8 @@ or:
curl -s https://raw.githubusercontent.com/89luca89/distrobox/main/install | sh -s -- --next --prefix ~/.local
```
+### Git
+
Alternatively you can clone the project using `git clone` or using the latest
release [HERE](https://github.com/89luca89/distrobox/releases/latest).
@@ -318,6 +341,34 @@ such as `./install --prefix ~/.distrobox`.
Prefix explained: main distrobox files get installed to `${prefix}/bin` whereas
the manpages get installed to `${prefix}/share/man`.
+### Flatpak
+
+⚠️ ⚠️ ⚠️ This is experimental! ⚠️ ⚠️ ⚠️
+
+You can find flatpak builds of distrobox here:
+[io.github.luca.distrobox](https://github.com/89luca89/io.github.luca.distrobox/releases)
+Download the latest release flatpak and run
+
+```sh
+flatpak install io.github.luca.distrobox.flatpak
+```
+
+You can then run distrobox with:
+
+```sh
+flatpak run io.github.luca.distrobox create ...
+flatpak run io.github.luca.distrobox enter ...
+flatpak run io.github.luca.distrobox list ...
+[...]
+```
+
+It will be handy to add an `alias distrobox="flatpak run io.github.luca.distrobox"` to your shell,
+so that you can run distrobox commands normally.
+
+Being experimental, please if you encounter problems, report them!
+
+---
+
Check the [Host Distros](compatibility.md#host-distros) compatibility list for
distro-specific instructions.
@@ -325,9 +376,13 @@ distro-specific instructions.
Distrobox depends on a container manager to work, you can choose to install
either podman or docker.
+
Please look in the [Compatibility Table](compatibility.md#host-distros) for your
distribution notes.
+There are ways to install [Podman without root privileges and in home.](compatibility.md#install-podman-in-a-static-manner)
+This should play well with completely sudoless setups and with devices like the Stean Deck.
+
---
## Uninstallation
diff --git a/docs/compatibility.md b/docs/compatibility.md
index e291bd8..ac54904 100644
--- a/docs/compatibility.md
+++ b/docs/compatibility.md
@@ -1,10 +1,15 @@
- [Distrobox](README.md)
- - [Supported container managers](#supported-container-managers)
- - [Host Distros](#host-distros)
- - [New Host Distro support](#new-host-distro-support)
- - [Containers Distros](#containers-distros)
- - [New Distro support](#new-distro-support)
- - [Older Distributions](#older-distributions)
+ - [Compatibility](#compatibility)
+ - [Supported container managers](#supported-container-managers)
+ - [Host Distros](#host-distros)
+ - [Install Podman in a static manner](#install-podman-in-a-static-manner)
+ - [Compatibility notes](#compatibility-notes)
+ - [Non shared mounts](#non-shared-mounts)
+ - [List of distributions including distrobox in their repositories](#list-of-distributions-including-distrobox-in-their-repositories)
+ - [New Host Distro support](#new-host-distro-support)
+ - [Containers Distros](#containers-distros)
+ - [New Distro support](#new-distro-support)
+ - [Older distributions](#older-distributions)
---
@@ -13,9 +18,11 @@
This project **does not need a dedicated image**. It can use any OCI images from
docker-hub, quay.io, or any registry of your choice.
-Granted, they may not be as featureful as expected (some of them do not even have
-`which`, `mount`, `less` or `vi`) but that's all doable in the container itself
-after bootstrapping it.
+Many cloud images are stripped down on purpose to save size and may not include
+commands such as `which`, `mount`, `less` or `vi`). Additional packages can be
+installed once inside the container. We recommend using your preferred automation
+tool inside the container if you find yourself having to repeatedly create new containers.
+Maintaining your own custom image is also an option.
The main concern is having basic Linux utilities (`mount`), basic user management
utilities (`usermod, passwd`), and `sudo` correctly set.
@@ -25,7 +32,7 @@ utilities (`usermod, passwd`), and `sudo` correctly set.
`distrobox` can run on either `podman` or `docker`
It depends either on `podman` configured in `rootless mode`
-or on `docker` configured without sudo (follow [THIS instructions](https://docs.docker.com/engine/install/linux-postinstall/))
+or on `docker` configured without sudo (follow [THESE instructions](https://docs.docker.com/engine/install/linux-postinstall/))
- Minimum podman version: **2.1.0**
- Minimum docker version: **18.06.1**
@@ -44,22 +51,49 @@ Distrobox has been successfully tested on:
| --- | --- | --- |
| Alpine Linux | 3.14 <br> 3.15 | To setup rootless podman, look [HERE](https://wiki.alpinelinux.org/wiki/Podman) |
| Arch Linux | | `distrobox` and `distrobox-git` are available in AUR (thanks [M0Rf30](https://github.com/M0Rf30)!). <br> To setup rootless podman, look [HERE](https://wiki.archlinux.org/title/Podman) |
-| Manjaro | | To setup rootless podman, look [HERE](https://wiki.archlinux.org/title/Podman) |
| CentOS | 8 <br> 8 Stream <br> 9 Stream | `distrobox` is available in epel repos. (thanks [alcir](https://github.com/alcir)!) |
-| RedHat | 8 <br> 9beta | `distrobox` is available in epel repos. (thanks [alcir](https://github.com/alcir)!) |
-| Debian | 11 <br> Testing <br> Unstable | |
-| Fedora | 34 <br> 35 <br> 36 | `distrobox` is available in default repos.(thanks [alcir](https://github.com/alcir)!) |
-| Fedora Silverblue/Kinoite | 34 <br> 35 <br> 36 | `distrobox` is available in default repos.(thanks [alcir](https://github.com/alcir)!) |
-| Gentoo | | To setup rootless podman, look [HERE](https://wiki.gentoo.org/wiki/Podman) |
-| Ubuntu | 18.04 <br> 20.04 <br> 21.10 | Older versions based on 20.04 or earlier may need external repos to install newer Podman and Docker releases. <br> Please follow their installation guide: [Podman](https://podman.io/getting-started/installation) [Docker](https://docs.docker.com/engine/install/ubuntu/) <br> Derivatives like Pop_OS!, Mint and Elementary OS should work the same. <br> [Now PPA available!](https://launchpad.net/~michel-slm/+archive/ubuntu/distrobox) (thanks [michel-slm](https://github.com/michel-slm)! |
+| Debian | 11 <br> Testing <br> Unstable | `distrobox` is available in default repos in `unstable` (thanks [michel-slm!](https://github.com/michel-slm!)!) |
| EndlessOS | 4.0.0 | |
-| openSUSE | Tumbleweed <br> MicroOS | `distrobox` is available in default repos (thanks [dfaggioli](https://github.com/dfaggioli)!) <br> For Tumbleweed, do: `zypper install distrobox`. <br> For MicroOS enter in a [transactional update](https://kubic.opensuse.org/documentation/transactional-update-guide/transactional-update.html) shell like this: `tukit --continue execute /bin/bash` (or `transactional-update shell --continue`, if you have `transactional-update` installed). Once inside: `zypper install distrobox`. Then exit the shell (`CTRL+D` is fine) and reboot the system. |
-| openSUSE | Leap 15.4 <br> Leap 15.3 <br> Leap 15.2 | Packages are available [here](https://software.opensuse.org/download/package?package=distrobox&project=home%3Adfaggioli%3Amicroos-desktop) (thanks [dfaggioli](https://github.com/dfaggioli)!).<br> To install on openSUSE Leap 15.4, do: <br> `zypper addrepo https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.4/home:dfaggioli:microos-desktop.repo && zypper refresh && zypper install distrobox`. <br> For earlier versions, the procedure is the same, the link to the repository (i.e., the last argument of the `zypper addrepo` command) is the only thing that changes: [Leap 15.3](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/openSUSE_Leap_15.3/home:dfaggioli:microos-desktop.repo), [Leap 15.2](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/openSUSE_Leap_15.2/home:dfaggioli:microos-desktop.repo).<br>``Podman`` under SUSE Leap, cannot initialize correctly the containers managed by ``distrobox`` until [this OpenSUSE bug](https://bugzilla.opensuse.org/show_bug.cgi?id=1199871&GoAheadAndLogIn=1) is fixed, or ``podman`` loggin is configured properly. ``Docker`` can be used instead, but it is less secure [because it does not work yet in rootless mode](https://github.com/89luca89/distrobox/issues/223).|
-| SUSE Linux Enterprise Server | 15 Service Pack 4 <br> 15 Service Pack 3 <br> 15 Service Pack 2 | Same procedure as the one for openSUSE (Leap, respective versions, of course). Use the following repository links in the `zypper addrepo` command: [SLE-15-SP4](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.4/home:dfaggioli:microos-desktop.repo), [SLE-15-SP3](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.3/home:dfaggioli:microos-desktop.repo), [SLE-15-SP4](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/SLE_15_SP2/home:dfaggioli:microos-desktop.repo). |
-| Void Linux | glibc | Systemd service export will not work. |
+| Fedora Silverblue/Kinoite | 35 <br> 36 <br> Rawhide | `distrobox` is available in default repos.(thanks [alcir](https://github.com/alcir)!) |
+| Fedora | 35 <br> 36 <br> Rawhide | `distrobox` is available in default repos.(thanks [alcir](https://github.com/alcir)!) |
+| Gentoo | | To setup rootless podman, look [HERE](https://wiki.gentoo.org/wiki/Podman) |
+| Manjaro | | To setup rootless podman, look [HERE](https://wiki.archlinux.org/title/Podman) |
| NixOS | 21.11 | Currently you must have your default shell set to Bash, if it is not, make sure you edit your configuration.nix so that it is. <br> Also make sure to mind your executable paths. Sometimes a container will not have nix paths, and sometimes it will not have its own paths. <br> Distrobox is available in Nixpkg collection (thanks [AtilaSaraiva](https://github.com/AtilaSaraiva)!)< <br> To setup Docker, look [HERE](https://nixos.wiki/wiki/Docker) <br> To setup Podman, look [HERE](https://nixos.wiki/wiki/Podman) and [HERE](https://gist.github.com/adisbladis/187204cb772800489ee3dac4acdd9947) |
+| OpenSUSE | Leap 15.4 <br> Leap 15.3 <br> Leap 15.2 | Packages are available [here](https://software.opensuse.org/download/package?package=distrobox&project=home%3Adfaggioli%3Amicroos-desktop) (thanks [dfaggioli](https://github.com/dfaggioli)!).<br> To install on openSUSE Leap 15, Use the following repository links in the `zypper addrepo` command: [15.4](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.4/home:dfaggioli:microos-desktop.repo), [15.3](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.3/home:dfaggioli:microos-desktop.repo), [15.2](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.2/home:dfaggioli:microos-desktop.repo). Then: <br> `zypper refresh && zypper install distrobox`. <br> `Podman` under SUSE Leap, cannot initialize correctly the containers managed by ``distrobox`` until [this OpenSUSE bug](https://bugzilla.opensuse.org/show_bug.cgi?id=1199871) is fixed, or ``podman`` loggin is configured properly. |
+| OpenSUSE | Tumbleweed <br> MicroOS | `distrobox` is available in default repos (thanks [dfaggioli](https://github.com/dfaggioli)!) <br> For Tumbleweed, do: `zypper install distrobox`. <br> For MicroOS, do: `pkcon install distrobox` and reboot the system. |
+| SUSE Linux Enterprise Server | 15 Service Pack 4 <br> 15 Service Pack 3 <br> 15 Service Pack 2 | Same procedure as the one for openSUSE (Leap, respective versions, of course). Use the following repository links in the `zypper addrepo` command: [SLE-15-SP4](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.4/home:dfaggioli:microos-desktop.repo), [SLE-15-SP3](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/15.3/home:dfaggioli:microos-desktop.repo), [SLE-15-SP4](https://download.opensuse.org/repositories/home:dfaggioli:microos-desktop/SLE_15_SP2/home:dfaggioli:microos-desktop.repo). Then: <br> `zypper refresh && zypper install distrobox`. <br> `Podman` under SUSE Leap, cannot initialize correctly the containers managed by ``distrobox`` until [this OpenSUSE bug](https://bugzilla.opensuse.org/show_bug.cgi?id=1199871) is fixed, or ``podman`` loggin is configured properly. |
+| SteamOS 3 | | You can use `steamos-readonly disable` and follow `Arch Linux` instructions. This will **NOT** survive updates.<br>Else you can follow the [Install Podman in a static manner](#install-podman-in-a-static-manner) guide, this will install it in your $HOME and it will survive updates.|
+| RedHat | 8 <br> 9 | `distrobox` is available in epel repos. (thanks [alcir](https://github.com/alcir)!) |
+| Ubuntu | 18.04 <br> 20.04 <br> 21.10 | Older versions based on 20.04 or earlier may need external repos to install newer Podman and Docker releases. <br> Derivatives like Pop_OS!, Mint and Elementary OS should work the same. <br> [Now PPA available!](https://launchpad.net/~michel-slm/+archive/ubuntu/distrobox), also `distrobox` is available in default repos in `22.10` (thanks [michel-slm](https://github.com/michel-slm)!) |
+| Void Linux | glibc | Systemd service export will not work. |
+
+### Install Podman in a static manner
+
+If on your distribution (eg. SteamOS) can be difficult to install something and keep it
+between reboots, then you could use this script to install `podman` in your `$HOME`.
-### Compatibility notes
+This has some limitations, for starters, it won't work in `rootful` mode for now,
+but otherwise it's working for normal use.
+
+This is particularly indicated also for completely *sudoless* setups, where you don't
+have any superuser access to the system, like for example company provided computers.
+
+Run:
+
+```sh
+curl -s https://raw.githubusercontent.com/89luca89/distrobox/main/extras/install-podman | sh -s -- --prefix ~/.local
+```
+
+Provided the only dependency on the host (`newuidmap/newgidmap`, of the package `uidmap`),
+you should be good to go.
+
+To uninstall:
+
+```sh
+curl -s https://raw.githubusercontent.com/89luca89/distrobox/main/extras/install-podman | sh -s -- --prefix ~/.local --remove
+```
+
+#### Compatibility notes
If your container is not able to connect to your host xserver, make sure to
install `xhost` on the host machine and run `xhost +si:localuser:$USER`.
@@ -72,7 +106,7 @@ Note also that in some distributions, root filesystem is **not** mounted as a sh
this will give an error like:
```sh
-$ distrobox-enter
+$ distrobox-enter
Error response from daemon: path /sys is mounted on /sys but it is not a shared or slave mount
Error: failed to start containers: ...
```
@@ -80,7 +114,7 @@ Error: failed to start containers: ...
To resolve this, use this command:
```sh
- mount --make-rshared /
+mount --make-rshared /
```
To make it permanent, you can place it in `/etc/rc.local`.
@@ -105,32 +139,31 @@ Distrobox guests tested successfully with the following container images:
| Distro | Version | Images |
| --- | --- | --- |
-| AlmaLinux | 8 <br> 8-minimal <br> 9 <br> 9-minimal | docker.io/library/almalinux:8 <br> docker.io/library/almalinux:9 <br> docker.io/library/almalinux:9-minimal |
-| AlmaLinux (UBI) | 8 | docker.io/almalinux/8-base <br> docker.io/almalinux/8-init |
-| Alpine Linux | 3.14 <br> 3.15 | docker.io/library/alpine:latest |
-| AmazonLinux | 2 | docker.io/library/amazonlinux:2.0.20211005.0 |
-| AmazonLinux | 2022 | public.ecr.aws/amazonlinux/amazonlinux:2022 |
+| AlmaLinux (UBI) | 8 | quay.io/almalinux/8-base:8 <br> quay.io/almalinux/8-init:8 |
+| AlmaLinux | 8 <br> 8-minimal <br> 9 <br> 9-minimal | quay.io/almalinux/almalinux:8 <br> quay.io/almalinux/almalinux:9 <br> quay.io/almalinux/almalinux:9-minimal |
+| Alpine Linux | 3.15 <br> 3.16 | docker.io/library/alpine:3.15 <br> docker.io/library/alpine:3.16 <br> docker.io/library/alpine:latest |
+| AmazonLinux | 1 <br> 2 <br> 2022 | public.ecr.aws/amazonlinux/amazonlinux:1 <br> public.ecr.aws/amazonlinux/amazonlinux:2 <br> public.ecr.aws/amazonlinux/amazonlinux:2022.0.20220531.0 |
| Archlinux | | docker.io/library/archlinux:latest |
-| ClearLinux | | docker.io/library/clearlinux:latest <br> docker.io/library/clearlinux:base |
-| CentOS | 7 | quay.io/centos/centos:7 |
| CentOS Stream | 8 <br> 9 | quay.io/centos/centos:stream8 <br> quay.io/centos/centos:stream9 |
-| RedHat (UBI) | 7 <br> 8 <br> 9 | registry.access.redhat.com/ubi7/ubi <br> registry.access.redhat.com/ubi7/ubi-init <br> registry.access.redhat.com/ubi7/ubi-minimal <br> registry.access.redhat.com/ubi8/ubi <br> registry.access.redhat.com/ubi8/ubi-init <br> registry.access.redhat.com/ubi8/ubi-minimal <br> registry.access.redhat.com/ubi9/ubi <br> registry.access.redhat.com/ubi9/ubi-init <br> registry.access.redhat.com/ubi9/ubi-minimal |
+| CentOS | 7 | quay.io/centos/centos:7 |
+| ClearLinux | | docker.io/library/clearlinux:latest <br> docker.io/library/clearlinux:base |
| Debian | 7 <br> 8 <br> 9 <br> 10 <br> 11 | docker.io/debian/eol:wheezy <br> docker.io/library/debian:8 <br> docker.io/library/debian:9 <br> docker.io/library/debian:10 <br> docker.io/library/debian:stable <br> docker.io/library/debian:stable-backports |
| Debian | Testing | docker.io/library/debian:testing <br> docker.io/library/debian:testing-backports |
| Debian | Unstable | docker.io/library/debian:unstable |
-| Neurodebian | nd100 | docker.io/library/neurodebian:nd100 |
-| Fedora | 34 <br> 35 <br> 36 <br> 37 <br> Rawhide | registry.fedoraproject.org/fedora-toolbox:34 <br> docker.io/library/fedora:34 <br> registry.fedoraproject.org/fedora-toolbox:35 <br> docker.io/library/fedora:35 <br> docker.io/library/fedora:36 <br> registry.fedoraproject.org/fedora:37 <br> docker.io/library/fedora:rawhide |
+| Fedora | 35 <br> 36 <br> 37 <br> Rawhide | registry.fedoraproject.org/fedora-toolbox:35 <br> quay.io/fedora/fedora:35 <br> quay.io/fedora/fedora:36 <br> registry.fedoraproject.org/fedora:37 <br> quay.io/fedora/fedora:rawhide |
+| Gentoo Linux | rolling | You will have to [Build your own](distrobox_gentoo.md) to have a complete Gentoo docker image |
+| Kali Linux | rolling | docker.io/kalilinux/kali-rolling:latest |
| Mageia | 8 | docker.io/library/mageia |
+| Neurodebian | nd100 | docker.io/library/neurodebian:nd100 |
| Opensuse | Leap | registry.opensuse.org/opensuse/leap:latest |
| Opensuse | Tumbleweed | registry.opensuse.org/opensuse/tumbleweed:latest <br> registry.opensuse.org/opensuse/toolbox:latest |
-| Oracle Linux | 7 <br> 8 | container-registry.oracle.com/os/oraclelinux:7 <br> container-registry.oracle.com/os/oraclelinux:8 |
-| Rocky Linux | 8 | docker.io/rockylinux/rockylinux:8 |
+| Oracle Linux | 7 <br> 7-slim <br> 8 <br> 8-slim <br> 9 <br> 9-slim |container-registry.oracle.com/os/oraclelinux:7 <br> container-registry.oracle.com/os/oraclelinux:7-slim <br> container-registry.oracle.com/os/oraclelinux:8 <br> container-registry.oracle.com/os/oraclelinux:8-slim <br> container-registry.oracle.com/os/oraclelinux:9 <br> container-registry.oracle.com/os/oraclelinux:9-slim |
+| RedHat (UBI) | 7 <br> 8 <br> 9 | registry.access.redhat.com/ubi7/ubi <br> registry.access.redhat.com/ubi7/ubi-init <br> registry.access.redhat.com/ubi7/ubi-minimal <br> registry.access.redhat.com/ubi8/ubi <br> registry.access.redhat.com/ubi8/ubi-init <br> registry.access.redhat.com/ubi8/ubi-minimal <br> registry.access.redhat.com/ubi9/ubi <br> registry.access.redhat.com/ubi9/ubi-init <br> registry.access.redhat.com/ubi9/ubi-minimal |
+| Rocky Linux | 8 <br> 8-minimal | quay.io/rockylinux/rockylinux:8 <br> quay.io/rockylinux/rockylinux:8-minimal <br> quay.io/rockylinux/rockylinux:latest |
| Scientific Linux | 7 | docker.io/library/sl:7 |
| Slackware | 14.2 | docker.io/vbatts/slackware:14.2 |
-| Ubuntu | 14.04 <br> 16.04 <br> 18.04 <br> 20.04 <br> 21.10 <br> 22.04 | docker.io/library/ubuntu:14.04 <br> docker.io/library/ubuntu:16.04 <br> docker.io/library/ubuntu:18.04 <br> docker.io/library/ubuntu:20.04 <br> docker.io/library/ubuntu:21.10 <br> docker.io/library/ubuntu:22.04 |
-| Kali Linux | rolling | docker.io/kalilinux/kali-rolling:latest |
+| Ubuntu | 14.04 <br> 16.04 <br> 18.04 <br> 20.04 <br> 22.04 | docker.io/library/ubuntu:14.04 <br> docker.io/library/ubuntu:16.04 <br> docker.io/library/ubuntu:18.04 <br> docker.io/library/ubuntu:20.04 <br> docker.io/library/ubuntu:22.04 |
| Void Linux | | ghcr.io/void-linux/void-linux:latest-full-x86_64 <br> ghcr.io/void-linux/void-linux:latest-full-x86_64-musl |
-| Gentoo Linux | rolling | You will have to [Build your own](distrobox_gentoo.md) to have a complete Gentoo docker image |
Note however that if you use a non-toolbox preconfigured image (e.g.
images pre-baked to work with <https://github.com/containers/toolbox),>
diff --git a/docs/distrobox_gentoo.md b/docs/distrobox_gentoo.md
index a39eb87..a475d18 100644
--- a/docs/distrobox_gentoo.md
+++ b/docs/distrobox_gentoo.md
@@ -11,7 +11,7 @@ You need to build your own image. The official resource is [here](https://github
but here is a simple Dockerfile:
``` Dockerfile
-FROM registry.hub.docker.com/gentoo/portage:latest
+FROM registry.hub.docker.com/gentoo/portage:latest as portage
FROM registry.hub.docker.com/gentoo/stage3:systemd
COPY --from=portage /var/db/repos/gentoo /var/db/repos/gentoo
```
diff --git a/docs/featured_articles.md b/docs/featured_articles.md
index 8984eb6..fe4c054 100644
--- a/docs/featured_articles.md
+++ b/docs/featured_articles.md
@@ -9,6 +9,7 @@
- [Run Distrobox on Fedora Linux - Fedora Magazine](https://fedoramagazine.org/run-distrobox-on-fedora-linux/)
- [DistroBox – Run Any Linux Distribution Inside Linux Terminal - TecMint](https://www.tecmint.com/distrobox-run-any-linux-distribution/)
+- [Distrobox: Try Multiple Linux Distributions via the Terminal - It's FOSS](https://itsfoss.com/distrobox/)
- [Distrobox - How to quickly deploy a Linux distribution with GUI applications via a container](https://www.techrepublic.com/article/how-to-quickly-deploy-a-linux-distribution-with-gui-applications-via-a-container/)
- [Using Distrobox To Augment The Package Selection On Clear Linux - Phoronix](https://www.phoronix.com/scan.php?page=news_item&px=Distrobox-Clear-Linux)
- [Benchmark: benefits of Clear Linux containers (distrobox) - Phoronix](https://www.phoronix.com/forums/forum/phoronix/latest-phoronix-articles/1305326-clear-linux-container-performance-continues-showing-sizable-gains)
@@ -16,12 +17,16 @@
- Running Other Linux Distros with Distrobox on Fedora Linux - bandithijo's blog:
[ORIGINAL](https://bandithijo.github.io/blog/menjalankan-distro-linux-lain-dengan-distrobox-di-fedora-linux)
or [TRANSLATED](https://bandithijo-github-io.translate.goog/blog/menjalankan-distro-linux-lain-dengan-distrobox-di-fedora-linux?_x_tr_sl=id&_x_tr_tl=en&_x_tr_hl=it&_x_tr_pto=wapp)
+- [Distrobox: Run (pretty much) any Linux distro under almost any other - TheRegister](https://www.theregister.com/2022/05/31/distrobox_130_released/)
- [Day-to-day differences between Fedora Silverblue and Ubuntu - castrojo's blog](https://www.ypsidanger.com/day-to-day-advantages-of-fedora-silverblue/)
- [Distrobox is Awesome - Running Window Manager and Desktop environments using Distrobox](https://cloudyday.tech.blog/2022/05/14/distrobox-is-awesome/)
+- [Japanese input on Clear Linux with Mozc via Ubuntu container with Distrobox](https://impsbl.hatenablog.jp/entry/JapaneseInputOnClearLinuxWithMozc_en)
+- [MID (MaXX Interactive Desktop) on Clear Linux via Ubuntu container with Distrobox](https://impsbl.hatenablog.jp/entry/MIDonClearLinuxWithDistrobox_en)
## Talks
- [Linux App Summit 2022 - Distrobox: Run Any App On Any Distro - BoF](https://github.com/89luca89/distrobox/files/8598433/distrobox-las-talk.pdf)
+- [A "Box" Full of Tools and Distros - Dario Faggioli @ OpenSUSE Conference 2022](https://www.youtube.com/watch?v=_RzARte80SQ)
## Podcasts
diff --git a/docs/posts/execute_commands_on_host.md b/docs/posts/execute_commands_on_host.md
index 706158f..c70c814 100644
--- a/docs/posts/execute_commands_on_host.md
+++ b/docs/posts/execute_commands_on_host.md
@@ -1,10 +1,10 @@
- [Distrobox](../README.md)
- - [Execute a command on the Host](execute_commands_on_host.md)
- - [With distrobox-host-exec](#distrobox-host-exec)
- - [Manually](#manually)
- - [The easy one](#the-easy-one)
- - [The not so easy one](#the-not-so-easy-one)
+ - [Execute a command on the host](#execute-a-command-on-the-host)
+ - [With distrobox-host-exec](#with-distrobox-host-exec)
+ - [Using symlinks](#using-symlinks)
- [Integrate host with container seamlessly](#integrate-host-with-container-seamlessly)
+ - [bash or zsh](#bash-or-zsh)
+ - [fish](#fish)
---
@@ -21,53 +21,47 @@ distrobox offers the `distrobox-host-exec` helper, that can be used exactly for
See [distrobox-host-exec](../usage/distrobox-host-exec.md).
-## Manually
-
-### The easy one
-
-Install `flatpak-spawn` inside the container, this example is running on a
-Fedora Distrobox:
-
-```shell
-~$ distrobox create --image fedora:35 --name fedora-distrobox
-~$ distrobox enter --name fedora-distrobox
-user at fedora-distrobox:~$ sudo dnf install -y flatpak-spawn
-```
-
-With `flatpak-spawn` we can easily execute commands on the host using:
+```console
+user at fedora-distrobox:~$ which podman
+/usr/bin/which: no podman in [...]
+user at fedora-distrobox:~$ distrobox-host-exec podman version # <-- this is executed on host.
+Client:
+Version: 3.4.2
+API Version: 3.4.2
+Go Version: go1.16.6
+Built: Thu Jan 1 01:00:00 1970
+OS/Arch: linux/amd64
-```shell
-user at fedora-distrobox:~$ flatpak-spawn --host bash -l
-~$ # We're back on host!
+Server:
+Version: 3.4.2
+API Version: 3.4.2
+Go Version: go1.16.6
+Built: Thu Jan 1 01:00:00 1970
+OS/Arch: linux/amd64
```
-### The not so easy one
-
-Alternatively you may don't have `flatpak-spawn` in the repository of your container,
-or simply want an alternative.
+## Using symlinks
-We can use `chroot` to enter back into the host, and execute what we need!
+Another way to execute commands on the host, is to create executables symlinking `distrobox-host-exec`:
-Create an executable file with this content:
-
-```shell
-#!/bin/sh
-
-result_command="sudo -E chroot --userspec=$(id -u):$(id -g) /run/host/ /usr/bin/env "
-for i in $(printenv | grep "=" | grep -Ev ' |"' | grep -Ev "^(_)"); do
- result_command="$result_command $i"
-done
-
-exec ${result_command} sh -c " cd ${PWD} && $@"
-```
-
-in `~/.local/bin/host-exec` and make it executable with `chmod +x ~/.local/bin/host-exec`
-
-Now we can simply use this to exec stuff back on the host:
+```console
+user at fedora-distrobox:~$ ln -s /usr/bin/distrobox-host-exec /usr/local/bin/podman
+user at fedora-distrobox:~$ ls -l /usr/local/bin/podman
+lrwxrwxrwx. 1 root root 51 Jul 11 19:26 /usr/local/bin/podman -> /usr/bin/distrobox-host-exec
+user at fedora-distrobox:~$ podman version # <-- this is executed on host. Equivalent to "distrobox-host-exec podman version"
+Client:
+Version: 3.4.2
+API Version: 3.4.2
+Go Version: go1.16.6
+Built: Thu Jan 1 01:00:00 1970
+OS/Arch: linux/amd64
-```shell
-user at fedora-distrobox:~$ host-exec bash -l
-~$ # We're back on host!
+Server:
+Version: 3.4.2
+API Version: 3.4.2
+Go Version: go1.16.6
+Built: Thu Jan 1 01:00:00 1970
+OS/Arch: linux/amd64
```
# Integrate host with container seamlessly
@@ -75,30 +69,22 @@ user at fedora-distrobox:~$ host-exec bash -l
Another cool trick we can pull, is to use the handy `command_not_found_handle` function
to try and execute missing commands in the container on the host.
-## bash / zsh
+## bash or zsh
Place this in your `~/.profile`:
```shell
command_not_found_handle() {
- # don't run if not in a container
- if [ ! -e /run/.containerenv ] &&
- [ ! -e /.dockerenv ]; then
- exit 127
- fi
-
- if command -v flatpak-spawn >/dev/null 2>&1; then
- flatpak-spawn --host "${@}"
- elif command -v host-exec >/dev/null 2>&1; then
- host-exec "$@"
- else
- exit 127
- fi
+# don't run if not in a container
+ if [ ! -e /run/.containerenv ] && [ ! -e /.dockerenv ]; then
+ exit 127
+ fi
+
+ distrobox-host-exec "${@}"
}
-
if [ -n "${ZSH_VERSION-}" ]; then
- command_not_found_handler() {
- command_not_found_handle "$@"
+ command_not_found_handler() {
+ command_not_found_handle "$@"
}
fi
```
@@ -111,13 +97,7 @@ Place this snippet in a new fish function file (`~/.config/fish/functions/fish_c
function fish_command_not_found
# "In a container" check
if test -e /run/.containerenv -o -e /.dockerenv
- if command -q flatpak-spawn
- flatpak-spawn --host $argv
- else if command -q host-exec
- host-exec "$argv"
- else
- __fish_default_command_not_found_handler $argv
- end
+ distrobox-host-exec "$argv"
else
__fish_default_command_not_found_handler $argv
end
diff --git a/docs/posts/integrate_vscode_distrobox.md b/docs/posts/integrate_vscode_distrobox.md
index f5a5c11..514fc67 100644
--- a/docs/posts/integrate_vscode_distrobox.md
+++ b/docs/posts/integrate_vscode_distrobox.md
@@ -1,11 +1,11 @@
- [Distrobox](../README.md)
- - [Integrate VSCode and Distrobox](integrate_vscode_distrobox.md)
+ - [Integrate VSCode and Distrobox](#integrate-vscode-and-distrobox)
- [The easy one](#the-easy-one)
- [The not so easy one](#the-not-so-easy-one)
- - [First step, install it](#first-step--install-it)
- - [Second step, extensions](#second-step--extensions)
- - [Third step, podman wrapper](#third-step--podman-wrapper)
- - [Fourth step, configure the container](#fourth-step--configure-the-container)
+ - [First step, install it](#first-step-install-it)
+ - [Second step, extensions](#second-step-extensions)
+ - [Third step, podman wrapper](#third-step-podman-wrapper)
+ - [Fourth step, configure the container](#fourth-step-configure-the-container)
- [Final Result](#final-result)
---
@@ -60,7 +60,7 @@ to integrate VSCode installed via **Flatpak** with Distrobox.
Note that this integration process is inspired by the awesome project [toolbox-vscode](https://github.com/owtaylor/toolbox-vscode)
so many thanks to @owtaylor for the heavy lifting!
-### First step, install it
+### First step install it
```shell
~$ flatpak install --user app/com.visualstudio.code
@@ -72,7 +72,7 @@ Now we want to install VSCode [Remote Container extension](https://marketplace.v
![image](https://user-images.githubusercontent.com/598882/149207447-76a82e91-dd3f-43fa-8c52-9c2e85ae8fee.png)
-### Third step, podman wrapper
+### Third step podman wrapper
Being in a Flatpak, we will need access to host's `podman` (or `docker`) to be
able to use the containers. Place this in your `~/.local/bin/podman-host`
@@ -107,7 +107,7 @@ set it to the path of `podman-exec`, like in the example
This will give a way to execute host's container manager from within the
flatpak app.
-### Fourth step, configure the container
+### Fourth step configure the container
We need not to deploy a configuration for our container. We should create one for
each Distrobox we choose to integrate with VSCode:
@@ -120,20 +120,14 @@ each Distrobox we choose to integrate with VSCode:
"remote.containers.copyGitConfig": false,
"remote.containers.gitCredentialHelperConfigLocation": "none",
"terminal.integrated.profiles.linux": {
- "capsh": {
- "path": "/usr/sbin/capsh",
+ "shell": {
+ "path": "${localEnv:SHELL}",
"args": [
- "--caps=",
- "--",
- "-c",
- "exec \"$@\"",
- "/bin/sh",
- "${localEnv:SHELL}",
"-l"
]
}
},
- "terminal.integrated.defaultProfile.linux": "capsh"
+ "terminal.integrated.defaultProfile.linux": "shell"
},
"remoteEnv": {
"COLORTERM": "${localEnv:COLORTERM}",
diff --git a/docs/usage/distrobox-create.md b/docs/usage/distrobox-create.md
index f5b6412..bc76136 100644
--- a/docs/usage/distrobox-create.md
+++ b/docs/usage/distrobox-create.md
@@ -1,43 +1,27 @@
-<!-- markdownlint-disable MD010 -->
-# Create the distrobox
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox create
+ distrobox-create
+
+# DESCRIPTION
distrobox-create takes care of creating the container with input name and image.
The created container will be tightly integrated with the host, allowing sharing of
the HOME directory of the user, external storage, external usb devices and
graphical apps (X11/Wayland), and audio.
-Usage:
-
- distrobox create --image alpine:latest --name test --init-hooks "touch /var/tmp/test1 && touch /var/tmp/test2"
- distrobox create --image fedora:35 --name test --additional-flags "--env MY_VAR-value"
- distrobox create --image fedora:35 --name test --volume /opt/my-dir:/usr/local/my-dir:rw --additional-flags "--pids-limit -1"
- distrobox create -i docker.io/almalinux/8-init --init --name test --pre-init-hooks "dnf config-manager --enable powertools && dnf -y install epel-release"
- distrobox create --clone fedora-35 --name fedora-35-copy
- distrobox create --image alpine my-alpine-container
- distrobox create --image registry.fedoraproject.org/fedora-toolbox:35 --name fedora-toolbox-35
- distrobox create --pull --image centos:stream9 --home ~/distrobox/centos9
-
-You can also use environment variables to specify container name, image and container manager:
-
- DBX_CONTAINER_MANAGER="docker" DBX_NON_INTERACTIVE=1 DBX_CONTAINER_NAME=test-alpine DBX_CONTAINER_IMAGE=alpine distrobox-create
-
-Supported environment variables:
-
- DBX_CONTAINER_ALWAYS_PULL
- DBX_CONTAINER_CUSTOM_HOME
- DBX_CONTAINER_IMAGE
- DBX_CONTAINER_MANAGER
- DBX_CONTAINER_NAME
- DBX_NON_INTERACTIVE
+# SYNOPSIS
-Options:
+**distrobox create**
--image/-i: image to use for the container default: registry.fedoraproject.org/fedora-toolbox:36
--name/-n: name for the distrobox default: my-distrobox
--pull/-p: pull latest image unconditionally without asking
--yes/-Y: non-interactive, pull images without asking
--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
--clone/-c: name of the distrobox container to use as base for a new container
this will be useful to either rename an existing distrobox or have multiple copies
of the same environment.
@@ -53,13 +37,38 @@ Options:
--verbose/-v: show more verbosity
--version/-V: show version
-Compatibility:
+# COMPATIBILITY
for a list of compatible images and container managers, please consult the man page:
man distrobox
man distrobox-compatibility
or consult the documentation page on: https://github.com/89luca89/distrobox/blob/main/docs/compatibility.md#containers-distros
+# EXAMPLES
+
+ distrobox create --image alpine:latest --name test --init-hooks "touch /var/tmp/test1 && touch /var/tmp/test2"
+ distrobox create --image fedora:35 --name test --additional-flags "--env MY_VAR-value"
+ distrobox create --image fedora:35 --name test --volume /opt/my-dir:/usr/local/my-dir:rw --additional-flags "--pids-limit -1"
+ distrobox create -i docker.io/almalinux/8-init --init --name test --pre-init-hooks "dnf config-manager --enable powertools && dnf -y install epel-release"
+ distrobox create --clone fedora-35 --name fedora-35-copy
+ distrobox create --image alpine my-alpine-container
+ distrobox create --image registry.fedoraproject.org/fedora-toolbox:35 --name fedora-toolbox-35
+ distrobox create --pull --image centos:stream9 --home ~/distrobox/centos9
+
+You can also use environment variables to specify container name, image and container manager:
+
+ DBX_CONTAINER_MANAGER="docker" DBX_NON_INTERACTIVE=1 DBX_CONTAINER_NAME=test-alpine DBX_CONTAINER_IMAGE=alpine distrobox-create
+
+Supported environment variables:
+
+ DBX_CONTAINER_ALWAYS_PULL
+ DBX_CONTAINER_CUSTOM_HOME
+ DBX_CONTAINER_IMAGE
+ DBX_CONTAINER_MANAGER
+ DBX_CONTAINER_NAME
+ DBX_NON_INTERACTIVE
+ DBX_SUDO_PROGRAM
+
The `--additional-flags` or `-a` is useful to modify defaults in the container creations.
For example:
@@ -109,3 +118,6 @@ Inside the container we will be able to use normal systemd units:
Note that enabling `--init` **will disable host's process integration**.
From within the container you will not be able to see and manage host's processes.
This is needed because `/sbin/init` must be pid 1.
+
+From version 1.4.0 of distrobox, when you create a new container, it will also generate
+an entry in the applications list.
diff --git a/docs/usage/distrobox-enter.md b/docs/usage/distrobox-enter.md
index 9224ec0..3ed720e 100644
--- a/docs/usage/distrobox-enter.md
+++ b/docs/usage/distrobox-enter.md
@@ -1,5 +1,10 @@
-<!-- markdownlint-disable MD010 -->
-# Enter the distrobox
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox enter
+ distrobox-enter
+
+# DESCRIPTION
distrobox-enter takes care of entering the container with the name specified.
Default command executed is your SHELL, but you can specify different shells or
@@ -7,7 +12,24 @@ entire commands to execute.
If using it inside a script, an application, or a service, you can specify the
--headless mode to disable tty and interactivity.
-Usage:
+# SYNOPSIS
+
+**distrobox enter**
+
+ --name/-n: name for the distrobox default: my-distrobox
+ --/-e: end arguments execute the rest as command to execute at login default: bash -l
+ --no-tty/-T: do not instantiate a tty
+ --no-workdir/-nw: always start the container from container's home directory
+ --additional-flags/-a: additional flags to pass to the container manager command
+ --help/-h: show this message
+ --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
+ --dry-run/-d: only print the container manager command generated
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+# EXAMPLES
distrobox-enter --name fedora-toolbox-35 -- bash -l
distrobox-enter my-alpine-container -- sh -l
@@ -24,20 +46,7 @@ Supported environment variables:
DBX_CONTAINER_NAME
DBX_CONTAINER_MANAGER
DBX_SKIP_WORKDIR
-
-Options:
-
- --name/-n: name for the distrobox default: my-distrobox
- --/-e: end arguments execute the rest as command to execute at login default: bash -l
- --no-tty/-T: do not instantiate a tty
- --no-workdir/-nw: always start the container from container's home directory
- --additional-flags/-a: additional flags to pass to the container manager command
- --help/-h: show this message
- --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
- --dry-run/-d: only print the container manager command generated
- --verbose/-v: show more verbosity
- --version/-V: show version
+ DBX_SUDO_PROGRAM
This is used to enter the distrobox itself. Personally, I just create multiple profiles in
my `gnome-terminal` to have multiple distros accessible.
@@ -52,3 +61,13 @@ This is possible also using normal env variables:
my_var=test distrobox enter -n dev-arch --additional-flags -- printenv &| grep my_var
my_var=test
+
+If you'd like to enter a rootful container having distrobox use a program other than 'sudo' to
+run podman/docker as root, such as 'pkexec' or 'doas', you may specify it with the
+`DBX_SUDO_PROGRAM` environment variable. For example, to use 'doas' to enter a rootful container:
+
+ DBX_SUDO_PROGRAM="doas" distrobox enter -n container --root
+
+Additionally, in one of the config file paths that distrobox supports, such as `~/.distroboxrc`,
+you can also append the line `distrobox_sudo_program="doas"` (for example) to always run
+distrobox commands involving rootful containers using 'doas'.
diff --git a/docs/usage/distrobox-ephemeral.md b/docs/usage/distrobox-ephemeral.md
new file mode 100644
index 0000000..258077c
--- /dev/null
+++ b/docs/usage/distrobox-ephemeral.md
@@ -0,0 +1,42 @@
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox ephemeral
+ distrobox-ephemeral
+
+# DESCRIPTION
+
+distrobox-ephemeral creates a temporary distrobox that is automatically destroyed
+when the command is terminated.
+
+# SYNOPSIS
+
+**distrobox ephemeral**
+
+ --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
+ --verbose/-v: show more verbosity
+ --help/-h: show this message
+ --/-e: end arguments execute the rest as command to execute at login default: bash -l
+ --version/-V: show version
+
+# EXAMPLES
+
+ distrobox-ephemeral --image alpine:latest -- cat /etc/os-release
+ distrobox-ephemeral --root --verbose --image alpine:latest --volume /opt:/opt
+
+You can also use [flags from **distrobox-create**](distrobox-create.md) to customize the ephemeral container to run.
+
+Refer to
+
+ man distrobox-create
+
+or
+
+ distrobox-create --help
+
+Supported environment variables:
+
+ distrobox-ephemeral calls distrobox-create, SEE ALSO distrobox-create(1) for
+ a list of supported environment variables to use.
diff --git a/docs/usage/distrobox-export.md b/docs/usage/distrobox-export.md
index 435efb9..4008f6c 100644
--- a/docs/usage/distrobox-export.md
+++ b/docs/usage/distrobox-export.md
@@ -1,5 +1,12 @@
-<!-- markdownlint-disable MD010 -->
-# Application and service exporting
+<!-- markdownlint-disable MD010 MD036 -->
+
+# NAME
+
+ distrobox-export
+
+# DESCRIPTION
+
+**Application and service exporting**
distrobox-export takes care of exporting an app a binary or a service from the container
to the host.
@@ -7,16 +14,72 @@ to the host.
The exported app will be easily available in your normal launcher and it will
automatically be launched from the container it is exported from.
+# SYNOPSIS
+
+**distrobox-export**
+
+ --app/-a: name of the application to export
+ --bin/-b: absolute path of the binary to export
+ --service/-s: name of the service to export
+ --delete/-d: delete exported application or service
+ --export-label/-el: label to add to exported application name.
+ Defaults to (on \$container_name)
+ --export-path/-ep: path where to export the binary
+ --extra-flags/-ef: extra flags to add to the command
+ --sudo/-S: specify if the exported item should be run as sudo
+ --help/-h: show this message
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+You may want to install graphical applications or user services in your distrobox.
+Using `distrobox-export` from **inside** the container will let you use them from the host itself.
+
+# EXAMPLES
+
+ distrobox-export --app mpv [--extra-flags "flags"] [--delete] [--sudo]
+ distrobox-export --service syncthing [--extra-flags "flags"] [--delete] [--sudo]
+ distrobox-export --bin /path/to/bin --export-path ~/.local/bin [--extra-flags "flags"] [--delete] [--sudo]
+
+**App export example**
+
+ distrobox-export --app abiword
+
+This tool will simply copy the original `.desktop` files along with needed icons,
+add the prefix `/usr/local/bin/distrobox-enter -n distrobox_name -e ...` to the commands to run, and
+save them in your home to be used directly from the host as a normal app.
+
+**Service export example**
+
+ distrobox-export --service syncthing --extra-flags "--allow-newer-config"
+ distrobox-export --service nginx --sudo
+
+For services, it will similarly export the systemd unit inside the container to a
+`systemctl --user` service, prefixing the various
+`ExecStart ExecStartPre ExecStartPost ExecReload ExecStop ExecStopPost` with the
+`distrobox-enter` command prefix.
+
The exported services will be available in the host's user's systemd session, so
systemctl --user status exported_service_name
will show the status of the service exported.
+**Binary export example**
+
+ distrobox-export --bin /usr/bin/code --extra-flags "--foreground" --export-path $HOME/.local/bin
+
+In the case of exporting binaries, you will have to specify **where** to export it
+(`--export-path`) and the tool will create a little wrapper script that will
+`distrobox-enter -e` from the host, the desired binary.
+This can be handy with the use of `direnv` to have different versions of the same binary based on
+your `env` or project.
+
The exported binaries will be exported in the "--export-path" of choice as a wrapper
script that acts naturally both on the host and in the container.
Note that "--export-path" is NOT OPTIONAL, you have to explicitly set it.
+**Additional flags**
+
You can specify additional flags to add to the command, for example if you want
to export an electron app, you could add the "--foreground" flag to the command:
@@ -28,6 +91,8 @@ This works for services, binaries, and apps.
Extra flags are only used then the exported app, binary, or service is used from
the host, using them inside the container will not include them.
+**Unexport**
+
The option "--delete" will un-export an app, binary, or service.
distrobox-export --app atom --delete
@@ -35,63 +100,62 @@ The option "--delete" will un-export an app, binary, or service.
distrobox-export --service syncthing --delete
distrobox-export --service nginx --delete
+**Run as root in the container**
+
The option "--sudo" will launch the exported item as root inside the distrobox.
-Note you can use --app OR --bin OR --service but not together.
+**Exporting apps from rootful containers**
- distrobox-export --service nginx --sudo
+It is worth noting that, when exporting any item - which includes graphical apps - from rootful
+containers (created with `distrobox create --root`), root privileges will be needed every time
+the item is launched (in order to enter the rootful container), which, by default, is done
+using `sudo` (see docs for `distrobox-enter` on how to customize that). However, for
+graphical apps in specific, since they launch without a terminal, the usage of `sudo`
+might, at first, make it impossible to launch them.
-Usage:
+To fix this without needing to customize the sudo program, one can define a global
+`SUDO_ASKPASS` environment variable on their machine, which is a PATH to an executable
+that is run by `sudo` when no terminal is available (or when it is given the `--askpass`
+or `-A` option), and the output of that executable to stdout is used as the password input.
+The executable is called as many times is needed for authentication as root to succeed
+(unless a limit of amount of attempts is reached).
- distrobox-export --app mpv [--extra-flags "flags"] [--delete] [--sudo]
- distrobox-export --service syncthing [--extra-flags "flags"] [--delete] [--sudo]
- distrobox-export --bin /path/to/bin --export-path ~/.local/bin [--extra-flags "flags"] [--delete] [--sudo]
-
-Options:
-
- --app/-a: name of the application to export
- --bin/-b: absolute path of the binary to export
- --service/-s: name of the service to export
- --delete/-d: delete exported application or service
- --export-label/-el: label to add to exported application name.
- Defaults to (on \$container_name)
- --export-path/-ep: path where to export the binary
- --extra-flags/-ef: extra flags to add to the command
- --sudo/-S: specify if the exported item should be ran as sudo
- --help/-h: show this message
- --verbose/-v: show more verbosity
- --version/-V: show version
+To do this, pick a program to ask the user for graphical password input. In this example,
+we will use `zenity --password`, which should be present for GNOME users (and can
+also be installed in other DEs) - there are other options, such as
+`kdialog --password "Message"` for KDE users.
-You may want to install graphical applications or user services in your distrobox.
-Using `distrobox-export` from **inside** the container will let you use them from the host itself.
+Write the call to the desired program to a script file, for example to
+`/usr/bin/my-password-prompt` (sample contents below):
-App export example:
+ #!/bin/sh
+ zenity --password "Authentication as root is required"
- distrobox-export --app abiword
+(You may save the script under, for example, `~/.local/bin` if you want to keep it
+fully local to your user.)
-This tool will simply copy the original `.desktop` files along with needed icons,
-add the prefix `/usr/local/bin/distrobox-enter -n distrobox_name -e ...` to the commands to run, and
-save them in your home to be used directly from the host as a normal app.
+Afterwards, make it executable (e.g. run `sudo chmod +x /usr/bin/my-password-prompt`). Then,
+make sure to set `SUDO_ASKPASS` to `"/usr/bin/my-password-prompt"` (replace with your script's path)
+in a global profile file, so that it is picked up by sudo when running graphical apps (and, therefore,
+sudo will run the script you created to ask for a password).
+This is done with the shell line `export SUDO_ASKPASS="/path/to/script/goes/here"`.
+You can do this for your user only by running the command below (replace the script path as needed):
-Service export example:
+ echo 'export SUDO_ASKPASS="/usr/bin/my-password-prompt"' >> ~/.profile
- distrobox-export --service syncthing --extra-flags "--allow-newer-config"
- distrobox-export --service nginx --sudo
+Which appends the appropriate line to the end of your `~/.profile` file, thus making the change
+local to your user. Alternatively, to set it system-wide (for all users), you may create a file
+in `/etc/profile.d/` (or equivalent for your system) with that line.
-For services, it will similarly export the systemd unit inside the container to a
-`systemctl --user` service, prefixing the various
-`ExecStart ExecStartPre ExecStartPost ExecReload ExecStop ExecStopPost` with the
-`distrobox-enter` command prefix.
+Now just log out and log back in, and graphical apps exported from rootful containers should
+now be properly asking for root's password before launching (instead of not opening, if that
+was the case before).
-Binary export example:
+**Notes**
- distrobox-export --bin /usr/bin/code --extra-flags "--foreground" --export-path $HOME/.local/bin
+Note you can use --app OR --bin OR --service but not together.
-In the case of exporting binaries, you will have to specify **where** to export it
-(`--export-path`) and the tool will create a little wrapper script that will
-`distrobox-enter -e` from the host, the desired binary.
-This can be handy with the use of `direnv` to have different versions of the same binary based on
-your `env` or project.
+ distrobox-export --service nginx --sudo
![app-export](https://user-images.githubusercontent.com/598882/144294795-c7785620-bf68-4d1b-b251-1e1f0a32a08d.png)
diff --git a/docs/usage/distrobox-generate-entry.md b/docs/usage/distrobox-generate-entry.md
new file mode 100644
index 0000000..3f12891
--- /dev/null
+++ b/docs/usage/distrobox-generate-entry.md
@@ -0,0 +1,24 @@
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox generate-entry
+
+# DESCRIPTION
+
+distrobox-generate-entry will create a desktop icon for one of the available distroboxes.
+This will be then deleted when you remove the matching distrobox.
+
+# SYNOPSIS
+
+**distrobox generate-entry**
+
+ --help/-h: show this message
+ --all/-a: perform for all distroboxes
+ --delete/-d: delete the entry
+ --icon/-i: specify a custom icon [/path/to/icon] (default auto)
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+# EXAMPLES
+
+ distrobox-generate-entry container-name [--delete] [--icon [auto,/path/to/icon]]
diff --git a/docs/usage/distrobox-host-exec.md b/docs/usage/distrobox-host-exec.md
index 52ced6e..b5b12ef 100644
--- a/docs/usage/distrobox-host-exec.md
+++ b/docs/usage/distrobox-host-exec.md
@@ -1,28 +1,39 @@
-<!-- markdownlint-disable MD010 -->
-# Host Command Execution
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox-host-exec
+
+# DESCRIPTION
distrobox-host-exec lets one execute command on the host, while inside of a container.
-If "flatpak-spawn" is installed in the container, this is what is used, and it is the
-most powerful and recommended method. If, instead, "flatpak-spawn" can't be found, it
-still try to get the job done with "chroot" (but beware that not all commands/programs
-will work well in this mode).
+Under the hood, distrobox-host-exec uses `host-spawn` a project that let's us
+execute commands back on the host.
+If the tool is not found the user will be prompted to install it.
+
+# SYNOPSIS
Just pass to "distrobox-host-exec" any command and all its arguments, if any.
distrobox-host-exec [command [arguments]]
-If no command is provided, it will execute "/bin/sh".
+ --help/-h: show this message
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+If no command is provided, it will execute "$SHELL".
-Example usage:
+Alternatively, use symlinks to make `distrobox-host-exec` execute as that command:
+
+ ~$: ln -s /usr/bin/distrobox-host-exec /usr/local/bin/podman
+ ~$: ls -l /usr/local/bin/podman
+ lrwxrwxrwx. 1 root root 51 Jul 11 19:26 /usr/local/bin/podman -> /usr/bin/distrobox-host-exec
+ ~$: podman version
+ ...this is executed on host...
+
+# EXAMPLES
distrobox-host-exec ls
distrobox-host-exec bash -l
distrobox-host-exec flatpak run org.mozilla.firefox
distrobox-host-exec podman ps -a
-
-Options:
-
- --help/-h: show this message
- --verbose/-v: show more verbosity
- --version/-V: show version
diff --git a/docs/usage/distrobox-init.md b/docs/usage/distrobox-init.md
index cfeb72d..b8d4121 100644
--- a/docs/usage/distrobox-init.md
+++ b/docs/usage/distrobox-init.md
@@ -1,22 +1,26 @@
-<!-- markdownlint-disable MD010 -->
-# Init the distrobox (not to be launched manually)
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox-init
+
+# DESCRIPTION
+
+**Init the distrobox (not to be launched manually)**
distrobox-init is the entrypoint of a created distrobox.
Note that this HAS to run from inside a distrobox, will not work if you run it
from your host.
-This is not intended to be used manually, but instead used by distrobox-enter
-to set up the container's entrypoint.
+**This is not intended to be used manually, but instead used by distrobox-create
+to set up the container's entrypoint.**
distrobox-init will take care of installing missing dependencies (eg. sudo), set
up the user and groups, mount directories from the host to ensure the tight
integration.
-Usage:
+# SYNOPSIS
- distrobox-init --name test-user --user 1000 --group 1000 --home /home/test-user
-
-Options:
+**distrobox-init**
--name/-n: user name
--user/-u: uid of the user
@@ -25,12 +29,12 @@ Options:
--help/-h: show this message
--init/-I: whether to use or not init
--pre-init-hooks: commands to execute prior to init
+ --upgrade/-U: run init in upgrade mode
--verbose/-v: show more verbosity
--version/-V: show version
--: end arguments execute the rest as command to execute during init
-This is used as entrypoint for the created container, it will take care of creating the users,
-setting up sudo, mountpoints, and exports.
+# EXAMPLES
-**You should not have to launch this manually**, this is used by `distrobox create` to set up
-container's entrypoint.
+ distrobox-init --name test-user --user 1000 --group 1000 --home /home/test-user
+ distrobox-init --upgrade
diff --git a/docs/usage/distrobox-list.md b/docs/usage/distrobox-list.md
index c15fd79..ad3ea9b 100644
--- a/docs/usage/distrobox-list.md
+++ b/docs/usage/distrobox-list.md
@@ -1,10 +1,28 @@
-<!-- markdownlint-disable MD010 -->
-# List containers
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox list
+ distrobox-list
+
+# DESCRIPTION
distrobox-list lists available distroboxes. It detects them and lists them separately
from the rest of normal podman or docker containers.
-Usage:
+# SYNOPSIS
+
+**distrobox list**
+
+ --help/-h: show this message
+ --no-color: disable color formatting
+ --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
+ --size/-s: show also container size
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+# EXAMPLES
distrobox-list
@@ -15,14 +33,6 @@ You can also use environment variables to specify container manager
Supported environment variables:
DBX_CONTAINER_MANAGER
-
-Options:
-
- --help/-h: show this message
- --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
- --size/-s: show also container size
- --verbose/-v: show more verbosity
- --version/-V: show version
+ DBX_SUDO_PROGRAM
![image](https://user-images.githubusercontent.com/598882/147831082-24b5bc2e-b47e-49ac-9b1a-a209478c9705.png)
diff --git a/docs/usage/distrobox-rm.md b/docs/usage/distrobox-rm.md
index bdbda78..2a9f5e5 100644
--- a/docs/usage/distrobox-rm.md
+++ b/docs/usage/distrobox-rm.md
@@ -1,9 +1,27 @@
-<!-- markdownlint-disable MD010 -->
-# Remove containers
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox rm
+ distrobox-rm
+
+# DESCRIPTION
distrobox-rm delete one of the available distroboxes.
-Usage:
+# SYNOPSIS
+
+**distrobox rm**
+
+ --name/-n: name for the distrobox
+ --force/-f: force deletion
+ --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
+ --help/-h: show this message
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+# EXAMPLES
distrobox-rm --name container-name [--force]
distrobox-rm container-name [-f]
@@ -17,13 +35,4 @@ Supported environment variables:
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
-
-Options:
-
- --name/-n: name for the distrobox
- --force/-f: force deletion
- --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
- --help/-h: show this message
- --verbose/-v: show more verbosity
- --version/-V: show version
+ DBX_SUDO_PROGRAM
diff --git a/docs/usage/distrobox-stop.md b/docs/usage/distrobox-stop.md
index a648f51..78f7ba9 100644
--- a/docs/usage/distrobox-stop.md
+++ b/docs/usage/distrobox-stop.md
@@ -1,12 +1,30 @@
-<!-- markdownlint-disable MD010 -->
-# Stop containers
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox stop
+ distrobox-stop
+
+# DESCRIPTION
distrobox-stop stop a running distrobox.
Distroboxes are left running, even after exiting out of them, so that
subsequent enters are really quick. This is how they can be stopped.
-Usage:
+# SYNOPSIS
+
+**distrobox stop**
+
+ --name/-n: name for the distrobox
+ --yes/-Y: non-interactive, stop without asking
+ --help/-h: show this message
+ --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over "sudo distrobox" (note: if using a program other than 'sudo' for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or 'distrobox_sudo_program' config variable)
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+# EXAMPLES
distrobox-stop --name container-name
distrobox-stop container-name
@@ -20,13 +38,4 @@ Supported environment variables:
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
-
-Options:
-
- --name/-n: name for the distrobox
- --yes/-Y: non-interactive, stop without asking
- --help/-h: show this message
- --root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over "sudo distrobox"
- --verbose/-v: show more verbosity
- --version/-V: show version
+ DBX_SUDO_PROGRAM
diff --git a/docs/usage/distrobox-upgrade.md b/docs/usage/distrobox-upgrade.md
new file mode 100644
index 0000000..87b8859
--- /dev/null
+++ b/docs/usage/distrobox-upgrade.md
@@ -0,0 +1,24 @@
+<!-- markdownlint-disable MD010 MD036 -->
+# NAME
+
+ distrobox-upgrade
+
+# DESCRIPTION
+
+distrobox-upgrade will enter the specified list of containers and will perform
+an upgrade using the container's package manager.
+
+# SYNOPSIS
+
+**distrobox upgrade**
+
+ --help/-h: show this message
+ --all/-a: perform for all distroboxes
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+
+# EXAMPLES
+
+ distrobox-upgrade --all
+ distrobox-upgrade alpine-linux ubuntu22 my-distrobox123
+ distrobox upgrade CONTAINER_NAME [CONTAINER_NAME1 CONTAINER_NAME2 ...]
diff --git a/docs/usage/usage.md b/docs/usage/usage.md
index 01691ae..a06fb92 100644
--- a/docs/usage/usage.md
+++ b/docs/usage/usage.md
@@ -1,10 +1,15 @@
+<!-- markdownlint-disable MD010 MD051 -->
- [Distrobox](../README.md)
- [Outside the distrobox](#outside-the-distrobox)
- [distrobox-create](distrobox-create.md)
- [distrobox-enter](distrobox-enter.md)
+ - [distrobox-ephemeral](distrobox-ephemeral.md)
- [distrobox-list](distrobox-list.md)
- [distrobox-rm](distrobox-rm.md)
- [distrobox-stop](distrobox-stop.md)
+ - [distrobox-upgrade](distrobox-upgrade.md)
+ - [distrobox-generate-entry](distrobox-generate-entry.md)
- [Inside the distrobox](#inside-the-distrobox)
- [distrobox-export](distrobox-export.md)
+ - [distrobox-host-exec](distrobox-host-exec.md)
- [distrobox-init](distrobox-init.md)
diff --git a/docs/useful_tips.md b/docs/useful_tips.md
index 5620a37..4cf1fe7 100644
--- a/docs/useful_tips.md
+++ b/docs/useful_tips.md
@@ -3,6 +3,8 @@
- [Create a distrobox with a custom HOME directory](#create-a-distrobox-with-a-custom-home-directory)
- [Mount additional volumes in a distrobox](#mount-additional-volumes-in-a-distrobox)
- [Use a different shell than the host](#use-a-different-shell-than-the-host)
+ - [Run the container with real root](#run-the-container-with-real-root)
+ - [Using a command other than sudo to run a rootful container](#using-a-command-other-than-sudo-to-run-a-rootful-container)
- [Duplicate an existing distrobox](#duplicate-an-existing-distrobox)
- [Export to the host](#export-to-the-host)
- [Execute commands on the host](#execute-commands-on-the-host)
@@ -25,6 +27,17 @@
# Useful tips
+## Launch a distrobox from you applications list
+
+Starting from distrobox 1.4.0, containers created will automatically generate a desktop entry.
+For containers generated with older versions, you can use:
+
+`distrobox generate-entry you-container-name`
+
+To delete it:
+
+`distrobox generate-entry you-container-name --delete`
+
## Execute complex commands directly from distrobox enter
Sometimes it is necessary to execure complex commands from a distrobox enter,
@@ -59,7 +72,14 @@ Simply use:
## Use a different shell than the host
-By default distrobox will pick up the shell from the host and use it inside the container.
+From version 1.4.0, `distrobox enter` will execute the login shell of the container's user
+by default. So, just change the default shell in the container using:
+
+`chsh -s /bin/shell-to-use`
+
+exit and log back in the container.
+
+For version older than 1.4.0, distrobox will pick up the shell from the host and use it inside the container.
If you want a different one you can use:
`SHELL=/bin/zsh distrobox create -n test`
@@ -79,6 +99,60 @@ with your `$USER`.
`distrobox create --name test --image your-choosen-image:tag --root`
+## Using a command other than sudo to run a rootful container
+
+When using the `--root` option with Distrobox, internally, it uses `sudo` to be able to
+interact with the rootful container through podman/docker, which will prompt for a valid
+root password on the terminal. However, some users might prefer to use a command other
+than `sudo` in order to authenticate as root; for example, `pkexec` could be used to
+display a graphical authentication prompt. If you need this, make sure to specify
+the desired command through the `DBX_SUDO_PROGRAM` environment variable
+(supported by most `distrobox` subcommands), alongside `--root`. Sample usage:
+
+`DBX_SUDO_PROGRAM="pkexec" distrobox create --name test --image your-chosen-image:tag --root`
+
+Additionally, you may also have any further distrobox commands use `pkexec` (for example)
+for rootful containers by appending the line `distrobox_sudo_program="pkexec"`
+(replace `pkexec` with the desired program) to one of the config file paths that
+distrobox supports; for example, to '~/.distroboxrc'.
+
+It is also worth noting that, if your sudo program does not have persistence
+(i.e., cooldown before asking for the root password again after a successful authentication)
+configured, then you may have to enter the root password multiple times, as distrobox
+calls multiple podman/docker commands under the hood. In order to avoid this, it is
+recommended to either configure your sudo program to be persistent, or, if that's
+not feasible, use `sudo` whenever possible (which has persistence enabled by default).
+
+However, if you'd like to have a graphical authentication prompt, but would also like
+to benefit from `sudo`'s persistence (to avoid prompting for a password multiple times in a row),
+you may specify `sudo --askpass` as the sudo program.
+The `--askpass` option makes sudo launch the program in the path (or name, if it is in `$PATH`)
+specified by the `SUDO_ASKPASS` environment variable, and uses its output (to stdout)
+as the password input to authenticate as root. If unsuccessful, it launches the program again,
+until either it outputs the correct password, the user cancels the operation, or
+a limit of amount of authentication attempts is reached.
+
+So, for example, assume you'd like to use `zenity --password` to prompt for the sudo password.
+You may save a script, e.g. `my-password-prompt`, to somewhere in your machine - say,
+to `~/.local/bin/my-password-prompt` - with the following contents:
+
+```sh
+#!/bin/sh
+zenity --password
+```
+
+Make it executable using, for example, `chmod` (in the example, by running `chmod +x ~/.local/bin/my-password-prompt` -
+replace with the path to your script). Afterwards, make sure `SUDO_ASKPASS` is set to your newly-created script's path,
+and also ensure `DBX_SUDO_PROGRAM` is set to `sudo --askpass`, and you should be good to go. For example,
+running the below command should only prompt the root authentication GUI once throughout the whole process:
+
+`SUDO_ASKPASS="$HOME/.local/bin/my-password-prompt" DBX_SUDO_PROGRAM="sudo --askpass" distrobox-ephemeral -r`
+
+You may make these options persist by specifying those environment variables in your shell's rc file (such as `~/.bashrc`).
+Note that this will also work if `distrobox_sudo_program="sudo --askpass"` is specified in one of distrobox's config files
+(such as `~/.distroboxrc`), alongside `export SUDO_ASKPASS="/path/to/password/prompt/program"` (for example - however, this
+last line is usually better suited to your shell's rc file).
+
## Duplicate an existing distrobox
It can be useful to just duplicate an already set up environment, to do this,
diff --git a/extras/install-podman b/extras/install-podman
new file mode 100755
index 0000000..0d2c443
--- /dev/null
+++ b/extras/install-podman
@@ -0,0 +1,158 @@
+#!/bin/sh
+# SPDX-License-Identifier: GPL-3.0-only
+#
+# This file is part of the distrobox project: https://github.com/89luca89/distrobox
+#
+# Copyright (C) 2021 distrobox contributors
+#
+# distrobox is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License version 3
+# as published by the Free Software Foundation.
+#
+# distrobox is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with distrobox; if not, see <http://www.gnu.org/licenses/>.
+
+# POSIX
+
+# Print usage to stdout.
+# Arguments:
+# None
+# Outputs:
+# print usage with examples.
+show_help() {
+ cat << EOF
+install --prefix ~/.local/podman
+
+Options:
+ --prefix/-P: base bath where all files will be deployed (default ~/.local/)
+ --help/-h: show this message
+ --remove/-R: uninstall from prefix
+ -v: show more verbosity
+EOF
+}
+
+# First thing first, chekc if we have all the dependencies.
+printf >&2 "\033[1;31m Checking dependencies...\n\033[0m"
+if [ ! -e /etc/subuid ] || [ ! -e /etc/subgid ]; then
+ if ! command -v newuidmap > /dev/null; then
+ echo "Rootless podman requires the presence of newuidmap and newgidmap, please install package 'uidmap'"
+ echo "with your package manager."
+ exit 1
+ fi
+ echo "Setting up subuid and subgid, needed for rootless podman..."
+ echo "$(whoami):100000:65536" | sudo tee /etc/subuid | sudo tee /etc/subgid
+fi
+
+if [ "$(id -ru)" = 0 ]; then
+ printf "ERROR: rootful install not supported in this mode.\n"
+ exit 2
+fi
+
+verbose=0
+remove=0
+prefix="${HOME}/.local"
+
+# Parse arguments
+while :; do
+ case $1 in
+ -h | --help)
+ # Call a "show_help" function to display a synopsis, then exit.
+ show_help
+ exit
+ ;;
+ -v | --verbose)
+ shift
+ verbose=1
+ ;;
+ -R | --remove)
+ shift
+ remove=1
+ ;;
+ -P | --prefix)
+ if [ -n "$2" ]; then
+ prefix="$2"
+ shift
+ shift
+ fi
+ ;;
+ *) # Default case: If no more options then break out of the loop.
+ break ;;
+ esac
+done
+
+dest_path="${prefix}/podman"
+conf_path="${HOME}/.config/"
+
+set -o errexit
+set -o nounset
+# set verbosity
+if [ "${verbose}" -ne 0 ]; then
+ set -o xtrace
+fi
+
+if [ "${remove}" -ne 0 ]; then
+ printf >&2 "\033[1;31m Resetting...\n\033[0m"
+ "${dest_path}/bin/podman" system reset -f > /dev/null
+ printf >&2 "\033[1;31m Removing...\n\033[0m"
+ rm -r "${dest_path}" "${conf_path}/containers" "${prefix}/bin/podman"
+ printf >&2 "\033[1;31m Done.\n\033[0m"
+ exit $?
+fi
+
+printf >&2 "\033[1;31m Fetching latest podman version...\n\033[0m"
+# Using static podman bulds semplifies our lifes! Thanks to the wonderful project
+# https://github.com/mgoltzsche/podman-static
+# All credits to @mgoltzsche for the builds.
+RELEASE=$(curl -s -L https://github.com/mgoltzsche/podman-static/releases/latest |
+ grep href |
+ grep podman |
+ grep download |
+ grep linux | grep amd64 | sort | tail -n 1 | cut -d'"' -f2)
+printf >&2 "\033[1;31m Found %s, downloading...\n\033[0m" "${RELEASE}"
+
+NAME=$(echo "${RELEASE}" | rev | cut -d'/' -f1 | rev)
+# Download and unpack the tar in /tmp
+curl -L "https://github.com/${RELEASE}" -o "/tmp/${NAME}"
+printf >&2 "\033[1;31m Unpacking...\n\033[0m"
+tar xf /tmp/"${NAME}" -C /tmp/
+
+# Setup the config and local dirs, they are needed to make podman work
+# on this particular setup
+mkdir -p "${conf_path}" "${dest_path}" "${prefix}/bin"
+
+printf >&2 "\033[1;31m Copying in %s...\n\033[0m" "${dest_path}"
+# Copy default config files in there
+cp -r /tmp/podman-linux-amd64/usr/local/bin "${dest_path}"
+cp -r /tmp/podman-linux-amd64/usr/local/lib "${dest_path}"
+cp -r /tmp/podman-linux-amd64/etc/containers "${conf_path}"
+
+printf >&2 "\033[1;31m Configuring...\n\033[0m"
+# We need to tell podman to use those costom directories in order to make
+# it work from custom directories
+echo "conmon_path=[ \"${dest_path}/lib/podman/conmon\" ]
+static_dir = \"${dest_path}/share/podman/libpod\"
+volume_path = \"${dest_path}//share/podman/volume\"
+" >> "${conf_path}/containers/containers.conf"
+
+# Same for mouning programs
+sed -i "s|/var|${dest_path}|g" "${conf_path}/containers/storage.conf"
+sed -i "s|mount_program =.*|mount_program = \"${dest_path}/bin/fuse-overlayfs\"|g" \
+ "${conf_path}/containers/storage.conf"
+
+printf >&2 "\033[1;31m Cleaning up...\n\033[0m"
+# Cleanup
+rm -f /tmp/"${NAME}"
+rm -rf /tmp/podman-linux-amd64/
+
+printf >&2 "\033[1;31m Migrating...\n\033[0m"
+
+"${dest_path}/bin/podman" system migrate
+ln -sf "${dest_path}/bin/podman" "${prefix}/bin/podman"
+
+printf >&2 "Successfully installed to %s.\n" "${dest_path}"
+printf >&2 "Be sure that %s is in your \$PATH environment variable for it to work.\n" "${dest_path}"
diff --git a/install b/install
index 14b027e..9c944c0 100755
--- a/install
+++ b/install
@@ -33,7 +33,7 @@ install --prefix /usr/local
Options:
--prefix/-P: base bath where all files will be deployed (default /usr/local if root, ~/.local if not)
- --path/-p: (DEPRECATED) path where to deploy the files (default /usr/local/bin if root, ~/.local/bin if not)
+ --next/-N: install latest development version from git, instead of the latest stable release.
--help/-h: show this message
-v: show more verbosity
EOF
@@ -51,13 +51,6 @@ while :; do
shift
verbose=1
;;
- -p | --path)
- if [ -n "$2" ]; then
- dest_path="$2"
- shift
- shift
- fi
- ;;
-N | --next)
if [ -n "$2" ]; then
shift
@@ -76,26 +69,16 @@ while :; do
esac
done
-if [ -n "${dest_path}" ] && [ -n "${prefix}" ]; then
- printf >&2 "Both -p and -P are set. Cannot continue. Exiting.\n"
- exit 1
-fi
-
-if [ -z "${dest_path}" ]; then
- if [ -z "${prefix}" ]; then
- prefix="/usr/local"
- # in case we're not root, just default to the home directory
- if [ "$(id -u)" -ne 0 ]; then
- prefix="${HOME}/.local"
- fi
+if [ -z "${prefix}" ]; then
+ prefix="/usr/local"
+ # in case we're not root, just default to the home directory
+ if [ "$(id -u)" -ne 0 ]; then
+ prefix="${HOME}/.local"
fi
- dest_path="${prefix}/bin"
- man_dest_path="${prefix}/share/man/man1"
-else
- printf >&2 "Warning: -p/--path is deprecated. Please refer to the documentation and switch to -P/--prefix.\n"
- # dest_path is already set
- man_dest_path="${dest_path}/../share/man/man1"
fi
+dest_path="${prefix}/bin"
+man_dest_path="${prefix}/share/man/man1"
+icon_dest_path="${prefix}/share/icons"
set -o errexit
set -o nounset
@@ -122,17 +105,29 @@ if [ -e "${curr_dir}/distrobox-enter" ]; then
install -D -m 0644 -t "${man_dest_path}" "${file}"
done
fi
+ if [ -e terminal-distrobox-icon.png ]; then
+ install -D -m 0644 -t "${icon_dest_path}" terminal-distrobox-icon.png
+ fi
else
+ printf >&2 "\033[1;31m Checking dependencies...\n\033[0m"
# check that we have base dependencies
- if ! command -v curl || ! command -v tar; then
- printf >&2 "Online install depends on curl and tar\n"
+ if ! { command -v curl > /dev/null || command -v wget > /dev/null; } || ! command -v tar > /dev/null; then
+ printf >&2 "Online install depends on tar and either curl or wget\n"
+ printf >&2 "Ensure you have all dependencies installed.\n"
exit 1
fi
+ if command -v curl > /dev/null 2>&1; then
+ download="curl -sLo"
+ elif command -v wget > /dev/null 2>&1; then
+ download="wget -qO"
+ fi
+
+ printf >&2 "\033[1;31m Downloading...\n\033[0m"
if [ "${next}" -eq 0 ]; then
- release_ver=$(curl -L https://github.com/89luca89/distrobox/releases/latest |
+ release_ver=$(${download} - https://github.com/89luca89/distrobox/releases/latest |
grep 'refs/tags' | tail -1 | cut -d'"' -f2)
- release_name=$(echo "${release_ver}" | rev | cut -d'/' -f1 | rev)
+ release_name=$(echo "${release_ver}" | grep -Eo '[0-9]+\.[0-9]+\.[0-9]+\.tar\.gz$')
else
release_ver="89luca89/distrobox/archive/refs/heads/main.tar.gz"
release_name="main"
@@ -141,9 +136,14 @@ else
tmp_dir="$(mktemp -d)"
cd "${tmp_dir}"
# download our target
- curl -L "https://github.com/${release_ver}" -o "${release_name}"
+ ${download} "${release_name}" "https://github.com/${release_ver}"
# uncompress
- tar xvf "${release_name}"
+ printf >&2 "\033[1;31m Unpacking...\n\033[0m"
+ if [ "${verbose}" -ne 0 ]; then
+ tar xvf "${release_name}"
+ else
+ tar xf "${release_name}"
+ fi
# deploy our files
for file in "distrobox-$(echo "${release_name}" | sed 's/.tar.gz//g')"/distrobox*; do
if ! install -D -m 0755 -t "${dest_path}" "${file}"; then
@@ -152,10 +152,14 @@ else
fi
done
if [ -e "distrobox-$(echo "${release_name}" | sed 's/.tar.gz//g')/man/" ]; then
- for file in "distrobox-$(echo "${release_name}" | sed 's/.tar.gz//g')"/man/*; do
+ for file in "distrobox-$(echo "${release_name}" | sed 's/.tar.gz//g')"/man/man1/*; do
install -D -m 0644 -t "${man_dest_path}" "${file}"
done
fi
+ if [ -e "distrobox-$(echo "${release_name}" | sed 's/.tar.gz//g')"/terminal-distrobox-icon.png ]; then
+ install -D -m 0644 -t "${icon_dest_path}" \
+ "distrobox-$(echo "${release_name}" | sed 's/.tar.gz//g')"/terminal-distrobox-icon.png
+ fi
# securely delete unneeded files
cd
@@ -164,5 +168,8 @@ else
fi
fi
-printf >&2 "Successfully installed to %s.\n" "${dest_path}"
-printf >&2 "Be sure that %s is in your \$PATH environment variable for it to work.\n" "${dest_path}"
+[ ! -w "${dest_path}" ] && printf >&2 "Cannot write into %s, permission denied.\n" "${dest_path}" && exit 1
+[ ! -w "${man_dest_path}" ] && printf >&2 "Cannot write into %s, permission denied.\n" "${man_dest_path}" && exit 1
+
+printf >&2 "\033[1;31m Successfully installed to %s.\n\033[0m" "${dest_path}"
+printf >&2 "\033[1;31m Be sure that %s is in your \$PATH environment variable for it to work.\n\033[0m" "${dest_path}"
diff --git a/man/gen-man b/man/gen-man
index 749cb4e..3a34724 100755
--- a/man/gen-man
+++ b/man/gen-man
@@ -29,6 +29,7 @@ END="$(grep -n -B1 "# Containers Distros" "$(dirname "${0}")/../docs/compatibili
sed -e "${START},${END}d" "$(dirname "${0}")/../docs/compatibility.md" > "${compatibility_file}"
sed -e "1,${HEAD}d" -i "${compatibility_file}"
+sed -i "s/^#.*/\U&/g" "${compatibility_file}"
pandoc --standalone \
--metadata title="DISTROBOX" \
diff --git a/man/man1/distrobox-compatibility.1 b/man/man1/distrobox-compatibility.1
index be70aca..94e522b 100644
--- a/man/man1/distrobox-compatibility.1
+++ b/man/man1/distrobox-compatibility.1
@@ -15,30 +15,33 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Compatibility
+.SH COMPATIBILITY
.PP
This project \f[B]does not need a dedicated image\f[R].
It can use any OCI images from docker-hub, quay.io, or any registry of
your choice.
.PP
-Granted, they may not be as featureful as expected (some of them do not
-even have \f[V]which\f[R], \f[V]mount\f[R], \f[V]less\f[R] or
-\f[V]vi\f[R]) but that\[cq]s all doable in the container itself after
-bootstrapping it.
+Many cloud images are stripped down on purpose to save size and may not
+include commands such as \f[V]which\f[R], \f[V]mount\f[R],
+\f[V]less\f[R] or \f[V]vi\f[R]).
+Additional packages can be installed once inside the container.
+We recommend using your preferred automation tool inside the container
+if you find yourself having to repeatedly create new containers.
+Maintaining your own custom image is also an option.
.PP
The main concern is having basic Linux utilities (\f[V]mount\f[R]),
basic user management utilities (\f[V]usermod, passwd\f[R]), and
\f[V]sudo\f[R] correctly set.
-.SS Supported container managers
+.SS SUPPORTED CONTAINER MANAGERS
.PP
\f[V]distrobox\f[R] can run on either \f[V]podman\f[R] or
\f[V]docker\f[R]
.PP
It depends either on \f[V]podman\f[R] configured in
\f[V]rootless mode\f[R] or on \f[V]docker\f[R] configured without sudo
-(follow THIS
+(follow THESE
instructions (https://docs.docker.com/engine/install/linux-postinstall/))
.IP \[bu] 2
Minimum podman version: \f[B]2.1.0\f[R]
@@ -52,7 +55,7 @@ Follow the official installation guide here:
<https://docs.docker.com/engine/install>
.IP \[bu] 2
<https://docs.docker.com/engine/install/linux-postinstall/>
-.SS Containers Distros
+.SS CONTAINERS DISTROS
.PP
Distrobox guests tested successfully with the following container
images:
@@ -69,40 +72,36 @@ Images
T}
_
T{
-AlmaLinux
-T}@T{
-8 8-minimal 9 9-minimal
-T}@T{
-docker.io/library/almalinux:8 docker.io/library/almalinux:9
-docker.io/library/almalinux:9-minimal
-T}
-T{
AlmaLinux (UBI)
T}@T{
8
T}@T{
-docker.io/almalinux/8-base docker.io/almalinux/8-init
+quay.io/almalinux/8-base:8 quay.io/almalinux/8-init:8
T}
T{
-Alpine Linux
+AlmaLinux
T}@T{
-3.14 3.15
+8 8-minimal 9 9-minimal
T}@T{
-docker.io/library/alpine:latest
+quay.io/almalinux/almalinux:8 quay.io/almalinux/almalinux:9
+quay.io/almalinux/almalinux:9-minimal
T}
T{
-AmazonLinux
+Alpine Linux
T}@T{
-2
+3.15 3.16
T}@T{
-docker.io/library/amazonlinux:2.0.20211005.0
+docker.io/library/alpine:3.15 docker.io/library/alpine:3.16
+docker.io/library/alpine:latest
T}
T{
AmazonLinux
T}@T{
-2022
+1 2 2022
T}@T{
-public.ecr.aws/amazonlinux/amazonlinux:2022
+public.ecr.aws/amazonlinux/amazonlinux:1
+public.ecr.aws/amazonlinux/amazonlinux:2
+public.ecr.aws/amazonlinux/amazonlinux:2022.0.20220531.0
T}
T{
Archlinux
@@ -111,10 +110,11 @@ T}@T{
docker.io/library/archlinux:latest
T}
T{
-ClearLinux
+CentOS Stream
T}@T{
+8 9
T}@T{
-docker.io/library/clearlinux:latest docker.io/library/clearlinux:base
+quay.io/centos/centos:stream8 quay.io/centos/centos:stream9
T}
T{
CentOS
@@ -124,26 +124,10 @@ T}@T{
quay.io/centos/centos:7
T}
T{
-CentOS Stream
-T}@T{
-8 9
-T}@T{
-quay.io/centos/centos:stream8 quay.io/centos/centos:stream9
-T}
-T{
-RedHat (UBI)
+ClearLinux
T}@T{
-7 8 9
T}@T{
-registry.access.redhat.com/ubi7/ubi
-registry.access.redhat.com/ubi7/ubi-init
-registry.access.redhat.com/ubi7/ubi-minimal
-registry.access.redhat.com/ubi8/ubi
-registry.access.redhat.com/ubi8/ubi-init
-registry.access.redhat.com/ubi8/ubi-minimal
-registry.access.redhat.com/ubi9/ubi
-registry.access.redhat.com/ubi9/ubi-init
-registry.access.redhat.com/ubi9/ubi-minimal
+docker.io/library/clearlinux:latest docker.io/library/clearlinux:base
T}
T{
Debian
@@ -171,21 +155,27 @@ T}@T{
docker.io/library/debian:unstable
T}
T{
-Neurodebian
+Fedora
T}@T{
-nd100
+35 36 37 Rawhide
T}@T{
-docker.io/library/neurodebian:nd100
+registry.fedoraproject.org/fedora-toolbox:35 quay.io/fedora/fedora:35
+quay.io/fedora/fedora:36 registry.fedoraproject.org/fedora:37
+quay.io/fedora/fedora:rawhide
T}
T{
-Fedora
+Gentoo Linux
+T}@T{
+rolling
+T}@T{
+You will have to Build your own to have a complete Gentoo docker image
+T}
+T{
+Kali Linux
T}@T{
-34 35 36 37 Rawhide
+rolling
T}@T{
-registry.fedoraproject.org/fedora-toolbox:34 docker.io/library/fedora:34
-registry.fedoraproject.org/fedora-toolbox:35 docker.io/library/fedora:35
-docker.io/library/fedora:36 registry.fedoraproject.org/fedora:37
-docker.io/library/fedora:rawhide
+docker.io/kalilinux/kali-rolling:latest
T}
T{
Mageia
@@ -195,6 +185,13 @@ T}@T{
docker.io/library/mageia
T}
T{
+Neurodebian
+T}@T{
+nd100
+T}@T{
+docker.io/library/neurodebian:nd100
+T}
+T{
Opensuse
T}@T{
Leap
@@ -212,17 +209,37 @@ T}
T{
Oracle Linux
T}@T{
-7 8
+7 7-slim 8 8-slim 9 9-slim
T}@T{
container-registry.oracle.com/os/oraclelinux:7
+container-registry.oracle.com/os/oraclelinux:7-slim
container-registry.oracle.com/os/oraclelinux:8
+container-registry.oracle.com/os/oraclelinux:8-slim
+container-registry.oracle.com/os/oraclelinux:9
+container-registry.oracle.com/os/oraclelinux:9-slim
+T}
+T{
+RedHat (UBI)
+T}@T{
+7 8 9
+T}@T{
+registry.access.redhat.com/ubi7/ubi
+registry.access.redhat.com/ubi7/ubi-init
+registry.access.redhat.com/ubi7/ubi-minimal
+registry.access.redhat.com/ubi8/ubi
+registry.access.redhat.com/ubi8/ubi-init
+registry.access.redhat.com/ubi8/ubi-minimal
+registry.access.redhat.com/ubi9/ubi
+registry.access.redhat.com/ubi9/ubi-init
+registry.access.redhat.com/ubi9/ubi-minimal
T}
T{
Rocky Linux
T}@T{
-8
+8 8-minimal
T}@T{
-docker.io/rockylinux/rockylinux:8
+quay.io/rockylinux/rockylinux:8 quay.io/rockylinux/rockylinux:8-minimal
+quay.io/rockylinux/rockylinux:latest
T}
T{
Scientific Linux
@@ -241,18 +258,11 @@ T}
T{
Ubuntu
T}@T{
-14.04 16.04 18.04 20.04 21.10 22.04
+14.04 16.04 18.04 20.04 22.04
T}@T{
docker.io/library/ubuntu:14.04 docker.io/library/ubuntu:16.04
docker.io/library/ubuntu:18.04 docker.io/library/ubuntu:20.04
-docker.io/library/ubuntu:21.10 docker.io/library/ubuntu:22.04
-T}
-T{
-Kali Linux
-T}@T{
-rolling
-T}@T{
-docker.io/kalilinux/kali-rolling:latest
+docker.io/library/ubuntu:22.04
T}
T{
Void Linux
@@ -261,13 +271,6 @@ T}@T{
ghcr.io/void-linux/void-linux:latest-full-x86_64
ghcr.io/void-linux/void-linux:latest-full-x86_64-musl
T}
-T{
-Gentoo Linux
-T}@T{
-rolling
-T}@T{
-You will have to Build your own to have a complete Gentoo docker image
-T}
.TE
.PP
Note however that if you use a non-toolbox preconfigured image (e.g.
@@ -284,7 +287,7 @@ plans to bring support to it.
If you are looking for unprivlaged NixOS environments, we suggest you
look into
nix-shell (https://nixos.org/manual/nix/unstable/command-ref/nix-shell.html).
-.SS New Distro support
+.SS NEW DISTRO SUPPORT
.PP
If your distro of choice is not on the list, open an issue requesting
support for it, we can work together to check if it is possible to add
@@ -292,7 +295,7 @@ support for it.
.PP
Or just try using it anyway, if it works, open an issue and it will be
added to the list!
-.SS Older distributions
+.SS OLDER DISTRIBUTIONS
.PP
For older distributions like CentOS 5, CentOS 6, Debian 6, Ubuntu 12.04,
compatibility is not assured.
diff --git a/man/man1/distrobox-create.1 b/man/man1/distrobox-create.1
index 956d8a7..86c1596 100644
--- a/man/man1/distrobox-create.1
+++ b/man/man1/distrobox-create.1
@@ -14,17 +14,63 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-CREATE" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-CREATE" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Create the distrobox
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox create
+distrobox-create
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-create takes care of creating the container with input name
and image.
The created container will be tightly integrated with the host, allowing
sharing of the HOME directory of the user, external storage, external
usb devices and graphical apps (X11/Wayland), and audio.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox create\f[R]
+.IP
+.nf
+\f[C]
+--image/-i: image to use for the container default: registry.fedoraproject.org/fedora-toolbox:36
+--name/-n: name for the distrobox default: my-distrobox
+--pull/-p: pull latest image unconditionally without asking
+--yes/-Y: non-interactive, pull images without asking
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--clone/-c: name of the distrobox container to use as base for a new container
+ this will be useful to either rename an existing distrobox or have multiple copies
+ of the same environment.
+--home/-H select a custom HOME directory for the container. Useful to avoid host\[aq]s home littering with temp files.
+--volume additional volumes to add to the container
+--additional-flags/-a: additional flags to pass to the container manager command
+--init-hooks additional commands to execute during container initialization
+--pre-init-hooks additional commands to execute prior to container initialization
+--init/-I use init system (like systemd) inside the container.
+ this will make host\[aq]s processes not visible from within the container.
+--help/-h: show this message
+--dry-run/-d: only print the container manager command generated
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH COMPATIBILITY
+.IP
+.nf
+\f[C]
+for a list of compatible images and container managers, please consult the man page:
+ man distrobox
+ man distrobox-compatibility
+or consult the documentation page on: https://github.com/89luca89/distrobox/blob/main/docs/compatibility.md#containers-distros
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -58,44 +104,7 @@ DBX_CONTAINER_IMAGE
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
-\f[R]
-.fi
-.PP
-Options:
-.IP
-.nf
-\f[C]
---image/-i: image to use for the container default: registry.fedoraproject.org/fedora-toolbox:36
---name/-n: name for the distrobox default: my-distrobox
---pull/-p: pull latest image unconditionally without asking
---yes/-Y: non-interactive, pull images without asking
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---clone/-c: name of the distrobox container to use as base for a new container
- this will be useful to either rename an existing distrobox or have multiple copies
- of the same environment.
---home/-H select a custom HOME directory for the container. Useful to avoid host\[aq]s home littering with temp files.
---volume additional volumes to add to the container
---additional-flags/-a: additional flags to pass to the container manager command
---init-hooks additional commands to execute during container initialization
---pre-init-hooks additional commands to execute prior to container initialization
---init/-I use init system (like systemd) inside the container.
- this will make host\[aq]s processes not visible from within the container.
---help/-h: show this message
---dry-run/-d: only print the container manager command generated
---verbose/-v: show more verbosity
---version/-V: show version
-\f[R]
-.fi
-.PP
-Compatibility:
-.IP
-.nf
-\f[C]
-for a list of compatible images and container managers, please consult the man page:
- man distrobox
- man distrobox-compatibility
-or consult the documentation page on: https://github.com/89luca89/distrobox/blob/main/docs/compatibility.md#containers-distros
+DBX_SUDO_PROGRAM
\f[R]
.fi
.PP
@@ -181,3 +190,6 @@ integration\f[R].
From within the container you will not be able to see and manage
host\[cq]s processes.
This is needed because \f[V]/sbin/init\f[R] must be pid 1.
+.PP
+From version 1.4.0 of distrobox, when you create a new container, it
+will also generate an entry in the applications list.
diff --git a/man/man1/distrobox-enter.1 b/man/man1/distrobox-enter.1
index 70ac564..d6763a1 100644
--- a/man/man1/distrobox-enter.1
+++ b/man/man1/distrobox-enter.1
@@ -14,9 +14,17 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-ENTER" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-ENTER" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Enter the distrobox
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox enter
+distrobox-enter
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-enter takes care of entering the container with the name
specified.
@@ -24,8 +32,27 @@ Default command executed is your SHELL, but you can specify different
shells or entire commands to execute.
If using it inside a script, an application, or a service, you can
specify the \[en]headless mode to disable tty and interactivity.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox enter\f[R]
+.IP
+.nf
+\f[C]
+--name/-n: name for the distrobox default: my-distrobox
+--/-e: end arguments execute the rest as command to execute at login default: bash -l
+--no-tty/-T: do not instantiate a tty
+--no-workdir/-nw: always start the container from container\[aq]s home directory
+--additional-flags/-a: additional flags to pass to the container manager command
+--help/-h: show this message
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--dry-run/-d: only print the container manager command generated
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -53,24 +80,7 @@ Supported environment variables:
DBX_CONTAINER_NAME
DBX_CONTAINER_MANAGER
DBX_SKIP_WORKDIR
-\f[R]
-.fi
-.PP
-Options:
-.IP
-.nf
-\f[C]
---name/-n: name for the distrobox default: my-distrobox
---/-e: end arguments execute the rest as command to execute at login default: bash -l
---no-tty/-T: do not instantiate a tty
---no-workdir/-nw: always start the container from container\[aq]s home directory
---additional-flags/-a: additional flags to pass to the container manager command
---help/-h: show this message
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---dry-run/-d: only print the container manager command generated
---verbose/-v: show more verbosity
---version/-V: show version
+DBX_SUDO_PROGRAM
\f[R]
.fi
.PP
@@ -97,3 +107,20 @@ my_var=test distrobox enter -n dev-arch --additional-flags -- printenv &| grep m
my_var=test
\f[R]
.fi
+.PP
+If you\[cq]d like to enter a rootful container having distrobox use a
+program other than `sudo' to run podman/docker as root, such as `pkexec'
+or `doas', you may specify it with the \f[V]DBX_SUDO_PROGRAM\f[R]
+environment variable.
+For example, to use `doas' to enter a rootful container:
+.IP
+.nf
+\f[C]
+DBX_SUDO_PROGRAM=\[dq]doas\[dq] distrobox enter -n container --root
+\f[R]
+.fi
+.PP
+Additionally, in one of the config file paths that distrobox supports,
+such as \f[V]\[ti]/.distroboxrc\f[R], you can also append the line
+\f[V]distrobox_sudo_program=\[dq]doas\[dq]\f[R] (for example) to always
+run distrobox commands involving rootful containers using `doas'.
diff --git a/man/man1/distrobox-ephemeral.1 b/man/man1/distrobox-ephemeral.1
new file mode 100644
index 0000000..dd79d04
--- /dev/null
+++ b/man/man1/distrobox-ephemeral.1
@@ -0,0 +1,81 @@
+.\
+.\"
+.\" Define V font for inline verbatim, using C font in formats
+.\" that render this, and otherwise B font.
+.ie "\f[CB]x\f[]"x" \{\
+. ftr V B
+. ftr VI BI
+. ftr VB B
+. ftr VBI BI
+.\}
+.el \{\
+. ftr V CR
+. ftr VI CI
+. ftr VB CB
+. ftr VBI CBI
+.\}
+.TH "DISTROBOX-EPHEMERAL" "1" "Sep 2022" "Distrobox" "User Manual"
+.hy
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox ephemeral
+distrobox-ephemeral
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+distrobox-ephemeral creates a temporary distrobox that is automatically
+destroyed when the command is terminated.
+.SH SYNOPSIS
+.PP
+\f[B]distrobox ephemeral\f[R]
+.IP
+.nf
+\f[C]
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--verbose/-v: show more verbosity
+--help/-h: show this message
+--/-e: end arguments execute the rest as command to execute at login default: bash -l
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-ephemeral --image alpine:latest -- cat /etc/os-release
+distrobox-ephemeral --root --verbose --image alpine:latest --volume /opt:/opt
+\f[R]
+.fi
+.PP
+You can also use flags from \f[B]distrobox-create\f[R] to customize the
+ephemeral container to run.
+.PP
+Refer to
+.IP
+.nf
+\f[C]
+man distrobox-create
+\f[R]
+.fi
+.PP
+or
+.IP
+.nf
+\f[C]
+distrobox-create --help
+\f[R]
+.fi
+.PP
+Supported environment variables:
+.IP
+.nf
+\f[C]
+distrobox-ephemeral calls distrobox-create, SEE ALSO distrobox-create(1) for
+a list of supported environment variables to use.
+\f[R]
+.fi
diff --git a/man/man1/distrobox-export.1 b/man/man1/distrobox-export.1
index a0cfeb2..51bd291 100644
--- a/man/man1/distrobox-export.1
+++ b/man/man1/distrobox-export.1
@@ -14,15 +14,86 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-EXPORT" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-EXPORT" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Application and service exporting
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-export
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+\f[B]Application and service exporting\f[R]
.PP
distrobox-export takes care of exporting an app a binary or a service
from the container to the host.
.PP
The exported app will be easily available in your normal launcher and it
will automatically be launched from the container it is exported from.
+.SH SYNOPSIS
+.PP
+\f[B]distrobox-export\f[R]
+.IP
+.nf
+\f[C]
+--app/-a: name of the application to export
+--bin/-b: absolute path of the binary to export
+--service/-s: name of the service to export
+--delete/-d: delete exported application or service
+--export-label/-el: label to add to exported application name.
+ Defaults to (on \[rs]$container_name)
+--export-path/-ep: path where to export the binary
+--extra-flags/-ef: extra flags to add to the command
+--sudo/-S: specify if the exported item should be run as sudo
+--help/-h: show this message
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.PP
+You may want to install graphical applications or user services in your
+distrobox.
+Using \f[V]distrobox-export\f[R] from \f[B]inside\f[R] the container
+will let you use them from the host itself.
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-export --app mpv [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+distrobox-export --service syncthing [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+distrobox-export --bin /path/to/bin --export-path \[ti]/.local/bin [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+\f[R]
+.fi
+.PP
+\f[B]App export example\f[R]
+.IP
+.nf
+\f[C]
+distrobox-export --app abiword
+\f[R]
+.fi
+.PP
+This tool will simply copy the original \f[V].desktop\f[R] files along
+with needed icons, add the prefix
+\f[V]/usr/local/bin/distrobox-enter -n distrobox_name -e ...\f[R] to the
+commands to run, and save them in your home to be used directly from the
+host as a normal app.
+.PP
+\f[B]Service export example\f[R]
+.IP
+.nf
+\f[C]
+distrobox-export --service syncthing --extra-flags \[dq]--allow-newer-config\[dq]
+distrobox-export --service nginx --sudo
+\f[R]
+.fi
+.PP
+For services, it will similarly export the systemd unit inside the
+container to a \f[V]systemctl --user\f[R] service, prefixing the various
+\f[V]ExecStart ExecStartPre ExecStartPost ExecReload ExecStop ExecStopPost\f[R]
+with the \f[V]distrobox-enter\f[R] command prefix.
.PP
The exported services will be available in the host\[cq]s user\[cq]s
systemd session, so
@@ -35,12 +106,29 @@ systemctl --user status exported_service_name
.PP
will show the status of the service exported.
.PP
+\f[B]Binary export example\f[R]
+.IP
+.nf
+\f[C]
+distrobox-export --bin /usr/bin/code --extra-flags \[dq]--foreground\[dq] --export-path $HOME/.local/bin
+\f[R]
+.fi
+.PP
+In the case of exporting binaries, you will have to specify
+\f[B]where\f[R] to export it (\f[V]--export-path\f[R]) and the tool will
+create a little wrapper script that will \f[V]distrobox-enter -e\f[R]
+from the host, the desired binary.
+This can be handy with the use of \f[V]direnv\f[R] to have different
+versions of the same binary based on your \f[V]env\f[R] or project.
+.PP
The exported binaries will be exported in the \[lq]\[en]export-path\[rq]
of choice as a wrapper script that acts naturally both on the host and
in the container.
Note that \[lq]\[en]export-path\[rq] is NOT OPTIONAL, you have to
explicitly set it.
.PP
+\f[B]Additional flags\f[R]
+.PP
You can specify additional flags to add to the command, for example if
you want to export an electron app, you could add the
\[lq]\[en]foreground\[rq] flag to the command:
@@ -58,6 +146,8 @@ Extra flags are only used then the exported app, binary, or service is
used from the host, using them inside the container will not include
them.
.PP
+\f[B]Unexport\f[R]
+.PP
The option \[lq]\[en]delete\[rq] will un-export an app, binary, or
service.
.IP
@@ -70,94 +160,90 @@ distrobox-export --service nginx --delete
\f[R]
.fi
.PP
+\f[B]Run as root in the container\f[R]
+.PP
The option \[lq]\[en]sudo\[rq] will launch the exported item as root
inside the distrobox.
.PP
-Note you can use \[en]app OR \[en]bin OR \[en]service but not together.
-.IP
-.nf
-\f[C]
-distrobox-export --service nginx --sudo
-\f[R]
-.fi
-.PP
-Usage:
+\f[B]Exporting apps from rootful containers\f[R]
+.PP
+It is worth noting that, when exporting any item - which includes
+graphical apps - from rootful containers (created with
+\f[V]distrobox create --root\f[R]), root privileges will be needed every
+time the item is launched (in order to enter the rootful container),
+which, by default, is done using \f[V]sudo\f[R] (see docs for
+\f[V]distrobox-enter\f[R] on how to customize that).
+However, for graphical apps in specific, since they launch without a
+terminal, the usage of \f[V]sudo\f[R] might, at first, make it
+impossible to launch them.
+.PP
+To fix this without needing to customize the sudo program, one can
+define a global \f[V]SUDO_ASKPASS\f[R] environment variable on their
+machine, which is a PATH to an executable that is run by \f[V]sudo\f[R]
+when no terminal is available (or when it is given the
+\f[V]--askpass\f[R] or \f[V]-A\f[R] option), and the output of that
+executable to stdout is used as the password input.
+The executable is called as many times is needed for authentication as
+root to succeed (unless a limit of amount of attempts is reached).
+.PP
+To do this, pick a program to ask the user for graphical password input.
+In this example, we will use \f[V]zenity --password\f[R], which should
+be present for GNOME users (and can also be installed in other DEs) -
+there are other options, such as
+\f[V]kdialog --password \[dq]Message\[dq]\f[R] for KDE users.
+.PP
+Write the call to the desired program to a script file, for example to
+\f[V]/usr/bin/my-password-prompt\f[R] (sample contents below):
.IP
.nf
\f[C]
-distrobox-export --app mpv [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
-distrobox-export --service syncthing [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
-distrobox-export --bin /path/to/bin --export-path \[ti]/.local/bin [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+#!/bin/sh
+zenity --password \[dq]Authentication as root is required\[dq]
\f[R]
.fi
.PP
-Options:
+(You may save the script under, for example, \f[V]\[ti]/.local/bin\f[R]
+if you want to keep it fully local to your user.)
+.PP
+Afterwards, make it executable (e.g.\ run
+\f[V]sudo chmod +x /usr/bin/my-password-prompt\f[R]).
+Then, make sure to set \f[V]SUDO_ASKPASS\f[R] to
+\f[V]\[dq]/usr/bin/my-password-prompt\[dq]\f[R] (replace with your
+script\[cq]s path) in a global profile file, so that it is picked up by
+sudo when running graphical apps (and, therefore, sudo will run the
+script you created to ask for a password).
+This is done with the shell line
+\f[V]export SUDO_ASKPASS=\[dq]/path/to/script/goes/here\[dq]\f[R].
+You can do this for your user only by running the command below (replace
+the script path as needed):
.IP
.nf
\f[C]
---app/-a: name of the application to export
---bin/-b: absolute path of the binary to export
---service/-s: name of the service to export
---delete/-d: delete exported application or service
---export-label/-el: label to add to exported application name.
- Defaults to (on \[rs]$container_name)
---export-path/-ep: path where to export the binary
---extra-flags/-ef: extra flags to add to the command
---sudo/-S: specify if the exported item should be ran as sudo
---help/-h: show this message
---verbose/-v: show more verbosity
---version/-V: show version
+echo \[aq]export SUDO_ASKPASS=\[dq]/usr/bin/my-password-prompt\[dq]\[aq] >> \[ti]/.profile
\f[R]
.fi
.PP
-You may want to install graphical applications or user services in your
-distrobox.
-Using \f[V]distrobox-export\f[R] from \f[B]inside\f[R] the container
-will let you use them from the host itself.
+Which appends the appropriate line to the end of your
+\f[V]\[ti]/.profile\f[R] file, thus making the change local to your
+user.
+Alternatively, to set it system-wide (for all users), you may create a
+file in \f[V]/etc/profile.d/\f[R] (or equivalent for your system) with
+that line.
.PP
-App export example:
-.IP
-.nf
-\f[C]
-distrobox-export --app abiword
-\f[R]
-.fi
+Now just log out and log back in, and graphical apps exported from
+rootful containers should now be properly asking for root\[cq]s password
+before launching (instead of not opening, if that was the case before).
.PP
-This tool will simply copy the original \f[V].desktop\f[R] files along
-with needed icons, add the prefix
-\f[V]/usr/local/bin/distrobox-enter -n distrobox_name -e ...\f[R] to the
-commands to run, and save them in your home to be used directly from the
-host as a normal app.
+\f[B]Notes\f[R]
.PP
-Service export example:
+Note you can use \[en]app OR \[en]bin OR \[en]service but not together.
.IP
.nf
\f[C]
-distrobox-export --service syncthing --extra-flags \[dq]--allow-newer-config\[dq]
distrobox-export --service nginx --sudo
\f[R]
.fi
.PP
-For services, it will similarly export the systemd unit inside the
-container to a \f[V]systemctl --user\f[R] service, prefixing the various
-\f[V]ExecStart ExecStartPre ExecStartPost ExecReload ExecStop ExecStopPost\f[R]
-with the \f[V]distrobox-enter\f[R] command prefix.
-.PP
-Binary export example:
-.IP
-.nf
-\f[C]
-distrobox-export --bin /usr/bin/code --extra-flags \[dq]--foreground\[dq] --export-path $HOME/.local/bin
-\f[R]
-.fi
-.PP
-In the case of exporting binaries, you will have to specify
-\f[B]where\f[R] to export it (\f[V]--export-path\f[R]) and the tool will
-create a little wrapper script that will \f[V]distrobox-enter -e\f[R]
-from the host, the desired binary.
-This can be handy with the use of \f[V]direnv\f[R] to have different
-versions of the same binary based on your \f[V]env\f[R] or project.
-.PP
[IMAGE: app-export (https://user-images.githubusercontent.com/598882/144294795-c7785620-bf68-4d1b-b251-1e1f0a32a08d.png)]
.PP
[IMAGE: service-export (https://user-images.githubusercontent.com/598882/144294314-29a8921f-4511-453d-bf8e-d0d1e336db91.png)]
diff --git a/man/man1/distrobox-generate-entry.1 b/man/man1/distrobox-generate-entry.1
new file mode 100644
index 0000000..eb7ac2d
--- /dev/null
+++ b/man/man1/distrobox-generate-entry.1
@@ -0,0 +1,51 @@
+.\
+.\"
+.\" Define V font for inline verbatim, using C font in formats
+.\" that render this, and otherwise B font.
+.ie "\f[CB]x\f[]"x" \{\
+. ftr V B
+. ftr VI BI
+. ftr VB B
+. ftr VBI BI
+.\}
+.el \{\
+. ftr V CR
+. ftr VI CI
+. ftr VB CB
+. ftr VBI CBI
+.\}
+.TH "DISTROBOX-GENERATE-ENTRY" "1" "Sep 2022" "Distrobox" "User Manual"
+.hy
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox generate-entry
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+distrobox-generate-entry will create a desktop icon for one of the
+available distroboxes.
+This will be then deleted when you remove the matching distrobox.
+.SH SYNOPSIS
+.PP
+\f[B]distrobox generate-entry\f[R]
+.IP
+.nf
+\f[C]
+ --help/-h: show this message
+ --all/-a: perform for all distroboxes
+ --delete/-d: delete the entry
+ --icon/-i: specify a custom icon [/path/to/icon] (default auto)
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-generate-entry container-name [--delete] [--icon [auto,/path/to/icon]]
+\f[R]
+.fi
diff --git a/man/man1/distrobox-host-exec.1 b/man/man1/distrobox-host-exec.1
index 1fb327e..44e017a 100644
--- a/man/man1/distrobox-host-exec.1
+++ b/man/man1/distrobox-host-exec.1
@@ -14,18 +14,24 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-HOST-EXEC" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-HOST-EXEC" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Host Command Execution
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-host-exec
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-host-exec lets one execute command on the host, while inside
of a container.
.PP
-If \[lq]flatpak-spawn\[rq] is installed in the container, this is what
-is used, and it is the most powerful and recommended method.
-If, instead, \[lq]flatpak-spawn\[rq] can\[cq]t be found, it still try to
-get the job done with \[lq]chroot\[rq] (but beware that not all
-commands/programs will work well in this mode).
+Under the hood, distrobox-host-exec uses \f[V]host-spawn\f[R] a project
+that let\[cq]s us execute commands back on the host.
+If the tool is not found the user will be prompted to install it.
+.SH SYNOPSIS
.PP
Just pass to \[lq]distrobox-host-exec\[rq] any command and all its
arguments, if any.
@@ -33,28 +39,34 @@ arguments, if any.
.nf
\f[C]
distrobox-host-exec [command [arguments]]
+
+--help/-h: show this message
+--verbose/-v: show more verbosity
+--version/-V: show version
\f[R]
.fi
.PP
-If no command is provided, it will execute \[lq]/bin/sh\[rq].
+If no command is provided, it will execute \[lq]$SHELL\[rq].
.PP
-Example usage:
+Alternatively, use symlinks to make \f[V]distrobox-host-exec\f[R]
+execute as that command:
.IP
.nf
\f[C]
-distrobox-host-exec ls
-distrobox-host-exec bash -l
-distrobox-host-exec flatpak run org.mozilla.firefox
-distrobox-host-exec podman ps -a
+\[ti]$: ln -s /usr/bin/distrobox-host-exec /usr/local/bin/podman
+\[ti]$: ls -l /usr/local/bin/podman
+lrwxrwxrwx. 1 root root 51 Jul 11 19:26 /usr/local/bin/podman -> /usr/bin/distrobox-host-exec
+\[ti]$: podman version
+\&...this is executed on host...
\f[R]
.fi
-.PP
-Options:
+.SH EXAMPLES
.IP
.nf
\f[C]
---help/-h: show this message
---verbose/-v: show more verbosity
---version/-V: show version
+distrobox-host-exec ls
+distrobox-host-exec bash -l
+distrobox-host-exec flatpak run org.mozilla.firefox
+distrobox-host-exec podman ps -a
\f[R]
.fi
diff --git a/man/man1/distrobox-init.1 b/man/man1/distrobox-init.1
index a5d6fcc..664460a 100644
--- a/man/man1/distrobox-init.1
+++ b/man/man1/distrobox-init.1
@@ -14,30 +14,32 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-INIT" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-INIT" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Init the distrobox (not to be launched manually)
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-init
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+\f[B]Init the distrobox (not to be launched manually)\f[R]
.PP
distrobox-init is the entrypoint of a created distrobox.
Note that this HAS to run from inside a distrobox, will not work if you
run it from your host.
.PP
-This is not intended to be used manually, but instead used by
-distrobox-enter to set up the container\[cq]s entrypoint.
+\f[B]This is not intended to be used manually, but instead used by
+distrobox-create to set up the container\[cq]s entrypoint.\f[R]
.PP
distrobox-init will take care of installing missing dependencies (eg.
sudo), set up the user and groups, mount directories from the host to
ensure the tight integration.
+.SH SYNOPSIS
.PP
-Usage:
-.IP
-.nf
-\f[C]
-distrobox-init --name test-user --user 1000 --group 1000 --home /home/test-user
-\f[R]
-.fi
-.PP
-Options:
+\f[B]distrobox-init\f[R]
.IP
.nf
\f[C]
@@ -48,14 +50,17 @@ Options:
--help/-h: show this message
--init/-I: whether to use or not init
--pre-init-hooks: commands to execute prior to init
+--upgrade/-U: run init in upgrade mode
--verbose/-v: show more verbosity
--version/-V: show version
--: end arguments execute the rest as command to execute during init
\f[R]
.fi
-.PP
-This is used as entrypoint for the created container, it will take care
-of creating the users, setting up sudo, mountpoints, and exports.
-.PP
-\f[B]You should not have to launch this manually\f[R], this is used by
-\f[V]distrobox create\f[R] to set up container\[cq]s entrypoint.
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-init --name test-user --user 1000 --group 1000 --home /home/test-user
+distrobox-init --upgrade
+\f[R]
+.fi
diff --git a/man/man1/distrobox-list.1 b/man/man1/distrobox-list.1
index 8316db4..24c2912 100644
--- a/man/man1/distrobox-list.1
+++ b/man/man1/distrobox-list.1
@@ -14,48 +14,59 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-LIST" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-LIST" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH List containers
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox list
+distrobox-list
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-list lists available distroboxes.
It detects them and lists them separately from the rest of normal podman
or docker containers.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox list\f[R]
.IP
.nf
\f[C]
-distrobox-list
+--help/-h: show this message
+--no-color: disable color formatting
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--size/-s: show also container size
+--verbose/-v: show more verbosity
+--version/-V: show version
\f[R]
.fi
-.PP
-You can also use environment variables to specify container manager
+.SH EXAMPLES
.IP
.nf
\f[C]
-DBX_CONTAINER_MANAGER=\[dq]docker\[dq] distrobox-list
+distrobox-list
\f[R]
.fi
.PP
-Supported environment variables:
+You can also use environment variables to specify container manager
.IP
.nf
\f[C]
-DBX_CONTAINER_MANAGER
+DBX_CONTAINER_MANAGER=\[dq]docker\[dq] distrobox-list
\f[R]
.fi
.PP
-Options:
+Supported environment variables:
.IP
.nf
\f[C]
---help/-h: show this message
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---size/-s: show also container size
---verbose/-v: show more verbosity
---version/-V: show version
+DBX_CONTAINER_MANAGER
+DBX_SUDO_PROGRAM
\f[R]
.fi
.PP
diff --git a/man/man1/distrobox-rm.1 b/man/man1/distrobox-rm.1
index 1eb7edb..8c20a92 100644
--- a/man/man1/distrobox-rm.1
+++ b/man/man1/distrobox-rm.1
@@ -14,13 +14,36 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-RM" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-RM" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Remove containers
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox rm
+distrobox-rm
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-rm delete one of the available distroboxes.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox rm\f[R]
+.IP
+.nf
+\f[C]
+--name/-n: name for the distrobox
+--force/-f: force deletion
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--help/-h: show this message
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -45,19 +68,6 @@ Supported environment variables:
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
-\f[R]
-.fi
-.PP
-Options:
-.IP
-.nf
-\f[C]
---name/-n: name for the distrobox
---force/-f: force deletion
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---help/-h: show this message
---verbose/-v: show more verbosity
---version/-V: show version
+DBX_SUDO_PROGRAM
\f[R]
.fi
diff --git a/man/man1/distrobox-stop.1 b/man/man1/distrobox-stop.1
index 11bf35f..1162b68 100644
--- a/man/man1/distrobox-stop.1
+++ b/man/man1/distrobox-stop.1
@@ -14,17 +14,40 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-STOP" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-STOP" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Stop containers
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox stop
+distrobox-stop
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-stop stop a running distrobox.
.PP
Distroboxes are left running, even after exiting out of them, so that
subsequent enters are really quick.
This is how they can be stopped.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox stop\f[R]
+.IP
+.nf
+\f[C]
+--name/-n: name for the distrobox
+--yes/-Y: non-interactive, stop without asking
+--help/-h: show this message
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -49,19 +72,6 @@ Supported environment variables:
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
-\f[R]
-.fi
-.PP
-Options:
-.IP
-.nf
-\f[C]
---name/-n: name for the distrobox
---yes/-Y: non-interactive, stop without asking
---help/-h: show this message
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---verbose/-v: show more verbosity
---version/-V: show version
+DBX_SUDO_PROGRAM
\f[R]
.fi
diff --git a/man/man1/distrobox-upgrade.1 b/man/man1/distrobox-upgrade.1
new file mode 100644
index 0000000..4f1f769
--- /dev/null
+++ b/man/man1/distrobox-upgrade.1
@@ -0,0 +1,50 @@
+.\
+.\"
+.\" Define V font for inline verbatim, using C font in formats
+.\" that render this, and otherwise B font.
+.ie "\f[CB]x\f[]"x" \{\
+. ftr V B
+. ftr VI BI
+. ftr VB B
+. ftr VBI BI
+.\}
+.el \{\
+. ftr V CR
+. ftr VI CI
+. ftr VB CB
+. ftr VBI CBI
+.\}
+.TH "DISTROBOX-UPGRADE" "1" "Sep 2022" "Distrobox" "User Manual"
+.hy
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-upgrade
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+distrobox-upgrade will enter the specified list of containers and will
+perform an upgrade using the container\[cq]s package manager.
+.SH SYNOPSIS
+.PP
+\f[B]distrobox upgrade\f[R]
+.IP
+.nf
+\f[C]
+--help/-h: show this message
+--all/-a: perform for all distroboxes
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-upgrade --all
+distrobox-upgrade alpine-linux ubuntu22 my-distrobox123
+distrobox upgrade CONTAINER_NAME [CONTAINER_NAME1 CONTAINER_NAME2 ...]
+\f[R]
+.fi
diff --git a/man/man1/distrobox.1 b/man/man1/distrobox.1
index 31139e3..132a745 100644
--- a/man/man1/distrobox.1
+++ b/man/man1/distrobox.1
@@ -15,30 +15,33 @@
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Compatibility
+.SH COMPATIBILITY
.PP
This project \f[B]does not need a dedicated image\f[R].
It can use any OCI images from docker-hub, quay.io, or any registry of
your choice.
.PP
-Granted, they may not be as featureful as expected (some of them do not
-even have \f[V]which\f[R], \f[V]mount\f[R], \f[V]less\f[R] or
-\f[V]vi\f[R]) but that\[cq]s all doable in the container itself after
-bootstrapping it.
+Many cloud images are stripped down on purpose to save size and may not
+include commands such as \f[V]which\f[R], \f[V]mount\f[R],
+\f[V]less\f[R] or \f[V]vi\f[R]).
+Additional packages can be installed once inside the container.
+We recommend using your preferred automation tool inside the container
+if you find yourself having to repeatedly create new containers.
+Maintaining your own custom image is also an option.
.PP
The main concern is having basic Linux utilities (\f[V]mount\f[R]),
basic user management utilities (\f[V]usermod, passwd\f[R]), and
\f[V]sudo\f[R] correctly set.
-.SS Supported container managers
+.SS SUPPORTED CONTAINER MANAGERS
.PP
\f[V]distrobox\f[R] can run on either \f[V]podman\f[R] or
\f[V]docker\f[R]
.PP
It depends either on \f[V]podman\f[R] configured in
\f[V]rootless mode\f[R] or on \f[V]docker\f[R] configured without sudo
-(follow THIS
+(follow THESE
instructions (https://docs.docker.com/engine/install/linux-postinstall/))
.IP \[bu] 2
Minimum podman version: \f[B]2.1.0\f[R]
@@ -52,7 +55,7 @@ Follow the official installation guide here:
<https://docs.docker.com/engine/install>
.IP \[bu] 2
<https://docs.docker.com/engine/install/linux-postinstall/>
-.SS Containers Distros
+.SS CONTAINERS DISTROS
.PP
Distrobox guests tested successfully with the following container
images:
@@ -69,40 +72,36 @@ Images
T}
_
T{
-AlmaLinux
-T}@T{
-8 8-minimal 9 9-minimal
-T}@T{
-docker.io/library/almalinux:8 docker.io/library/almalinux:9
-docker.io/library/almalinux:9-minimal
-T}
-T{
AlmaLinux (UBI)
T}@T{
8
T}@T{
-docker.io/almalinux/8-base docker.io/almalinux/8-init
+quay.io/almalinux/8-base:8 quay.io/almalinux/8-init:8
T}
T{
-Alpine Linux
+AlmaLinux
T}@T{
-3.14 3.15
+8 8-minimal 9 9-minimal
T}@T{
-docker.io/library/alpine:latest
+quay.io/almalinux/almalinux:8 quay.io/almalinux/almalinux:9
+quay.io/almalinux/almalinux:9-minimal
T}
T{
-AmazonLinux
+Alpine Linux
T}@T{
-2
+3.15 3.16
T}@T{
-docker.io/library/amazonlinux:2.0.20211005.0
+docker.io/library/alpine:3.15 docker.io/library/alpine:3.16
+docker.io/library/alpine:latest
T}
T{
AmazonLinux
T}@T{
-2022
+1 2 2022
T}@T{
-public.ecr.aws/amazonlinux/amazonlinux:2022
+public.ecr.aws/amazonlinux/amazonlinux:1
+public.ecr.aws/amazonlinux/amazonlinux:2
+public.ecr.aws/amazonlinux/amazonlinux:2022.0.20220531.0
T}
T{
Archlinux
@@ -111,10 +110,11 @@ T}@T{
docker.io/library/archlinux:latest
T}
T{
-ClearLinux
+CentOS Stream
T}@T{
+8 9
T}@T{
-docker.io/library/clearlinux:latest docker.io/library/clearlinux:base
+quay.io/centos/centos:stream8 quay.io/centos/centos:stream9
T}
T{
CentOS
@@ -124,26 +124,10 @@ T}@T{
quay.io/centos/centos:7
T}
T{
-CentOS Stream
-T}@T{
-8 9
-T}@T{
-quay.io/centos/centos:stream8 quay.io/centos/centos:stream9
-T}
-T{
-RedHat (UBI)
+ClearLinux
T}@T{
-7 8 9
T}@T{
-registry.access.redhat.com/ubi7/ubi
-registry.access.redhat.com/ubi7/ubi-init
-registry.access.redhat.com/ubi7/ubi-minimal
-registry.access.redhat.com/ubi8/ubi
-registry.access.redhat.com/ubi8/ubi-init
-registry.access.redhat.com/ubi8/ubi-minimal
-registry.access.redhat.com/ubi9/ubi
-registry.access.redhat.com/ubi9/ubi-init
-registry.access.redhat.com/ubi9/ubi-minimal
+docker.io/library/clearlinux:latest docker.io/library/clearlinux:base
T}
T{
Debian
@@ -171,21 +155,27 @@ T}@T{
docker.io/library/debian:unstable
T}
T{
-Neurodebian
+Fedora
T}@T{
-nd100
+35 36 37 Rawhide
T}@T{
-docker.io/library/neurodebian:nd100
+registry.fedoraproject.org/fedora-toolbox:35 quay.io/fedora/fedora:35
+quay.io/fedora/fedora:36 registry.fedoraproject.org/fedora:37
+quay.io/fedora/fedora:rawhide
T}
T{
-Fedora
+Gentoo Linux
+T}@T{
+rolling
+T}@T{
+You will have to Build your own to have a complete Gentoo docker image
+T}
+T{
+Kali Linux
T}@T{
-34 35 36 37 Rawhide
+rolling
T}@T{
-registry.fedoraproject.org/fedora-toolbox:34 docker.io/library/fedora:34
-registry.fedoraproject.org/fedora-toolbox:35 docker.io/library/fedora:35
-docker.io/library/fedora:36 registry.fedoraproject.org/fedora:37
-docker.io/library/fedora:rawhide
+docker.io/kalilinux/kali-rolling:latest
T}
T{
Mageia
@@ -195,6 +185,13 @@ T}@T{
docker.io/library/mageia
T}
T{
+Neurodebian
+T}@T{
+nd100
+T}@T{
+docker.io/library/neurodebian:nd100
+T}
+T{
Opensuse
T}@T{
Leap
@@ -212,17 +209,37 @@ T}
T{
Oracle Linux
T}@T{
-7 8
+7 7-slim 8 8-slim 9 9-slim
T}@T{
container-registry.oracle.com/os/oraclelinux:7
+container-registry.oracle.com/os/oraclelinux:7-slim
container-registry.oracle.com/os/oraclelinux:8
+container-registry.oracle.com/os/oraclelinux:8-slim
+container-registry.oracle.com/os/oraclelinux:9
+container-registry.oracle.com/os/oraclelinux:9-slim
+T}
+T{
+RedHat (UBI)
+T}@T{
+7 8 9
+T}@T{
+registry.access.redhat.com/ubi7/ubi
+registry.access.redhat.com/ubi7/ubi-init
+registry.access.redhat.com/ubi7/ubi-minimal
+registry.access.redhat.com/ubi8/ubi
+registry.access.redhat.com/ubi8/ubi-init
+registry.access.redhat.com/ubi8/ubi-minimal
+registry.access.redhat.com/ubi9/ubi
+registry.access.redhat.com/ubi9/ubi-init
+registry.access.redhat.com/ubi9/ubi-minimal
T}
T{
Rocky Linux
T}@T{
-8
+8 8-minimal
T}@T{
-docker.io/rockylinux/rockylinux:8
+quay.io/rockylinux/rockylinux:8 quay.io/rockylinux/rockylinux:8-minimal
+quay.io/rockylinux/rockylinux:latest
T}
T{
Scientific Linux
@@ -241,18 +258,11 @@ T}
T{
Ubuntu
T}@T{
-14.04 16.04 18.04 20.04 21.10 22.04
+14.04 16.04 18.04 20.04 22.04
T}@T{
docker.io/library/ubuntu:14.04 docker.io/library/ubuntu:16.04
docker.io/library/ubuntu:18.04 docker.io/library/ubuntu:20.04
-docker.io/library/ubuntu:21.10 docker.io/library/ubuntu:22.04
-T}
-T{
-Kali Linux
-T}@T{
-rolling
-T}@T{
-docker.io/kalilinux/kali-rolling:latest
+docker.io/library/ubuntu:22.04
T}
T{
Void Linux
@@ -261,13 +271,6 @@ T}@T{
ghcr.io/void-linux/void-linux:latest-full-x86_64
ghcr.io/void-linux/void-linux:latest-full-x86_64-musl
T}
-T{
-Gentoo Linux
-T}@T{
-rolling
-T}@T{
-You will have to Build your own to have a complete Gentoo docker image
-T}
.TE
.PP
Note however that if you use a non-toolbox preconfigured image (e.g.
@@ -284,7 +287,7 @@ plans to bring support to it.
If you are looking for unprivlaged NixOS environments, we suggest you
look into
nix-shell (https://nixos.org/manual/nix/unstable/command-ref/nix-shell.html).
-.SS New Distro support
+.SS NEW DISTRO SUPPORT
.PP
If your distro of choice is not on the list, open an issue requesting
support for it, we can work together to check if it is possible to add
@@ -292,7 +295,7 @@ support for it.
.PP
Or just try using it anyway, if it works, open an issue and it will be
added to the list!
-.SS Older distributions
+.SS OLDER DISTRIBUTIONS
.PP
For older distributions like CentOS 5, CentOS 6, Debian 6, Ubuntu 12.04,
compatibility is not assured.
@@ -321,17 +324,63 @@ dependencies are met.
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-CREATE" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-CREATE" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Create the distrobox
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox create
+distrobox-create
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-create takes care of creating the container with input name
and image.
The created container will be tightly integrated with the host, allowing
sharing of the HOME directory of the user, external storage, external
usb devices and graphical apps (X11/Wayland), and audio.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox create\f[R]
+.IP
+.nf
+\f[C]
+--image/-i: image to use for the container default: registry.fedoraproject.org/fedora-toolbox:36
+--name/-n: name for the distrobox default: my-distrobox
+--pull/-p: pull latest image unconditionally without asking
+--yes/-Y: non-interactive, pull images without asking
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--clone/-c: name of the distrobox container to use as base for a new container
+ this will be useful to either rename an existing distrobox or have multiple copies
+ of the same environment.
+--home/-H select a custom HOME directory for the container. Useful to avoid host\[aq]s home littering with temp files.
+--volume additional volumes to add to the container
+--additional-flags/-a: additional flags to pass to the container manager command
+--init-hooks additional commands to execute during container initialization
+--pre-init-hooks additional commands to execute prior to container initialization
+--init/-I use init system (like systemd) inside the container.
+ this will make host\[aq]s processes not visible from within the container.
+--help/-h: show this message
+--dry-run/-d: only print the container manager command generated
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH COMPATIBILITY
+.IP
+.nf
+\f[C]
+for a list of compatible images and container managers, please consult the man page:
+ man distrobox
+ man distrobox-compatibility
+or consult the documentation page on: https://github.com/89luca89/distrobox/blob/main/docs/compatibility.md#containers-distros
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -365,44 +414,7 @@ DBX_CONTAINER_IMAGE
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
-\f[R]
-.fi
-.PP
-Options:
-.IP
-.nf
-\f[C]
---image/-i: image to use for the container default: registry.fedoraproject.org/fedora-toolbox:36
---name/-n: name for the distrobox default: my-distrobox
---pull/-p: pull latest image unconditionally without asking
---yes/-Y: non-interactive, pull images without asking
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---clone/-c: name of the distrobox container to use as base for a new container
- this will be useful to either rename an existing distrobox or have multiple copies
- of the same environment.
---home/-H select a custom HOME directory for the container. Useful to avoid host\[aq]s home littering with temp files.
---volume additional volumes to add to the container
---additional-flags/-a: additional flags to pass to the container manager command
---init-hooks additional commands to execute during container initialization
---pre-init-hooks additional commands to execute prior to container initialization
---init/-I use init system (like systemd) inside the container.
- this will make host\[aq]s processes not visible from within the container.
---help/-h: show this message
---dry-run/-d: only print the container manager command generated
---verbose/-v: show more verbosity
---version/-V: show version
-\f[R]
-.fi
-.PP
-Compatibility:
-.IP
-.nf
-\f[C]
-for a list of compatible images and container managers, please consult the man page:
- man distrobox
- man distrobox-compatibility
-or consult the documentation page on: https://github.com/89luca89/distrobox/blob/main/docs/compatibility.md#containers-distros
+DBX_SUDO_PROGRAM
\f[R]
.fi
.PP
@@ -488,6 +500,9 @@ integration\f[R].
From within the container you will not be able to see and manage
host\[cq]s processes.
This is needed because \f[V]/sbin/init\f[R] must be pid 1.
+.PP
+From version 1.4.0 of distrobox, when you create a new container, it
+will also generate an entry in the applications list.
.\
.\"
.\" Define V font for inline verbatim, using C font in formats
@@ -504,9 +519,17 @@ This is needed because \f[V]/sbin/init\f[R] must be pid 1.
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-ENTER" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-ENTER" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Enter the distrobox
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox enter
+distrobox-enter
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-enter takes care of entering the container with the name
specified.
@@ -514,8 +537,27 @@ Default command executed is your SHELL, but you can specify different
shells or entire commands to execute.
If using it inside a script, an application, or a service, you can
specify the \[en]headless mode to disable tty and interactivity.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox enter\f[R]
+.IP
+.nf
+\f[C]
+--name/-n: name for the distrobox default: my-distrobox
+--/-e: end arguments execute the rest as command to execute at login default: bash -l
+--no-tty/-T: do not instantiate a tty
+--no-workdir/-nw: always start the container from container\[aq]s home directory
+--additional-flags/-a: additional flags to pass to the container manager command
+--help/-h: show this message
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--dry-run/-d: only print the container manager command generated
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -543,24 +585,7 @@ Supported environment variables:
DBX_CONTAINER_NAME
DBX_CONTAINER_MANAGER
DBX_SKIP_WORKDIR
-\f[R]
-.fi
-.PP
-Options:
-.IP
-.nf
-\f[C]
---name/-n: name for the distrobox default: my-distrobox
---/-e: end arguments execute the rest as command to execute at login default: bash -l
---no-tty/-T: do not instantiate a tty
---no-workdir/-nw: always start the container from container\[aq]s home directory
---additional-flags/-a: additional flags to pass to the container manager command
---help/-h: show this message
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---dry-run/-d: only print the container manager command generated
---verbose/-v: show more verbosity
---version/-V: show version
+DBX_SUDO_PROGRAM
\f[R]
.fi
.PP
@@ -587,6 +612,23 @@ my_var=test distrobox enter -n dev-arch --additional-flags -- printenv &| grep m
my_var=test
\f[R]
.fi
+.PP
+If you\[cq]d like to enter a rootful container having distrobox use a
+program other than `sudo' to run podman/docker as root, such as `pkexec'
+or `doas', you may specify it with the \f[V]DBX_SUDO_PROGRAM\f[R]
+environment variable.
+For example, to use `doas' to enter a rootful container:
+.IP
+.nf
+\f[C]
+DBX_SUDO_PROGRAM=\[dq]doas\[dq] distrobox enter -n container --root
+\f[R]
+.fi
+.PP
+Additionally, in one of the config file paths that distrobox supports,
+such as \f[V]\[ti]/.distroboxrc\f[R], you can also append the line
+\f[V]distrobox_sudo_program=\[dq]doas\[dq]\f[R] (for example) to always
+run distrobox commands involving rootful containers using `doas'.
.\
.\"
.\" Define V font for inline verbatim, using C font in formats
@@ -603,88 +645,112 @@ my_var=test
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-EXPORT" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-EPHEMERAL" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Application and service exporting
-.PP
-distrobox-export takes care of exporting an app a binary or a service
-from the container to the host.
-.PP
-The exported app will be easily available in your normal launcher and it
-will automatically be launched from the container it is exported from.
-.PP
-The exported services will be available in the host\[cq]s user\[cq]s
-systemd session, so
+.SH NAME
.IP
.nf
\f[C]
-systemctl --user status exported_service_name
+distrobox ephemeral
+distrobox-ephemeral
\f[R]
.fi
+.SH DESCRIPTION
.PP
-will show the status of the service exported.
-.PP
-The exported binaries will be exported in the \[lq]\[en]export-path\[rq]
-of choice as a wrapper script that acts naturally both on the host and
-in the container.
-Note that \[lq]\[en]export-path\[rq] is NOT OPTIONAL, you have to
-explicitly set it.
+distrobox-ephemeral creates a temporary distrobox that is automatically
+destroyed when the command is terminated.
+.SH SYNOPSIS
.PP
-You can specify additional flags to add to the command, for example if
-you want to export an electron app, you could add the
-\[lq]\[en]foreground\[rq] flag to the command:
+\f[B]distrobox ephemeral\f[R]
.IP
.nf
\f[C]
-distrobox-export --app atom --extra-flags \[dq]--foreground\[dq]
-distrobox-export --bin /usr/bin/vim --export-path \[ti]/.local/bin --extra-flags \[dq]-p\[dq]
-distrobox-export --service syncthing --extra-flags \[dq]-allow-newer-config\[dq]
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--verbose/-v: show more verbosity
+--help/-h: show this message
+--/-e: end arguments execute the rest as command to execute at login default: bash -l
+--version/-V: show version
\f[R]
.fi
-.PP
-This works for services, binaries, and apps.
-Extra flags are only used then the exported app, binary, or service is
-used from the host, using them inside the container will not include
-them.
-.PP
-The option \[lq]\[en]delete\[rq] will un-export an app, binary, or
-service.
+.SH EXAMPLES
.IP
.nf
\f[C]
-distrobox-export --app atom --delete
-distrobox-export --bin /usr/bin/vim --export-path \[ti]/.local/bin --delete
-distrobox-export --service syncthing --delete
-distrobox-export --service nginx --delete
+distrobox-ephemeral --image alpine:latest -- cat /etc/os-release
+distrobox-ephemeral --root --verbose --image alpine:latest --volume /opt:/opt
\f[R]
.fi
.PP
-The option \[lq]\[en]sudo\[rq] will launch the exported item as root
-inside the distrobox.
+You can also use flags from \f[B]distrobox-create\f[R] to customize the
+ephemeral container to run.
.PP
-Note you can use \[en]app OR \[en]bin OR \[en]service but not together.
+Refer to
.IP
.nf
\f[C]
-distrobox-export --service nginx --sudo
+man distrobox-create
\f[R]
.fi
.PP
-Usage:
+or
.IP
.nf
\f[C]
-distrobox-export --app mpv [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
-distrobox-export --service syncthing [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
-distrobox-export --bin /path/to/bin --export-path \[ti]/.local/bin [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+distrobox-create --help
\f[R]
.fi
.PP
-Options:
+Supported environment variables:
.IP
.nf
\f[C]
---app/-a: name of the application to export
+distrobox-ephemeral calls distrobox-create, SEE ALSO distrobox-create(1) for
+a list of supported environment variables to use.
+\f[R]
+.fi
+.\
+.\"
+.\" Define V font for inline verbatim, using C font in formats
+.\" that render this, and otherwise B font.
+.ie "\f[CB]x\f[]"x" \{\
+. ftr V B
+. ftr VI BI
+. ftr VB B
+. ftr VBI BI
+.\}
+.el \{\
+. ftr V CR
+. ftr VI CI
+. ftr VB CB
+. ftr VBI CBI
+.\}
+.TH "DISTROBOX-EXPORT" "1" "Sep 2022" "Distrobox" "User Manual"
+.hy
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-export
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+\f[B]Application and service exporting\f[R]
+.PP
+distrobox-export takes care of exporting an app a binary or a service
+from the container to the host.
+.PP
+The exported app will be easily available in your normal launcher and it
+will automatically be launched from the container it is exported from.
+.SH SYNOPSIS
+.PP
+\f[B]distrobox-export\f[R]
+.IP
+.nf
+\f[C]
+--app/-a: name of the application to export
--bin/-b: absolute path of the binary to export
--service/-s: name of the service to export
--delete/-d: delete exported application or service
@@ -692,7 +758,7 @@ Options:
Defaults to (on \[rs]$container_name)
--export-path/-ep: path where to export the binary
--extra-flags/-ef: extra flags to add to the command
---sudo/-S: specify if the exported item should be ran as sudo
+--sudo/-S: specify if the exported item should be run as sudo
--help/-h: show this message
--verbose/-v: show more verbosity
--version/-V: show version
@@ -703,8 +769,17 @@ You may want to install graphical applications or user services in your
distrobox.
Using \f[V]distrobox-export\f[R] from \f[B]inside\f[R] the container
will let you use them from the host itself.
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-export --app mpv [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+distrobox-export --service syncthing [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+distrobox-export --bin /path/to/bin --export-path \[ti]/.local/bin [--extra-flags \[dq]flags\[dq]] [--delete] [--sudo]
+\f[R]
+.fi
.PP
-App export example:
+\f[B]App export example\f[R]
.IP
.nf
\f[C]
@@ -718,7 +793,7 @@ with needed icons, add the prefix
commands to run, and save them in your home to be used directly from the
host as a normal app.
.PP
-Service export example:
+\f[B]Service export example\f[R]
.IP
.nf
\f[C]
@@ -732,7 +807,18 @@ container to a \f[V]systemctl --user\f[R] service, prefixing the various
\f[V]ExecStart ExecStartPre ExecStartPost ExecReload ExecStop ExecStopPost\f[R]
with the \f[V]distrobox-enter\f[R] command prefix.
.PP
-Binary export example:
+The exported services will be available in the host\[cq]s user\[cq]s
+systemd session, so
+.IP
+.nf
+\f[C]
+systemctl --user status exported_service_name
+\f[R]
+.fi
+.PP
+will show the status of the service exported.
+.PP
+\f[B]Binary export example\f[R]
.IP
.nf
\f[C]
@@ -747,6 +833,129 @@ from the host, the desired binary.
This can be handy with the use of \f[V]direnv\f[R] to have different
versions of the same binary based on your \f[V]env\f[R] or project.
.PP
+The exported binaries will be exported in the \[lq]\[en]export-path\[rq]
+of choice as a wrapper script that acts naturally both on the host and
+in the container.
+Note that \[lq]\[en]export-path\[rq] is NOT OPTIONAL, you have to
+explicitly set it.
+.PP
+\f[B]Additional flags\f[R]
+.PP
+You can specify additional flags to add to the command, for example if
+you want to export an electron app, you could add the
+\[lq]\[en]foreground\[rq] flag to the command:
+.IP
+.nf
+\f[C]
+distrobox-export --app atom --extra-flags \[dq]--foreground\[dq]
+distrobox-export --bin /usr/bin/vim --export-path \[ti]/.local/bin --extra-flags \[dq]-p\[dq]
+distrobox-export --service syncthing --extra-flags \[dq]-allow-newer-config\[dq]
+\f[R]
+.fi
+.PP
+This works for services, binaries, and apps.
+Extra flags are only used then the exported app, binary, or service is
+used from the host, using them inside the container will not include
+them.
+.PP
+\f[B]Unexport\f[R]
+.PP
+The option \[lq]\[en]delete\[rq] will un-export an app, binary, or
+service.
+.IP
+.nf
+\f[C]
+distrobox-export --app atom --delete
+distrobox-export --bin /usr/bin/vim --export-path \[ti]/.local/bin --delete
+distrobox-export --service syncthing --delete
+distrobox-export --service nginx --delete
+\f[R]
+.fi
+.PP
+\f[B]Run as root in the container\f[R]
+.PP
+The option \[lq]\[en]sudo\[rq] will launch the exported item as root
+inside the distrobox.
+.PP
+\f[B]Exporting apps from rootful containers\f[R]
+.PP
+It is worth noting that, when exporting any item - which includes
+graphical apps - from rootful containers (created with
+\f[V]distrobox create --root\f[R]), root privileges will be needed every
+time the item is launched (in order to enter the rootful container),
+which, by default, is done using \f[V]sudo\f[R] (see docs for
+\f[V]distrobox-enter\f[R] on how to customize that).
+However, for graphical apps in specific, since they launch without a
+terminal, the usage of \f[V]sudo\f[R] might, at first, make it
+impossible to launch them.
+.PP
+To fix this without needing to customize the sudo program, one can
+define a global \f[V]SUDO_ASKPASS\f[R] environment variable on their
+machine, which is a PATH to an executable that is run by \f[V]sudo\f[R]
+when no terminal is available (or when it is given the
+\f[V]--askpass\f[R] or \f[V]-A\f[R] option), and the output of that
+executable to stdout is used as the password input.
+The executable is called as many times is needed for authentication as
+root to succeed (unless a limit of amount of attempts is reached).
+.PP
+To do this, pick a program to ask the user for graphical password input.
+In this example, we will use \f[V]zenity --password\f[R], which should
+be present for GNOME users (and can also be installed in other DEs) -
+there are other options, such as
+\f[V]kdialog --password \[dq]Message\[dq]\f[R] for KDE users.
+.PP
+Write the call to the desired program to a script file, for example to
+\f[V]/usr/bin/my-password-prompt\f[R] (sample contents below):
+.IP
+.nf
+\f[C]
+#!/bin/sh
+zenity --password \[dq]Authentication as root is required\[dq]
+\f[R]
+.fi
+.PP
+(You may save the script under, for example, \f[V]\[ti]/.local/bin\f[R]
+if you want to keep it fully local to your user.)
+.PP
+Afterwards, make it executable (e.g.\ run
+\f[V]sudo chmod +x /usr/bin/my-password-prompt\f[R]).
+Then, make sure to set \f[V]SUDO_ASKPASS\f[R] to
+\f[V]\[dq]/usr/bin/my-password-prompt\[dq]\f[R] (replace with your
+script\[cq]s path) in a global profile file, so that it is picked up by
+sudo when running graphical apps (and, therefore, sudo will run the
+script you created to ask for a password).
+This is done with the shell line
+\f[V]export SUDO_ASKPASS=\[dq]/path/to/script/goes/here\[dq]\f[R].
+You can do this for your user only by running the command below (replace
+the script path as needed):
+.IP
+.nf
+\f[C]
+echo \[aq]export SUDO_ASKPASS=\[dq]/usr/bin/my-password-prompt\[dq]\[aq] >> \[ti]/.profile
+\f[R]
+.fi
+.PP
+Which appends the appropriate line to the end of your
+\f[V]\[ti]/.profile\f[R] file, thus making the change local to your
+user.
+Alternatively, to set it system-wide (for all users), you may create a
+file in \f[V]/etc/profile.d/\f[R] (or equivalent for your system) with
+that line.
+.PP
+Now just log out and log back in, and graphical apps exported from
+rootful containers should now be properly asking for root\[cq]s password
+before launching (instead of not opening, if that was the case before).
+.PP
+\f[B]Notes\f[R]
+.PP
+Note you can use \[en]app OR \[en]bin OR \[en]service but not together.
+.IP
+.nf
+\f[C]
+distrobox-export --service nginx --sudo
+\f[R]
+.fi
+.PP
[IMAGE: app-export (https://user-images.githubusercontent.com/598882/144294795-c7785620-bf68-4d1b-b251-1e1f0a32a08d.png)]
.PP
[IMAGE: service-export (https://user-images.githubusercontent.com/598882/144294314-29a8921f-4511-453d-bf8e-d0d1e336db91.png)]
@@ -772,18 +981,75 @@ option to provide a series of flags, for example:
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-HOST-EXEC" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-GENERATE-ENTRY" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Host Command Execution
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox generate-entry
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+distrobox-generate-entry will create a desktop icon for one of the
+available distroboxes.
+This will be then deleted when you remove the matching distrobox.
+.SH SYNOPSIS
+.PP
+\f[B]distrobox generate-entry\f[R]
+.IP
+.nf
+\f[C]
+ --help/-h: show this message
+ --all/-a: perform for all distroboxes
+ --delete/-d: delete the entry
+ --icon/-i: specify a custom icon [/path/to/icon] (default auto)
+ --verbose/-v: show more verbosity
+ --version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-generate-entry container-name [--delete] [--icon [auto,/path/to/icon]]
+\f[R]
+.fi
+.\
+.\"
+.\" Define V font for inline verbatim, using C font in formats
+.\" that render this, and otherwise B font.
+.ie "\f[CB]x\f[]"x" \{\
+. ftr V B
+. ftr VI BI
+. ftr VB B
+. ftr VBI BI
+.\}
+.el \{\
+. ftr V CR
+. ftr VI CI
+. ftr VB CB
+. ftr VBI CBI
+.\}
+.TH "DISTROBOX-HOST-EXEC" "1" "Sep 2022" "Distrobox" "User Manual"
+.hy
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-host-exec
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-host-exec lets one execute command on the host, while inside
of a container.
.PP
-If \[lq]flatpak-spawn\[rq] is installed in the container, this is what
-is used, and it is the most powerful and recommended method.
-If, instead, \[lq]flatpak-spawn\[rq] can\[cq]t be found, it still try to
-get the job done with \[lq]chroot\[rq] (but beware that not all
-commands/programs will work well in this mode).
+Under the hood, distrobox-host-exec uses \f[V]host-spawn\f[R] a project
+that let\[cq]s us execute commands back on the host.
+If the tool is not found the user will be prompted to install it.
+.SH SYNOPSIS
.PP
Just pass to \[lq]distrobox-host-exec\[rq] any command and all its
arguments, if any.
@@ -791,29 +1057,35 @@ arguments, if any.
.nf
\f[C]
distrobox-host-exec [command [arguments]]
+
+--help/-h: show this message
+--verbose/-v: show more verbosity
+--version/-V: show version
\f[R]
.fi
.PP
-If no command is provided, it will execute \[lq]/bin/sh\[rq].
+If no command is provided, it will execute \[lq]$SHELL\[rq].
.PP
-Example usage:
+Alternatively, use symlinks to make \f[V]distrobox-host-exec\f[R]
+execute as that command:
.IP
.nf
\f[C]
-distrobox-host-exec ls
-distrobox-host-exec bash -l
-distrobox-host-exec flatpak run org.mozilla.firefox
-distrobox-host-exec podman ps -a
+\[ti]$: ln -s /usr/bin/distrobox-host-exec /usr/local/bin/podman
+\[ti]$: ls -l /usr/local/bin/podman
+lrwxrwxrwx. 1 root root 51 Jul 11 19:26 /usr/local/bin/podman -> /usr/bin/distrobox-host-exec
+\[ti]$: podman version
+\&...this is executed on host...
\f[R]
.fi
-.PP
-Options:
+.SH EXAMPLES
.IP
.nf
\f[C]
---help/-h: show this message
---verbose/-v: show more verbosity
---version/-V: show version
+distrobox-host-exec ls
+distrobox-host-exec bash -l
+distrobox-host-exec flatpak run org.mozilla.firefox
+distrobox-host-exec podman ps -a
\f[R]
.fi
.\
@@ -832,30 +1104,32 @@ Options:
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-INIT" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-INIT" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Init the distrobox (not to be launched manually)
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-init
+\f[R]
+.fi
+.SH DESCRIPTION
+.PP
+\f[B]Init the distrobox (not to be launched manually)\f[R]
.PP
distrobox-init is the entrypoint of a created distrobox.
Note that this HAS to run from inside a distrobox, will not work if you
run it from your host.
.PP
-This is not intended to be used manually, but instead used by
-distrobox-enter to set up the container\[cq]s entrypoint.
+\f[B]This is not intended to be used manually, but instead used by
+distrobox-create to set up the container\[cq]s entrypoint.\f[R]
.PP
distrobox-init will take care of installing missing dependencies (eg.
sudo), set up the user and groups, mount directories from the host to
ensure the tight integration.
+.SH SYNOPSIS
.PP
-Usage:
-.IP
-.nf
-\f[C]
-distrobox-init --name test-user --user 1000 --group 1000 --home /home/test-user
-\f[R]
-.fi
-.PP
-Options:
+\f[B]distrobox-init\f[R]
.IP
.nf
\f[C]
@@ -866,17 +1140,20 @@ Options:
--help/-h: show this message
--init/-I: whether to use or not init
--pre-init-hooks: commands to execute prior to init
+--upgrade/-U: run init in upgrade mode
--verbose/-v: show more verbosity
--version/-V: show version
--: end arguments execute the rest as command to execute during init
\f[R]
.fi
-.PP
-This is used as entrypoint for the created container, it will take care
-of creating the users, setting up sudo, mountpoints, and exports.
-.PP
-\f[B]You should not have to launch this manually\f[R], this is used by
-\f[V]distrobox create\f[R] to set up container\[cq]s entrypoint.
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-init --name test-user --user 1000 --group 1000 --home /home/test-user
+distrobox-init --upgrade
+\f[R]
+.fi
.\
.\"
.\" Define V font for inline verbatim, using C font in formats
@@ -893,48 +1170,59 @@ of creating the users, setting up sudo, mountpoints, and exports.
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-LIST" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-LIST" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH List containers
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox list
+distrobox-list
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-list lists available distroboxes.
It detects them and lists them separately from the rest of normal podman
or docker containers.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox list\f[R]
.IP
.nf
\f[C]
-distrobox-list
+--help/-h: show this message
+--no-color: disable color formatting
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--size/-s: show also container size
+--verbose/-v: show more verbosity
+--version/-V: show version
\f[R]
.fi
-.PP
-You can also use environment variables to specify container manager
+.SH EXAMPLES
.IP
.nf
\f[C]
-DBX_CONTAINER_MANAGER=\[dq]docker\[dq] distrobox-list
+distrobox-list
\f[R]
.fi
.PP
-Supported environment variables:
+You can also use environment variables to specify container manager
.IP
.nf
\f[C]
-DBX_CONTAINER_MANAGER
+DBX_CONTAINER_MANAGER=\[dq]docker\[dq] distrobox-list
\f[R]
.fi
.PP
-Options:
+Supported environment variables:
.IP
.nf
\f[C]
---help/-h: show this message
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---size/-s: show also container size
---verbose/-v: show more verbosity
---version/-V: show version
+DBX_CONTAINER_MANAGER
+DBX_SUDO_PROGRAM
\f[R]
.fi
.PP
@@ -955,13 +1243,36 @@ Options:
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-RM" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-RM" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Remove containers
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox rm
+distrobox-rm
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-rm delete one of the available distroboxes.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox rm\f[R]
+.IP
+.nf
+\f[C]
+--name/-n: name for the distrobox
+--force/-f: force deletion
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--help/-h: show this message
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -986,20 +1297,7 @@ Supported environment variables:
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
-\f[R]
-.fi
-.PP
-Options:
-.IP
-.nf
-\f[C]
---name/-n: name for the distrobox
---force/-f: force deletion
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
---help/-h: show this message
---verbose/-v: show more verbosity
---version/-V: show version
+DBX_SUDO_PROGRAM
\f[R]
.fi
.\
@@ -1018,17 +1316,40 @@ Options:
. ftr VB CB
. ftr VBI CBI
.\}
-.TH "DISTROBOX-STOP" "1" "Jun 2022" "Distrobox" "User Manual"
+.TH "DISTROBOX-STOP" "1" "Sep 2022" "Distrobox" "User Manual"
.hy
-.SH Stop containers
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox stop
+distrobox-stop
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
distrobox-stop stop a running distrobox.
.PP
Distroboxes are left running, even after exiting out of them, so that
subsequent enters are really quick.
This is how they can be stopped.
+.SH SYNOPSIS
.PP
-Usage:
+\f[B]distrobox stop\f[R]
+.IP
+.nf
+\f[C]
+--name/-n: name for the distrobox
+--yes/-Y: non-interactive, stop without asking
+--help/-h: show this message
+--root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
+ way over \[dq]sudo distrobox\[dq] (note: if using a program other than \[aq]sudo\[aq] for root privileges is necessary,
+ specify it through the DBX_SUDO_PROGRAM env variable, or \[aq]distrobox_sudo_program\[aq] config variable)
+--verbose/-v: show more verbosity
+--version/-V: show version
+\f[R]
+.fi
+.SH EXAMPLES
.IP
.nf
\f[C]
@@ -1053,19 +1374,56 @@ Supported environment variables:
DBX_CONTAINER_MANAGER
DBX_CONTAINER_NAME
DBX_NON_INTERACTIVE
+DBX_SUDO_PROGRAM
\f[R]
.fi
+.\
+.\"
+.\" Define V font for inline verbatim, using C font in formats
+.\" that render this, and otherwise B font.
+.ie "\f[CB]x\f[]"x" \{\
+. ftr V B
+. ftr VI BI
+. ftr VB B
+. ftr VBI BI
+.\}
+.el \{\
+. ftr V CR
+. ftr VI CI
+. ftr VB CB
+. ftr VBI CBI
+.\}
+.TH "DISTROBOX-UPGRADE" "1" "Sep 2022" "Distrobox" "User Manual"
+.hy
+.SH NAME
+.IP
+.nf
+\f[C]
+distrobox-upgrade
+\f[R]
+.fi
+.SH DESCRIPTION
.PP
-Options:
+distrobox-upgrade will enter the specified list of containers and will
+perform an upgrade using the container\[cq]s package manager.
+.SH SYNOPSIS
+.PP
+\f[B]distrobox upgrade\f[R]
.IP
.nf
\f[C]
---name/-n: name for the distrobox
---yes/-Y: non-interactive, stop without asking
--help/-h: show this message
---root/-r: launch podman/docker with root privileges. Note that if you need root this is the preferred
- way over \[dq]sudo distrobox\[dq]
+--all/-a: perform for all distroboxes
--verbose/-v: show more verbosity
--version/-V: show version
\f[R]
.fi
+.SH EXAMPLES
+.IP
+.nf
+\f[C]
+distrobox-upgrade --all
+distrobox-upgrade alpine-linux ubuntu22 my-distrobox123
+distrobox upgrade CONTAINER_NAME [CONTAINER_NAME1 CONTAINER_NAME2 ...]
+\f[R]
+.fi
diff --git a/terminal-distrobox-icon.png b/terminal-distrobox-icon.png
new file mode 100644
index 0000000..f2089b9
Binary files /dev/null and b/terminal-distrobox-icon.png differ
diff --git a/tests/compatibility-test b/tests/compatibility-test
deleted file mode 100755
index bf9dc0b..0000000
--- a/tests/compatibility-test
+++ /dev/null
@@ -1,109 +0,0 @@
-#!/bin/sh
-
-trap '[ "$?" -ne 0 ] && printf "\nAn error occurred\n"' EXIT
-
-verbose=0
-start_index=0
-end_index=0
-# Dont' run this command as sudo.
-if [ "$(id -u)" -eq 0 ]; then
- printf >&2 "Running %s as sudo is not supported.\n" "${0}"
- printf >&2 "Please check the documentation on:\n"
- printf >&2 "\tman distrobox-compatibility\t"
- printf >&2 "or consult the documentation page on:\n"
- printf >&2 "\thttps://github.com/89luca89/distrobox/blob/main/docs/compatibility.md\n"
- exit 1
-fi
-
-# Print usage to stdout.
-# Arguments:
-# None
-# Outputs:
-# print usage with examples.
-show_help() {
- cat << EOF
-Usage:
-
- compatibility-test [--index X]
-
-Options:
-
- --start-index/si: from which index image to start [default=0]
- --end-index/ei: from which index image to start [default=last]
- --help/-h: show this message
- --verbose/-v: show more verbosity
-
-EOF
-}
-
-# Parse arguments
-while :; do
- case $1 in
- -h | --help)
- # Call a "show_help" function to display a synopsis, then exit.
- show_help
- exit 0
- ;;
- -v | --verbose)
- shift
- verbose=1
- ;;
- -si | --start-index)
- if [ -n "$2" ]; then
- start_index="$2"
- shift
- shift
- fi
- ;;
- -ei | --end-index)
- if [ -n "$2" ]; then
- end_index="$2"
- shift
- shift
- fi
- ;;
- *) # Default case: If no more options then break out of the loop.
- break ;;
- esac
-done
-
-set -o errexit
-set -o nounset
-# set verbosity
-if [ "${verbose}" -ne 0 ]; then
- set -o xtrace
-fi
-
-image_list=$(grep -E "docker.io|quay.io|ghcr|registry.|ecr." "$(dirname "${0}")"/../docs/compatibility.md |
- cut -d'|' -f 4 | sed 's/<br>/\n/g' | tr -d ' ' | tail -n +2)
-if [ "${end_index}" -eq 0 ]; then
- end_index=$(echo "${image_list}" | wc -l)
-fi
-
-progress=1
-for image in ${image_list}; do
- # POSIX SH does not support C-style loops, let's check boundaries manually.
- if [ "${progress}" -lt "${start_index}" ]; then
- # increase counter
- progress=$((progress + 1))
- continue
- elif [ "${progress}" -gt "${end_index}" ]; then
- break
- fi
-
- echo "##### Image ${progress}/${end_index} - ${image}"
- container_name="$(basename "${image}" | sed -E 's/:/-/g')"
- # Ensure distrobox create works:
- "$(dirname "${0}")"/../distrobox create --yes -i "${image}" --name "${container_name}"
- # Ensure distrobox enter and init works:
- "$(dirname "${0}")"/../distrobox enter --name "${container_name}" -- whoami
- # Ensure distrobox list works:
- "$(dirname "${0}")"/../distrobox list | grep "${container_name}" | grep "${image}" | grep Up
- # Ensure distrobox stop works:
- "$(dirname "${0}")"/../distrobox stop --yes "${container_name}"
- # Ensure distrobox rm works:
- "$(dirname "${0}")"/../distrobox rm --force --name "${container_name}"
-
- # increase counter
- progress=$((progress + 1))
-done
diff --git a/uninstall b/uninstall
index 83dd4d0..d7c8b31 100755
--- a/uninstall
+++ b/uninstall
@@ -32,7 +32,6 @@ uninstall --prefix /usr/local
Options:
--prefix/-P: base bath where all files will be deployed (default /usr/local if root, ~/.local if not)
- --path/-p: (DEPRECATED) path where to deploy the files (default /usr/local/bin if root, ~/.local/bin if not)
--help/-h: show this message
-v: show more verbosity
EOF
@@ -69,26 +68,16 @@ while :; do
esac
done
-if [ -n "${dest_path}" ] && [ -n "${prefix}" ]; then
- printf >&2 "Both -p and -P are set. Cannot continue. Exiting.\n"
- exit 1
-fi
-
-if [ -z "${dest_path}" ]; then
- if [ -z "${prefix}" ]; then
- prefix="/usr/local"
- # in case we're not root, just default to the home directory
- if [ "$(id -u)" -ne 0 ]; then
- prefix="${HOME}/.local"
- fi
+if [ -z "${prefix}" ]; then
+ prefix="/usr/local"
+ # in case we're not root, just default to the home directory
+ if [ "$(id -u)" -ne 0 ]; then
+ prefix="${HOME}/.local"
fi
- dest_path="${prefix}/bin"
- man_dest_path="${prefix}/share/man/man1"
-else
- printf >&2 "Warning: -p/--path is deprecated. Please refer to the documentation and switch to -P/--prefix.\n"
- # dest_path is already set
- man_dest_path="${dest_path}/../share/man/man1"
fi
+dest_path="${prefix}/bin"
+man_dest_path="${prefix}/share/man/man1"
+icon_dest_path="${prefix}/share/icons"
set -o errexit
set -o nounset
@@ -97,9 +86,8 @@ if [ "${verbose}" -ne 0 ]; then
set -o xtrace
fi
-# Ensure the foundamental variables are set and not empty, we will not proceed if
-# they are not all set.
-[ ! -w "${dest_path}" ] && printf >&2 "Cannot write into %s, permission denied.\n" "${dest_path}/bin" && exit 1
+[ ! -w "${dest_path}" ] && printf >&2 "Cannot write into %s, permission denied.\n" "${dest_path}" && exit 1
+[ ! -w "${man_dest_path}" ] && printf >&2 "Cannot write into %s, permission denied.\n" "${man_dest_path}" && exit 1
# uninstall
for file in "${dest_path}/distrobox"*; do
@@ -108,4 +96,7 @@ done
for file in "${man_dest_path}/distrobox"*; do
[ -e "${file}" ] && rm "${file}"
done
-echo "Thank you for using Distrobox. Uninstall complete."
+[ -e "${icon_dest_path}"/terminal-distrobox-icon.png ] && rm "${icon_dest_path}"/terminal-distrobox-icon.png
+[ -e "${icon_dest_path}"/distrobox ] && rm -rf "${icon_dest_path}"/distrobox
+
+printf >&2 "\033[1;31m Thank you for using Distrobox. Uninstall complete.\n\033[0m"
More information about the Neon-commits
mailing list