[英]Unable to grep output of a command in bash script
以下腳本未按預期運行
if docker pull docker.pkg.github.com/private-repo/centos7 | grep -q 'Error response from daemon: unauthorized'; then
echo "matched"
else
echo "unmatched"
fi
output
Error response from daemon: unauthorized
unmatched
預計 output
matched
我已經關注了這篇文章
我嘗試了什么:我將“docker.pkg.github.com/private-repo/centos7”替換為回顯“來自守護程序的錯誤響應:未授權”,它給出了匹配的預期 o/p。
所以,我在這里理解的是來自命令“docker pull docker.pkg.github.com/private-repo/centos7”的 o/p 沒有被“grep”捕獲,但我不明白為什么?
我也試過這個但結果相同:
docker pull docker.pkg.github.com/private-repo/centos7 | grep 'Error response from daemon: unauthorized' &> /dev/null
if [ $? == 0 ]; then
echo "matched"
else
echo "unmatched"
fi
@Gordon Davisson 建議的工作解決方案
docker pull docker.pkg.github.com/private-repo/centos7 2>&1 | grep 'Error response from daemon: unauthorized' &> /dev/null
if [ $? == 0 ]; then
echo "matched"
else
echo "unmatched"
fi
output:匹配
正如@Gordon Davisson 所說,如果他選擇聲明,請將答案歸功於他。 我正在使答案更加明顯。
這是一個過於簡單化的問題,但它會讓人明白這一點。 所有“輸出”都通過 stdout 和 stderr 發送到終端。
當您使用基本管道語法 (|) 時,pipe 實際處理的唯一內容是標准輸出。 stderr 仍將打印到終端。 在您的情況下,這是不受歡迎的行為。
解決方法是強制 stderr 在 pipe 之前進入 stdout,其語法為 2&>1(或在 Bash |& 中)。 這解決了管道只能處理 stdout 的限制,並且還可以防止 stderr 泄漏到終端中。
if docker pull… 2&>1 | grep -q…
<SNIPPED>
或在 BASH
if docker pull… |& grep -q…
<SNIPPED>
您第二次嘗試的解決方案不起作用的原因是管道和重定向是按從左到右的順序處理的。
if docker pull… | grep… &> /dev/null
# ^ LEAK HAPPENS HERE, FIX COMES TOO LATE
<SNIPPED>
這意味着在您重定向 grep 的 output 之前,stderr 已經泄漏到終端中。並且錯誤不是從 grep 發生的。
問題是 docker 拉命令的 output 沒有傳遞給 grep 命令。 相反,output 被打印到控制台。 要解決此問題,您可以使用命令替換將 docker 拉命令的 output 分配給一個變量,然后將該變量傳遞給 grep,如下所示:
output=$(docker pull docker.pkg.github.com/private-repo/centos7)
if echo "$output" | grep -q 'Error response from daemon: unauthorized'; then
echo "matched"
else
echo "unmatched"
fi
這會將 docker pull 命令的 output 賦值給變量 output,然后將該變量傳遞給 grep 進行比較。 echo 命令用於將變量傳遞給 grep。
如果您只搜索Error
而不是整個字符串並查看您輸入字符串的方式是否有問題,您可能會很幸運。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.