22# Set the version to be captured in newer versions of CheckMK Inventory
33CMK_VERSION=" 0.0.0"
44
5- if [ -z $MK_VARDIR ]; then
5+ if [ -z " $MK_VARDIR " ]; then
66 echo " ERROR: Unable to load ENV variables"
77 exit 2
88fi
@@ -15,21 +15,52 @@ CACHE_YUM_UPDATE=$MK_VARDIR/cache/yum_update.cache
1515CACHE_PREV_UPTIME=$MK_VARDIR /cache/yum_uptime.cache
1616LAST_UPDATE_TIMESTAMP=-1
1717
18- # Check which major version we are running so we can run appropriate commands
18+ # Check which distribution and major version we are running
1919if [ -f " /etc/os-release" ]; then
20- MAJOR_VERSION=$( grep -oP ' (?<=^VERSION_ID=").*(?=")' /etc/os-release | cut -d ' .' -f 1)
20+ MAJOR_VERSION=$( awk -F' =' ' /^VERSION_ID=/ {gsub(/"/,"",$2); split($2,a,"."); print a[1]}' /etc/os-release)
21+ DISTRO_ID=$( awk -F' =' ' /^ID=/ {gsub(/"/,"",$2); print $2}' /etc/os-release)
2122else
2223 MAJOR_VERSION=0
24+ DISTRO_ID=" unknown"
2325fi
2426
25- # get current yum state - use cache directory contents as fingerprint
27+ # Determine which package manager to use based on distribution and availability
28+ PKG_MGR=" "
29+ HISTORY_CMD=" "
30+ LIST_CMD=" "
31+ SECURITY_SUPPORTED=0
32+
33+ # Check for dnf5 first (Fedora 41+)
34+ if command -v dnf5 > /dev/null 2>&1 ; then
35+ PKG_MGR=" dnf5"
36+ HISTORY_CMD=" dnf5 history list"
37+ LIST_CMD=" dnf5 list --upgrades"
38+ SECURITY_SUPPORTED=1 # dnf5 supports security updates via check-upgrade --security
39+ # Check for regular dnf (Fedora 22+ up to 40, CentOS 8+)
40+ elif command -v dnf > /dev/null 2>&1 ; then
41+ PKG_MGR=" dnf"
42+ HISTORY_CMD=" dnf history list"
43+ LIST_CMD=" dnf list updates"
44+ SECURITY_SUPPORTED=1
45+ # Fall back to yum (CentOS/RHEL 6-7)
46+ elif command -v yum > /dev/null 2>&1 ; then
47+ PKG_MGR=" yum"
48+ HISTORY_CMD=" yum history list"
49+ LIST_CMD=" yum list updates"
50+ SECURITY_SUPPORTED=1
51+ else
52+ echo " ERROR: No supported package manager found (yum, dnf, or dnf5)"
53+ exit 2
54+ fi
55+
56+ # get current package manager state - use cache directory contents as fingerprint
2657YUM_CURRENT=" $( ls -lR /var/cache/{yum,dnf}/ 2> /dev/null) "
2758
2859# check if cached listing of /var/cache/yum already exists - create empty one otherwise
29- if [ ! -e $CACHE_YUM_UPDATE ]
60+ if [ ! -e " $CACHE_YUM_UPDATE " ]
3061then
31- touch $CACHE_YUM_UPDATE
32- elif [ ! -f $CACHE_YUM_UPDATE ] || [ -L $CACHE_YUM_UPDATE ]
62+ touch " $CACHE_YUM_UPDATE "
63+ elif [ ! -f " $CACHE_YUM_UPDATE " ] || [ -L " $CACHE_YUM_UPDATE " ]
3364then
3465 # something is wrong here...
3566 echo " ERROR: invalid cache file"
4071fi
4172
4273# check if cached check result already exists and is nothing but a file
43- if [ ! -e $CACHE_RESULT_CHECK ]
74+ if [ ! -e " $CACHE_RESULT_CHECK " ]
4475then
45- touch $CACHE_RESULT_CHECK
46- elif [ ! -f $CACHE_RESULT_CHECK ] || [ -L $CACHE_RESULT_CHECK ]
76+ touch " $CACHE_RESULT_CHECK "
77+ elif [ ! -f " $CACHE_RESULT_CHECK " ] || [ -L " $CACHE_RESULT_CHECK " ]
4778then
4879 # something is wrong here...
4980 echo " ERROR: invalid cache file"
5485RUNNING_SECS=$( cat /proc/uptime | cut -d" " -f1 | cut -d" ." -f1)
5586
5687# check if cache file with previously seen uptime is existing - create one otherwise
57- if [ ! -e $CACHE_PREV_UPTIME ]
88+ if [ ! -e " $CACHE_PREV_UPTIME " ]
5889then
59- echo 0 > $CACHE_PREV_UPTIME
90+ echo 0 > " $CACHE_PREV_UPTIME "
6091 PREV_UPTIME=0
61- elif [ ! -f $CACHE_PREV_UPTIME ] || [ -L $CACHE_PREV_UPTIME ]
92+ elif [ ! -f " $CACHE_PREV_UPTIME " ] || [ -L " $CACHE_PREV_UPTIME " ]
6293then
6394 # something is wrong here...
6495 echo " ERROR: invalid cache file"
@@ -67,103 +98,129 @@ else
6798 # get cached information
6899 PREV_UPTIME=$( cat " $CACHE_PREV_UPTIME " )
69100 # save current uptime
70- echo $RUNNING_SECS > $CACHE_PREV_UPTIME
101+ echo " $RUNNING_SECS " > " $CACHE_PREV_UPTIME "
71102fi
72103
73104# check if current uptime is lower than cached last seen uptime to detect reboot
74105if (( RUNNING_SECS < PREV_UPTIME ))
75106then
76107 # remove pre-reboot cache which requires reboot
77- rm -f $CACHE_RESULT_CHECK
108+ rm -f " $CACHE_RESULT_CHECK "
78109 # create empty check cache
79- touch $CACHE_RESULT_CHECK
110+ touch " $CACHE_RESULT_CHECK "
80111fi
81112
82113echo " <<<yum>>>"
83114
84115# compare current and cached yum information
85116# Update cached data if YUM fingerprint has changed OR machine has recently rebooted.
86- if [ " $YUM_CURRENT " != " $YUM_CACHED " ] || [ ! -s $CACHE_RESULT_CHECK ]
117+ if [ " $YUM_CURRENT " != " $YUM_CACHED " ] || [ ! -s " $CACHE_RESULT_CHECK " ]
87118then
88119 count=0
89- while [ -n " $( pgrep -f " python (/usr|)/bin/(yum|dnf)" ) " ]; do
90- if [ $count -eq 3 ]; then
91- echo " ERROR: Tried to run yum for 30 secs but another yum instance was running"
92- exit 2
93- else
94- (( count++ ))
95- sleep 10
96- fi
97- done
98- LATEST_KERNEL=$( yum -q -C --noplugins --debuglevel 0 list installed | egrep " ^(vz)?kernel(|-(uek|ml|lt))\." | grep " \." | tail -n1 | awk ' {print $2};' )
120+ # Check for running package manager processes
121+ while [ -n " $( pgrep -f " (python|/usr/bin/).*/(yum|dnf)" | head -1) " ]; do
122+ if [ $count -eq 3 ]; then
123+ echo " ERROR: Tried to run $PKG_MGR for 30 secs but another package manager instance was running"
124+ exit 2
125+ else
126+ (( count++ ))
127+ sleep 10
128+ fi
129+ done
130+
131+ # Check for kernel updates - different approach for different package managers
132+ if [ " $PKG_MGR " = " dnf5" ]; then
133+ # dnf5 has different output format - get only main kernel package, not kernel-core or kernel-modules
134+ LATEST_KERNEL=$( dnf5 list --installed 2> /dev/null | grep -E " ^kernel\.x86_64" | tail -n1 | awk ' {print $2}' )
135+ else
136+ # Traditional yum/dnf approach
137+ LATEST_KERNEL=$( $PKG_MGR -q -C --noplugins list installed 2> /dev/null | egrep " ^(vz)?kernel(|-(uek|ml|lt))\." | grep " \." | tail -n1 | awk ' {print $2}' )
138+ fi
139+
99140 RUNNING_KERNEL=$( cat /proc/version | awk ' {print $3}' | sed ' s/.x86_64//g' )
100141 if [[ " $RUNNING_KERNEL " == " $LATEST_KERNEL " * ]]
101142 then
102143 BOOT_REQUIRED=" no"
103144 else
104145 BOOT_REQUIRED=" yes"
105146 fi
106- UPDATES=$( waitmax 25 /usr/bin/yum -C --noplugins --quiet list updates | grep " \." | cut -d' ' -f1 | wc -l || echo " -1" )
107- # check if --security is available
108- # Updated the timeout for the initial security list validation because it takes longer than 10 seconds on many machines
109- waitmax 25 /usr/bin/yum -C --noplugins --quiet --security list updates > /dev/null 2>&1
110- if [ $? -eq 0 ]
111- then
112- SECURITY_UPDATES=$( waitmax 25 /usr/bin/yum -C --noplugins --quiet --security list updates | grep " \." | cut -d' ' -f1 | wc -l || echo " -1" )
147+
148+ # Count available updates - different commands for different package managers
149+ if [ " $PKG_MGR " = " dnf5" ]; then
150+ UPDATES=$( waitmax 25 dnf5 list --upgrades 2> /dev/null | grep -E " ^[a-zA-Z]" | wc -l || echo " -1" )
113151 else
114- # --security not supported with this yum version
115- # maybe the yum-plugin-security package is needed (RH 6)
116- SECURITY_UPDATES=" -2"
152+ UPDATES=$( waitmax 25 $PKG_MGR -C --noplugins --quiet list updates 2> /dev/null | grep " \." | cut -d' ' -f1 | wc -l || echo " -1" )
117153 fi
118154
119- # Check last time of installed Updates from yum history
120- # Added "list all" to the history command as in situations where 20 or more RPM installs have been completed (non updates
121- # yum commands) have been run, the script will incorrectly report that the server has never updated
122- # Yum only lists 20 of the last actions when using only the "history" command.
123-
124- # Switch command based on which Major version we are running
125- if [ " $MAJOR_VERSION " -ge 8 ]; then
155+ # Check for security updates if supported
156+ if [ $SECURITY_SUPPORTED -eq 1 ]; then
157+ if [ " $PKG_MGR " = " dnf5" ]; then
158+ # dnf5 uses different command for security updates
159+ SECURITY_UPDATES=$( waitmax 25 dnf5 -C --quiet check-upgrade --security 2> /dev/null | grep -E " ^[a-zA-Z0-9]" | wc -l || echo " -1" )
160+ else
161+ # Test if --security is available for traditional yum/dnf
162+ waitmax 25 $PKG_MGR -C --noplugins --quiet --security list updates > /dev/null 2>&1
163+ if [ $? -eq 0 ]; then
164+ if [ " $PKG_MGR " = " dnf" ]; then
165+ SECURITY_UPDATES=$( waitmax 25 dnf -C --noplugins --quiet --security list updates 2> /dev/null | grep " \." | cut -d' ' -f1 | wc -l || echo " -1" )
166+ else
167+ SECURITY_UPDATES=$( waitmax 25 yum -C --noplugins --quiet --security list updates 2> /dev/null | grep " \." | cut -d' ' -f1 | wc -l || echo " -1" )
168+ fi
169+ else
170+ # --security not supported with this version
171+ SECURITY_UPDATES=" -2"
172+ fi
173+ fi
174+ else
175+ # Package manager doesn't support security updates
176+ SECURITY_UPDATES=" -2"
177+ fi
126178
127- LAST_UPDATE_TIMESTAMP=$( /usr/bin/yum -C --quiet --noplugins history list | awk ' {if(NR>2)print}' | grep ' U \|Upgrade\|Update' | cut -d ' |' -f3 | head -n 1 | date -f - +" %s" || echo " -1" )
179+ # Check last time of installed Updates from history
180+ if [ " $PKG_MGR " = " dnf5" ]; then
181+ # dnf5 has different history output format - look for upgrade/update actions, not download
182+ LAST_UPDATE_TIMESTAMP=$( dnf5 history list 2> /dev/null | awk ' /upgrade --refresh|update[^-]|update$/ {print $5" "$6}' | head -n1 | date -f - +" %s" 2> /dev/null || echo " -1" )
183+ elif [ " $DISTRO_ID " = " fedora" ] || [ " $DISTRO_ID " = " centos" -a " $MAJOR_VERSION " -ge 8 ] || [ " $DISTRO_ID " = " rhel" -a " $MAJOR_VERSION " -ge 8 ]; then
184+ # Modern dnf/yum with different history format
185+ LAST_UPDATE_TIMESTAMP=$( $PKG_MGR -C --quiet --noplugins history list 2> /dev/null | awk ' {if(NR>2)print}' | grep -E ' U | Upgrade| Update' | head -n1 | awk ' {print $3}' | date -f - +" %s" 2> /dev/null || echo " -1" )
128186 else
129- LAST_UPDATE_TIMESTAMP=$( /usr/bin/yum -C --quiet --noplugins history list all| awk ' {if(NR>2)print}' | grep ' U \|Upgrade\|Update' | cut -d ' |' -f3 | head -n 1 | date -f - +" %s" || echo " -1" )
187+ # Legacy yum (CentOS/RHEL 6-7)
188+ LAST_UPDATE_TIMESTAMP=$( yum -C --quiet --noplugins history list all 2> /dev/null | awk ' {if(NR>2)print}' | grep -E ' U | Upgrade| Update' | cut -d ' |' -f3 | head -n1 | date -f - +" %s" 2> /dev/null || echo " -1" )
130189 fi
131- # Add check in case this is a brand new built machine that has had
132- # up to date pacakges installed during build. In this case, neither
133- # command above will have yielded a value and LAST_UPDATE_TIMESTAMP
134- # will be empty
135-
136- if [ " $LAST_UPDATE_TIMESTAMP " == " " ]; then LAST_UPDATE_TIMESTAMP=-1; fi
137190
191+ # Add check in case this is a brand new built machine
192+ if [ " $LAST_UPDATE_TIMESTAMP " = " " ]; then
193+ LAST_UPDATE_TIMESTAMP=-1
194+ fi
138195
139- echo $BOOT_REQUIRED
140- echo $UPDATES
141- echo $SECURITY_UPDATES
142- echo $LAST_UPDATE_TIMESTAMP
196+ echo " $BOOT_REQUIRED "
197+ echo " $UPDATES "
198+ echo " $SECURITY_UPDATES "
199+ echo " $LAST_UPDATE_TIMESTAMP "
143200
144- # cache check yum
201+ # cache check yum/dnf
145202 # check if cached check already exists and is nothing but a file
146- if [ -f $CACHE_YUM_UPDATE ] || [ ! -L $CACHE_YUM_UPDATE ]; then
147- echo " $YUM_CURRENT " > $CACHE_YUM_UPDATE
203+ if [ -f " $CACHE_YUM_UPDATE " ] || [ ! -L " $CACHE_YUM_UPDATE " ]; then
204+ echo " $YUM_CURRENT " > " $CACHE_YUM_UPDATE "
148205 else
149206 # something is wrong here...
150207 echo " ERROR: invalid check cache file"
151208 exit 2
152209 fi
210+
153211 # cache check results
154- # check if cached check result already exists and is nothing but a file
155- if [ -f $CACHE_RESULT_CHECK ] || [ ! -L $CACHE_RESULT_CHECK ]
212+ if [ -f " $CACHE_RESULT_CHECK " ] || [ ! -L " $CACHE_RESULT_CHECK " ]
156213 then
157- echo $BOOT_REQUIRED > $CACHE_RESULT_CHECK
158- echo $UPDATES >> $CACHE_RESULT_CHECK
159- echo $SECURITY_UPDATES >> $CACHE_RESULT_CHECK
160- echo $LAST_UPDATE_TIMESTAMP >> $CACHE_RESULT_CHECK
214+ echo " $BOOT_REQUIRED " > " $CACHE_RESULT_CHECK "
215+ echo " $UPDATES " >> " $CACHE_RESULT_CHECK "
216+ echo " $SECURITY_UPDATES " >> " $CACHE_RESULT_CHECK "
217+ echo " $LAST_UPDATE_TIMESTAMP " >> " $CACHE_RESULT_CHECK "
161218 else
162219 # something is wrong here...
163220 echo " ERROR: invalid check result cache file"
164221 exit 2
165222 fi
166223else
167224 # use cache file
168- cat $CACHE_RESULT_CHECK
225+ cat " $CACHE_RESULT_CHECK "
169226fi
0 commit comments