【问题标题】:Bash script to check iptables rules for loop with if condition使用 if 条件检查循环的 iptables 规则的 Bash 脚本
【发布时间】:2022-10-17 20:46:27
【问题描述】:

我将端口保存在要检查的数组中,然后运行 ​​for 循环来检查 iptables 规则列表中的端口。我想用未找到 msg 来回显不在 iptables 列表中的端口。试图在循环内添加一个 if 条件但不起作用。 这是代码:[非工作;)]

#!/bin/bash
array=( 3306 1403 8080 443 22 )
for i in "${array[@]}"
pc=(iptables --list | grep $i | cut -d " " -f1)
do
if [ "${pc}" = "ACCEPT" ]
then 
echo "ok"
else
echo "Port not found"
fi
done

错误:

array.sh: line 4: syntax error near unexpected token `|'
array.sh: line 4: `pc=(iptables --list | grep $i | cut -d " " -f1)'
array.sh: line 5: syntax error near unexpected token `do'
array.sh: line 5: `do'

【问题讨论】:

  • 什么不工作?
  • @BenjaminW。整个脚本。一些语法问题?
  • 确实......你把它放在ShellCheck吗?:)
  • pc=... 行当然应该在“do”关键字之后。你的意思可能是 pc=$(...) 而不是 pc=(...)
  • “整个脚本不起作用”可能意味着很多事情。你有错误吗?出乎意料的输出?你期望什么输出?

标签: linux bash shell iptables


【解决方案1】:

我并没有尝试对整个脚本进行语法检查,但在我看来这是一个明显的问题;您在执行之前分配了 pc evar。如果您使用制表符格式化代码,这将变得非常明显。例如:

#!/bin/bash
array=( 3306 1403 8080 443 22 )

for i in "${array[@]}"
pc=(iptables --list | grep $i | cut -d " " -f1)
do
    if [ "${pc}" = "ACCEPT" ]
    then 
        echo "ok"
    else
        echo "Port not found"
    fi
done

从上面可以看出,在 for 循环中没有设置 pc。试试这个:

#!/bin/bash
array=( 3306 1403 8080 443 22 )

for i in "${array[@]}"
do
    pc=$(iptables --list | grep $i | cut -d " " -f1)
    if [ "${pc}" = "ACCEPT" ]
    then 
        echo "ok"
    else
        echo "Port not found"
    fi
done

编辑:另外,@tink(比我早 1 分钟)注意到在 pc 变量的赋值中缺少 $ 。我已经更新了我的答案以明确这一点。高温高压

【讨论】:

  • 加上 pc=$(...) 不是 pc=(...)
【解决方案2】:

两个语法问题:

#!/bin/bash
array=( 3306 1403 8080 443 22 )
for i in "${array[@]}"
do
    pc=$(iptables --list | grep $i | cut -d " " -f1)
    if [ "${pc}" = "ACCEPT" ]
    then 
        echo "ok"
    else
        echo "Port not found"
    fi
done

【讨论】:

    【解决方案3】:

    使用while + read 循环和ProcSub 的替代方法。而不是在for 循环中嵌入grepcut

    #!/usr/bin/env bash
    
    array=( 3306 1403 8080 443 22 )
    
    regex=$(IFS='|'; printf '%s' "${array[*]}")
    
    while read -r pc port; do
      if [[ "$pc" = "ACCEPT" ]]; then
        printf '%s is Ok.
    ' "$port"
      else
        printf >&2 'Port %s not found.
    ' "$port"
      fi
    done < <(iptables --list | grep -E "$regex")
    

    针对包含以下内容的文件进行测试。

    ACCEPT 3306
    REJECT 1403
    REJECT 8080
    ACCEPT 443
    ACCEPT 22
    

    改变:

    iptables --list | grep -E "$regex"
    

    cat file.txt | grep -E "$regex"
    

    只是为了模拟iptables 命令。


    输出

    3306 is Ok.
    Port 1403 not found.
    Port 8080 not found.
    443 is Ok.
    22 is Ok.
    

    这是iptables --list 输出的最小假设,如果需要调整模式匹配,但这就是想法。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-04-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-07-07
      • 2021-10-18
      • 2013-03-10
      • 1970-01-01
      相关资源
      最近更新 更多