BASH输出列格式

BASH输出列格式,bash,formatting,Bash,Formatting,第一次张贴。你好,世界。我的第一个脚本只是简单地检查我的网站列表是否在线,然后返回HTTP代码以及将其返回到桌面上的另一个文件所需的时间 --此脚本将在MAC OSX上运行-- 我想修改我的脚本,以便它将输出格式化为3个整洁的列 目前 #!/bin/bash file="/Users/USER12/Desktop/url-list.txt" printf "" > /Users/USER12/Desktop/url-results.txt while read line do pr

第一次张贴。你好,世界。我的第一个脚本只是简单地检查我的网站列表是否在线,然后返回HTTP代码以及将其返回到桌面上的另一个文件所需的时间

--此脚本将在MAC OSX上运行--

我想修改我的脚本,以便它将输出格式化为3个整洁的列

目前

#!/bin/bash
file="/Users/USER12/Desktop/url-list.txt"
printf "" > /Users/USER12/Desktop/url-results.txt
while read line
do
    printf "$line" >> /Users/USER12/Desktop/url-results.txt
    printf "\t\t\t\t" >> /Users/USER12/Desktop/url-results.txt
    curl -o /dev/null --silent --head --write-out '%{http_code} %{time_total}' "$line" >> /Users/USER12/Desktop/url-results.txt
    printf "\n" >> /Users/USER12/Desktop/url-results.txt
done <"$file"
但为了便于阅读,我想将其格式化成整齐排列的列

DOMAIN_NAME                 HTTP_CODE   RESPONSE_TIME
google.com                  200         0.389
facebook.com                200         0.511
abnormallyLongDomain.com    200         0.486

谢谢大家的帮助

栏目
非常好。但是,您已经在使用
printf
,它可以对输出格式进行精确控制。使用
printf
的功能还可以简化代码:

#!/bin/bash
file="/Users/USER12/Desktop/url-list.txt"
log="/Users/USER12/Desktop/url-results.txt"
fmt="%-25s%-12s%-12s\n"
printf "$fmt" DOMAIN_NAME HTTP_CODE RESPONSE_TIME > "$log"
while read line
do
    read code time < <(curl -o /dev/null --silent --head --write-out '%{http_code} %{time_total}' "$line")
    printf "$fmt" "$line" "$code" "$time" >> "$log"
done <"$file"
通过更改脚本中的
fmt
变量,可以微调输出格式,例如间距或对齐方式

进一步改进 上面的代码在每个循环中打开和关闭日志文件。正如Charles Duffy所建议的,这可以避免,只需使用
exec
stdout
重定向到第一条
printf
语句之前的日志文件:

#!/bin/bash
file="/Users/USER12/Desktop/url-list.txt"
exec >"/Users/USER12/Desktop/url-results.txt"
fmt="%-25s%-12s%-12s\n"
printf "$fmt" DOMAIN_NAME HTTP_CODE RESPONSE_TIME
while read line
do
    read code time < <(curl -o /dev/null --silent --head --write-out '%{http_code} %{time_total}' "$line")
    printf "$fmt" "$line" "$code" "$time"
done <"$file"
#/bin/bash
file=“/Users/USER12/Desktop/url list.txt”
exec>“/Users/USER12/Desktop/url results.txt”
fmt=“%-25s%-12s%-12s\n”
printf“$fmt”域名HTTP\u代码响应时间
读行时
做
读取代码的时间缩短了一点

#!/bin/bash

file="./url.txt"
fmt="%s\t%s\t%s\n"
( printf "$fmt" "DOMAIN_NAME" "HTTP_CODE" "RESPONSE_TIME"
while read -r line
do
    printf "$fmt" "$line" $(curl -o /dev/null --silent --head --write-out '%{http_code} %{time_total}' "$line")
done <"$file" ) | column -t > ./out.txt
然后像这样使用它:

myscript.sh < url-list.txt >result.txt

查看
命令。完美!!这正是我所需要的。更好,但为什么不只执行一次“$log”
,而不需要对每个命令执行任何重定向呢?当然,您还可以获得不重复打开同一文件的效率优势。避免每次尝试写入时重新打开
“$log”
的另一种方法是:将要写入该文件的所有命令放在一个命令组中:
{printf”$fmt“…;读取行时;do…;done;}<“$file”>“$log”
@CharlesDuffy感谢您为我展示了另一种方法。我已经实现了您建议的第二个版本。
#!/bin/bash
file="/Users/USER12/Desktop/url-list.txt"
fmt="%-25s%-12s%-12s\n"
{
printf "$fmt" DOMAIN_NAME HTTP_CODE RESPONSE_TIME
while read line
do
    read code time < <(curl -o /dev/null --silent --head --write-out '%{http_code} %{time_total}' "$line")
    printf "$fmt" "$line" "$code" "$time"
done <"$file"
} >"/Users/USER12/Desktop/url-results.txt"
#!/bin/bash

file="./url.txt"
fmt="%s\t%s\t%s\n"
( printf "$fmt" "DOMAIN_NAME" "HTTP_CODE" "RESPONSE_TIME"
while read -r line
do
    printf "$fmt" "$line" $(curl -o /dev/null --silent --head --write-out '%{http_code} %{time_total}' "$line")
done <"$file" ) | column -t > ./out.txt
#!/bin/bash

while read -r line
do
    printf "%s\t%s\t%s\n" "$line" $(curl -o /dev/null --silent --head --write-out '%{http_code} %{time_total}' "$line")
done | column -t
myscript.sh < url-list.txt >result.txt
something_produces_urls | myscript.sh | grep 200 > somewhere.txt