我有一个称为PPR的打印后台处理程序系统,该系统在其他之间控制用户的打印平衡。这样的命令“ppuser show username”将为给定用户打印信息。

[root@localhost ~]# ppuser show dpacheco
Name: dpacheco
Fullname:
Balance: 99.00
Cutoff point: 0.00
Last Modified: Wed Oct  1 11:37:58 2014
Account lifetime: 365
Credit revoked: FALSE

我需要为所有系统用户输出“用户名;余额”对的列表(PPR用户在/etc/passwd中是相同的)。为此,我编写了此命令...
cat /etc/passwd | awk -F : '$user=$1 {system("ppuser show "$user)}'| awk '$1 ~ /Balance/ {print $user;$2}'

解释..
  • 输出passwd的内容。
  • 将其传递到awk语句。
  • 我获得了用户名,将其存储在$ user var中,并使用它执行“ppuser show”命令。
  • 将结果传递到另一个awk语句
  • 评估包含“余额”的行的“ppuser show”输出,并打印用户名和余额,以分号分隔。

  • 问题..
    我得到这样的输出
    Balance: 100.00;100.00
    Balance: -40.00;-40.00
    Balance: 100.00;100.00
    Balance: 100.00;100.00
    Balance: 100.00;100.00
    Balance: 100.00;100.00
    .
    .
    .
    

    我看到的是$ user变量未在管道之间正确传递。
    我究竟做错了什么?

    谢谢

    最佳答案

    这里有一些解决方案。

    第一个根本不使用awk。我们使用/etc/passwdcut中提取用户名,然后使用Gnu grep grep选项从ppuser中对balance:行进行--label来输出用户名:

    cut -d: -f1 /etc/passwd | while read -r user; do
      grep -H --label="$user" ^Balance: < <(ppuser show "$user")
    done
    

    如果您没有Gnu grep,则可以使用printf以任何方便的格式打印用户名和提取的行:
    cut -d: -f1 /etc/passwd | while read -r user; do
      printf "%s: %s\n" "$user" "$(ppuser show "$user" | grep ^Balance:)"
    done
    

    如果愿意,您可以使用awk而不是shell来驱动整个过程,尽管这需要做更多的工作(并且没有经过很好的测试,但是根据@EdMorton的评论,我确实修复了一些输入错误并验证它是否可以在至少一个测试用例)。
    awk -F: '{cmd="ppuser show \""$1"\"";
              balance="";
              while ( (cmd | getline balance) > 0) {
                if (balance ~ /^Balance:/) {
                  printf "%s:%s\n", $1, substr(balance, index(balance, ":") + 1);
                  break;
                }
              }
              close(cmd);
             }' /etc/passwd
    

    关于linux - 在管道式awk语句之间传递变量,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/32232211/

    10-15 00:17
    查看更多