skip to Main Content

I want to detect the package manager on the system and then use that later on in my script. However, I feel this is clunky.

type apt    &> /dev/null && MANAGER=apt    && DISTRO="Debian/Ubuntu"
type yum    &> /dev/null && MANAGER=yum    && DISTRO="RHEL/Fedora/CentOS"
type dnf    &> /dev/null && MANAGER=dnf    && DISTRO="RHEL/Fedora/CentOS"   # $MANAGER=dnf will be default if both dnf and yum are present
type zypper &> /dev/null && MANAGER=zypper && DISTRO="SLES"
type apk    &> /dev/null && MANAGER=apk    && DISTRO="Alpine"

What I would like to do is define some kind of array or key-value pair such that

apt, Debian/Ubuntu
dnf, RedHat/Fedora/CentOS

and then have a function that allocates based on this pseudo-code:

for each item in the key-value pair {
    type {key} &> /dev/null && MANAGER={key} && DISTRO={value}
}

Can someone show me how that might be constructed in bash?

2

Answers


  1. Just define text. Of space separated columns, with newline separated elements.

    list=$(cat <<EOF
    apt Debian/Ubuntu
    dnf RedHat/Fedora/CentOS
    EOF
    )
    
    while IFS=' ' read -r key value; do
       if type "$key"; then...
    done <<<"$list"
    

    Prefer to use if instead of && for readability. You could use a different separator, to store spaces in elements, preprocess the list if you want to put some comments.

    You could also use multiple arrays:

    keys=(apt dnf)
    managers=(Debian/Ubuntu RedHat/Fedora/CentOS)
    for ((i=0;i<${#keys};++j)); do
        if type "${keys[i]}"; then
    

    You could also use associative arrays:

    declare -A managers=(
      [apt]=Debian/Ubuntu
      [dnf]=RedHat/Fedora/CentOS
    )
    for key in "${!managers[@]}"; do
       manager=${managers["$key"]}
    done
    

    Prefer to use lower case variables in scripts. Check your scripts with shellcheck.

    Login or Signup to reply.
  2. Defining such an array isn’t going to be significantly less clunky than what you already have.

    declare -A managers
    managers[apt]="Debian/Ubuntu"
    managers[yum]="RHEL/Fedora/CentOS"
    # etc
    
    for k in "${!managers[@]}"; do
        if type "$k"; then
            MANAGER=$k
            DISTRO=${managers[$k]}
            break
        fi
    done
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search