简体   繁体   English

版本排序 RPM Kernel 带数字的字符串 bash 返回不正确的结果

[英]Version sorting RPM Kernel string with numbers in bash returns incorrect result

I need the latest version out of these 4 kernel versions.我需要这 4 个 kernel 版本中的最新版本。

  • 4.18.0-187.el8.x86_64 4.18.0-187.el8.x86_64
  • 4.18.0-193.14.3.el8_2.x86_64 4.18.0-193.14.3.el8_2.x86_64
  • 4.18.0-193.el8.x86_64 4.18.0-193.el8.x86_64
  • 4.18.0-80.el8.x86_64 4.18.0-80.el8.x86_64

I had initially used numeric sort (which returns the 0-80 version incorrectly) before moving onto version sort for the same我最初使用数字排序(错误地返回 0-80 版本),然后再进行相同的版本排序

latest_kernel_in_use=$(ls boot/vmlinuz* | sed 's/\/boot\/vmlinuz-//' | sort -V | tail -n1 )

The command still returns 4.18.0-193.el8.x86_64 versus the desired 4.18.0-193.14.3.el8_2.x86_64 output.该命令仍然返回 4.18.0-193.el8.x86_64 而不是所需的 4.18.0-193.14.3.el8_2.x86_64 output。

Help me out with the correction in the command.帮助我更正命令。 I tested additionally and it's really the suffixes.el8.x86_64 complicating the sorting.我另外进行了测试,它确实是 suffixes.el8.x86_64 使排序复杂化。

[Edit] So I did it eventually, I removed the trailing alphabet/alphanumeric sequence, identifier being there is atleast one alphabet involved whether RPM kernel version is 4.18.0-193.14.3.el8_2.x86_64 or something like 4.18.0-193.14.3-generic as seen in Ubuntu [编辑] 所以我最终做到了,我删除了尾随的字母/字母数字序列,标识符至少涉及一个字母无论 RPM kernel 版本是4.18.0-193.14.3.el8_2.x86_64还是类似4.18.0-193.14 .3-generic如 Ubuntu 所示

latest_kernel_in_use=$(ls boot/vmlinuz* | sed 's/boot\/vmlinuz-//' | sed 's/[.-][[:alpha:]][[:alnum:][:punct:]]*//' | sort -V | tail -n1)

The Output with this is 4.18.0-193.14.3这个Output是4.18.0-193.14.3

I can work from there.我可以在那里工作。

seems to be because "e" > 1似乎是因为“e”> 1

I came up with this horror but I am sure there is a better way我想到了这种恐怖,但我相信有更好的方法

#!/bin/bash

# list your kernels and remove "vmlinuz-" prefix
KERNELS=$(find boot/ -iname "vmlinuz*" -exec basename {} \; | sed s/vmlinuz-//g)

# declare empty arrays (this will be arrays to contain our version and suffix strings)
VERSIONS_ARRAY=()
SUFFIXES_ARRAY=()

# we loop thought each kernel version
for KERNEL in $KERNELS;do
  # we will split each part of the kernel version on the dot (".")
  IFS="."
  read -ra KERNEL_VERSION <<< "$(echo $KERNEL)"
  # we define 2 empty strings to collect the kernel parts
  VERSION_STRING=""
  SUFFIX_STRING=""
  # we set back field separator to space
  IFS=" "
  # we loop throug all parts of kernel version
  for KERNEL_PART in ${KERNEL_VERSION[@]};do
    #echo -n $KERNEL_PART
    # if we encounter el8 or el8_2 or x86_64 string we append to the SUFFIX_STRING
    if [[ "$KERNEL_PART" == "el8" ]] || [[ "$KERNEL_PART" == "el8_2" ]] || [[ "$KERNEL_PART" == "x86_64" ]] ;then
      SUFFIX_STRING="${SUFFIX_STRING}${KERNEL_PART}."
    # else, we append to the VERSION_STRING
    else
      VERSION_STRING="${VERSION_STRING}${KERNEL_PART}."
    fi   
  done
  # we append the VERSION_STRING in VERSION_STRINGS
  VERSIONS_ARRAY+=("$VERSION_STRING")
  # we append the SUFFIX_STRING in SUFFIXES_ARRAYS
  SUFFIXES_ARRAY+=("$SUFFIX_STRING") 
done

# we set the field separator to split on linebreaks
IFS=$'\n'
# we find the highest value in version array
HIGHEST_VERSION=$(echo "${VERSIONS_ARRAY[*]}" | sort -V | tail -1)

# we get the position of highest value in array
for INDEX in ${VERSIONS_ARRAY[@]};do
    if [[ "$VERSIONS_ARRAY{[$INDEX]}" = "$HIGHEST_VERSION" ]]; then
        INDEX_OF_HIGHER_VERSION=$INDEX
    fi
done

# we get the corresponding suffix by index
HIGHEST_VERSION_SUFFIX=${SUFFIXES_ARRAY[$INDEX_OF_HIGHER_VERSION]}

# we remove the trailing dot in suffix
len=${#HIGHEST_VERSION_SUFFIX}
HIGHEST_VERSION_SUFFIX=${HIGHEST_VERSION_SUFFIX::len-1}

echo "vmlinuz-${HIGHEST_VERSION}${HIGHEST_VERSION_SUFFIX}"

# we set back field separator to space
IFS=" "

So I did it eventually, I removed the trailing alphabet/alphanumeric sequence, identifier being there is atleast one alphabet involved whether RPM kernel version is 4.18.0-193.14.3.el8_2.x86_64 or something like 4.18.0-193.14.3-generic as seen in Ubuntu所以我最终做到了,我删除了尾随的字母/字母数字序列,标识符至少涉及一个字母,无论 RPM kernel 版本是4.18.0-193.14.3.el8_2.x86_64还是类似4.18.0-193.14.3-通用如 Ubuntu 中所示

latest_kernel_in_use=$(ls boot/vmlinuz* | sed 's/boot\/vmlinuz-//' | sed 's/[.-][[:alpha:]][[:alnum:][:punct:]]*//' | sort -V | tail -n1)

The Output with this is 4.18.0-193.14.3这个Output是4.18.0-193.14.3

I can work from here.我可以在这里工作。

latest_kernel_in_use=$(ls /boot/vmlinuz* | sed 's//boot/vmlinuz-//' | sed 's/[.-][[:alpha:]][[:alnum:][:punct:]]*//' | sort -V | tail -n1) latest_kernel_in_use=$(ls /boot/vmlinuz* | sed 's//boot/vmlinuz-//' | sed 's/[.-][[:alpha:]][[:alnum:][:punct:] ]*//' | 排序 -V | 尾巴 -n1)

(/boot/vmlinux*) + s//boot... ) (/boot/vmlinux*) + s//boot... )

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM