Script to find Error: rpmdb open failed on list of servers

Hello all,

I have a task to patch red hat servers and some servers have a corrupted rpm database and return the error:

Error: rpmdb open failed

I know how to fix this when it occurs. What I'm hoping to do is scan a list of servers by IP and report back which server have this error.

Would someone be able to assist or point me in the right direction on how I capture this? My thought is to run the following:

sudo yum update infolist 

On each server and capture the output to find the error.

Thanks in advance for any assistance or pointers you can provide me.

Are you considering to run your "status checking" script in cron?

You can use a for loop and process substitution and some descriptor magic:

#!/bin/bash
for server in server1 server2
do
  ssh -x "$server" '
    echo "hello I am on `hostname`"
    sudo yum update infolist
  ' 2> >(sed "s/^/$server: /" >&3)
done 3>stderr

The stderr output goes to the file stderr, filtered by sed.
The sed prepends $server: to every stderr line. It can also prepend it once:

for server in server1 server2
do
  ssh -x "$server" '
    echo "hello I am on `hostname`"
    sudo yum update infolist
  ' 2> >(sed "1i\\
$server:" >&3)
done 3>stderr

Hello @MadeInGermany and @Neo,

Thanks very much for your replies.

My intention is not to use this in a cronjob.

The script that MadeInGermany is what I was looking for. When I run these scripts I receive the following errors:

First Script Error:

 
checkyum.sh: line 7: syntax error near unexpected token `>'
checkyum.sh: line 7: `  ' 2> >(sed "s/^/$server: /" >&3)'

Second Script Error:

 
checkyum.sh: line 7: syntax error near unexpected token `('
checkyum.sh: line 7: `  ' 2>>(sed "1i\\'

My BashFu is pretty weak. Would you be able to point out what I need to change to get this working?

thank you.

For using the <( ) and >( ) process substitution, the OS must support Unix devices, and bash must be compiled to utilize it.
Obviously not true for your OS and bash.?

uname -sr
bash --version

The following pipes stderr (descriptor 2) to sed. But a pipe works with stdout (descriptor 1) only. Therfore, it swaps stdin and stdout before the pipe, and afterwards swaps them back.

#!/bin/bash
for server in server1 server2
do
  {
  ssh -x "$server" '
    echo "hello I am on `hostname`"
    sudo yum update infolist
  '  3>&2 2>&1 1>&3 | sed "s/^/$server: /" 
  } 3>&2 2>&1 1>&3
done 2>stderr

Hello @MadeInGermany,

Apologies for not responding sooner to your helpful reply.

Here are some details of the Red Hat server I'm using:

$ uname -sr
Linux 3.10.0-1062.el7.x86_64
$ bash --version
GNU bash, version 4.2.46(2)-release (x86_64-redhat-linux-gnu)

I'm trying my hand at this script again. I've used your suggestion:

#!/bin/bash
for server in server1 server2
do
  ssh -x "$server" '
    echo "hello I am on `hostname`"
    sudo yum update infolist
  ' 2> >(sed "1i\\
$server:" >&3)
done 3>stderr

I can successfully login to a server and I receive the echo that says "hello I am on 'hostname'" so the script is working and gives me this detail back. But I don't receive any other data back after running this script against my test server? Would this be the result if rpmdb open failed wasn't occuring on this test server? What I mean is...will the above script only show if rpmdb open failed exists and if it doesn't the script returns nothing back?

Thank you.

Here is an example of what I'm trying to do. If someone can help me formulate this line properly to get what I need please:

Code:

sudo yum repolist | grep -qi 'Error: rpmdb open failed ' ; case "$?" in "0") echo "Match" ;; "1") echo "No Match" ;; *) echo "Error" ;; esac

I would like to use a one line command so use it in a bash script along with other checks I do.