用于将 ip 解析为主机名的 bash_completion 规则

用于将 ip 解析为主机名的 bash_completion 规则

bash_completion我正在尝试为我的脚本创建规则rmpxe。该脚本将<hostname>其作为唯一的参数。然后,它将该主机名解析为<ip_address>并删除相应的符号链接/srv/tftp/pxelinux.cfg/<ip_address>

<ip_address>符号链接中的IP 地址/srv/tftp/pxelinux.cfg/<ip_address>是十六进制格式,但我用 C ( getnameinfo) 编写了一个简单的程序,它将这个十六进制 IP 地址解析为主机名。

因此,我可以使用我的程序getnameinfo从十六进制 IP 获取主机名:

$ getnameinfo 0A6F010B
server1.mydomain.com

例如,以下命令将删除符号链接/srv/tftp/pxelinux.cfg/0A6F010B

 $ rmpxe server1.mydomain.com

现在我的bash_completion问题是:我创建了以下代码,该代码工作正常,只是它没有完成主机名(如我的脚本所期望的),而是完成了十六进制 IP 地址(即我的目录中的符号链接文件/srv/tftp/pxelinux.cfg/)。我需要以某种方式集成到此代码中,在参数自动完成之前,它将首先解析为主机名。

_rmpxe()
{
    local word
    COMPREPLY=()

    if [ 1 -eq "$COMP_CWORD" ]; then
      pushd /srv/tftp/pxelinux.cfg &>/dev/null || return 1
      word="${COMP_WORDS[COMP_CWORD]}"
      COMPREPLY=($(compgen -f "$word"))
      popd &>/dev/null
    fi

}
complete -F _rmpxe rmpxe

换句话说,目前我的 bash 完成工作如下:

$ ls /srv/tftp/pxelinux.cfg
0A6F010B 0A6F010C 0A6F010D 0A6F010E

$ rmpxe <tab>
0A6F010B 0A6F010C 0A6F010D 0A6F010E

然而,我需要它像这样工作:

$ rmpxe <tab>
server1.mydomain.com server2.mydomain.com server3.mydomain.com

答案1

因为您使用了compgen -f,含义compgen将列出当前路径下的所有文件和目录。在你的情况下,这意味着0A6F010B 0A6F010C 0A6F010D 0A6F010E.

要获取主机名,您可以循环遍历当前路径,将每个 IP 提供给以getnameinfo获取与该 IP 对应的主机名,将其保存到数组中,然后将此数组用作带有compgen -W.

我在我的环境中做了一个简单的测试。我创建了一个文件/etc/bash_completion.d/cuonglm

_rmpxe() {
  local word
  COMPREPLY=()

  if [ 1 -eq "$COMP_CWORD" ]; then
    pushd /home/cuonglm/test &>/dev/null || return 1
    word="${COMP_WORDS[COMP_CWORD]}"
    HOST_ARR=()
    for i in *; do
      HOST_ARR+=($(/home/cuonglm/getnameinfo "$i"))
    done
    COMPREPLY=($(compgen -W "$(printf "%s " "${HOST_ARR[@]}")" -- "$word"))
    popd &>/dev/null
  fi
}
complete -F _rmpxe cuonglm

我使用了你的完整功能并做了一些修改:

  • 我使用数组HOST_ARR来保存主机名。
  • 循环当前目录(pushd之前感谢),将每个文件名输入getnameinfo程序。
  • 然后我用compgen -Wcompgen 创建一个单词列表来完成。

这是结果:

$ cuonglm <Tab>
$ cuonglm server<Tab>
server1.example.com  server2.example.com

因为两个主机名具有相同的部分server,所以 bash 将首先自动完成这部分。如果有其他主机名Server.example

$ cuonglm <Tab>
Server.example server1.example.com  server2.example.com

相关内容