【问题标题】:Nested for loop with output text variable带有输出文本变量的嵌套 for 循环
【发布时间】:2020-07-09 19:32:30
【问题描述】:

我需要修改简单的 bash 脚本来遍历文件,并在每个文件的末尾添加一些带有文件变量名称的文本。有一个 Nagios .cfg 文件的例子……到目前为止我得到了这样的东西:

#!/bin/bash

list=$(ls /root/user/test/ | sed "s/\.cfg//")

用于 `/root/user/test/*.cfg` 中的服务器;做
    对于$列表;做
        回声`
        
        定义服务{
               主机名 $list
               service_description All_fs_free_space
               check_command check_nrpe!check_all_disks!3% 1%
               使用用户磁盘
        }` >> /etc/nagios3/conf.d/servers/test/$servery
    完毕
完成

不幸的是,由于引号没有工作......?有没有更好的解决方案如何实现?谢谢。

Paul Hodges 解决方案的调试输出:

root@bla:~/blabla# ./add2.sh ++ fmt=' 定义服务{ 主机名 %s service_description All_fs_free_space check_command check_nrpe!check_all_disks!3%% 1%% 使用用户磁盘 }' ++ 用于“/root/user/test/*.cfg”中的文件 ++ cfg='*.cfg' ++打印' 定义服务{ 主机名 %s service_description All_fs_free_space check_command check_nrpe!check_all_disks!3%% 1%% 使用用户磁盘 }''*' ./add2.sh:第 14 行:/root/blabla/test/servers/$cfg:不明确的重定向

【问题讨论】:

  • 通过Shell Check 运行您的脚本。你有几个简单的语法错误。
  • 很确定您不希望在 /root/user/test/*.cfg 或您的输出周围出现反引号。
  • ++ for file in '/root/user/test/*.cfg'++ cfg='*.cfg' 表示在 /root/user/test/ 中没有以 cfg 结尾的文件名可以循环。如果您希望它跳过循环而没有错误(或任何其他有用的输出),请设置shopt -s nullglob。否则,在处理之前明确测试/root/blabla/test/servers/$cfg 的存在,如果不存在则失败。见下文。

标签: bash for-loop nested-loops


【解决方案1】:

再抽象一点。

更新 -

根据上面的 cmets 检查文件是否存在。

#!/bin/bash
fmt='

    define service {
           host_name                       %s
           service_description             All_fs_free_space
           check_command                   check_nrpe!check_all_disks!3%% 1%%
           use                             user-disk
    }'

for file in /root/user/test/*.cfg # assuming there are *.cfg files here
do if [[ -e "/root/blabla/test/servers/$cfg" ]]
   then cfg=${file##*/}                # stripping the path
        printf "$fmt\n" "${cfg%.cfg}" >> /etc/nagios3/conf.d/servers/test/$cfg
   else echo "File not found: /root/blabla/test/servers/$cfg" >&2
   fi
done

对您的意图做出一些假设。
我会先备份所有内容,然后在使用通配符之前进行编辑以仅匹配一个文件进行测试...

【讨论】:

  • 是的,但这可能只完成部分工作。在“%s”位置(在我的示例中为 $list),我需要包含配置文件名称(确切地说是服务器的主机名)的变量,不带 cfg 后缀。一次迭代的 Skript 将 $fmt 的内容放在文件末尾,并更改变量 $list ,如将要修改的文件的名称。
  • %sprintf"$fmt" 格式字符串中的字符串替换指示符,这就是为什么还有另一个参数-cfg=${file##*/} 去掉前导路径信息,所以"${cfg%.cfg}"只是没有cfg后缀的配置文件名。你试过了吗?
  • 哦,好吧,抱歉,我不知道,bash 魔法。但无论如何我得到了“第 13 行:/etc/nagios3/conf.d/servers/test/$cfg: ambiguous redirect”
  • 在顶部放置一个set -x 以查看实际解析的内容。奇怪的是 $cfg 没有先被扩展。
  • use user-disk }' '*' 这是set -x 出错之前的最后两行代码
猜你喜欢
  • 1970-01-01
  • 2018-12-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-08-21
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多