6

I am writing a script that checks for a very big list of dependencies. So I wrote a function that gets the package name as input and using dpkg checks if it is installed and prints an appropriate output. Here is one version of this function:

check_dependency() { 
    dpkg -l $1 > /dev/null
    if [ $? -eq 0 ]; then
        # print something saying it is installed
    else
        # print something saying it was not found
    fi
}

which works fine when package is installed. But when it is not installed, it somehow doesn't redirect the output to /dev/null and prompts:

dpkg-query: no packages found matching foo-bar

In a second attempt, I modifed the body of function to use it with grep -q:

check_dependency() { 
    dpkg -s $1 | grep -q 'installed'
    if [ $? -eq 0 ]; then
        # print something saying it is installed
    else
        # print something saying it was not found
    fi
}

When the package is installed, again it seems to work fine, however, when package is not found and unwanted message from dpkg appears on terminal:

dpkg-query: package 'foo-bar' is not installed and no information is available bla bla...

Using directly dpkg-query results in similar problem. How to make it silent when it fails to find package?

2

2 Answers 2

4

You want to redirect both standard output (stdout) and standard error (stderr) to /dev/null. To do this, replace > with &>. This is a shortcut specific to bash. So your code would be:

check_dependency() { 
    dpkg -l $1 &> /dev/null
    if [ $? -eq 0 ]; then
        # print something saying it is installed
    else
        # print something saying it was not found
    fi
}

However, this would still count a package as being installed if it had been removed but config files remained (as pointed out by @A.B.). Instead, you could try

check_dependency() { 
    # Get the number of packages installed that match $1
    num=$(dpkg -l "$1" 2>/dev/null | egrep '^ii' | wc -l)

    if [ $num -eq 1 ]; then
        # print something saying it is installed
    elif [ $num -gt 1]; then
        # print something saying there is more than one package matching $1
    else
        # print something saying it was not found
    fi
}
2
  • Using dpkg -l $1 and checking the return code says nothing about the installation status of a package.
    – A.B.
    Nov 27, 2015 at 14:11
  • I used the check_dependency but I had to add extra [] in the conditonals to avoid issues Apr 3, 2021 at 12:38
2

Using dpkg -l $1 and checking the return code says nothing about the installation status of a package.

Use awk and dpkg -l and check the status ii

dpkg -l | awk '/^ii +'"$1"' +/'

Example

$ package="mc"
$ dpkg -l | awk '/^ii +'"$package" +' /'
ii  mc      3:4.8.13-3      i386       Midnight Commander - a powerful file manager

$ package="foobar"
$dpkg -l | awk '/^ii +'"$package" +' /'
<returns nothing>

or

$ package="mc"
$ dpkg -l | awk '/^ii +'"$package"' +/ {print $2}'
mc

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .