Bash

有沒有辦法檢查您的作業系統使用哪些換行符?

  • August 16, 2021

我正在嘗試執行這個開源 bash 腳本,但它不起作用,因為它假設我在解析輸入時正在執行 linux。實際上,我在 Windows 機器上執行 cygwin。腳本中有一個地方將 $IFS 設置為\n,這會留下\r導致錯誤的 a ,因為它無法匹配精確的字元串。

修改我的本地版本的腳本很容易,但我將如何解決這個問題以便它適用於任何作業系統?如果我可以執行一些命令來獲取換行符,那麼我可以將它們分配給 $IFS。


對於一些額外的上下文,處理換行符的程式碼是這樣的:

IFS=\n
# Word splitting is intended here
# shellcheck disable=2046
set -- $(printf '%s\n' "$_response" | jq -r '
   .error,
   .access_token,
   .token_type,
   .expires_in,
   .refresh_token,
   .scope')
IFS=$oifs

[ "$1" = "null" ] && ...

該測試最終將“null\r”與“null”進行比較。

與其確定您的系統使用哪種類型的行尾,另一個可能可行的選項可能是關注您的輸入文件使用哪種類型的行尾。

我這樣說是因為很容易(以程式方式)更改文件中的行尾,無論是在編寫時還是通過後處理(通過dos2unix或類似方式)。

您可以使用該file命令提供有關文件正在使用的行尾的一些資訊。

tim@chaos:~/tmp$ file lnx.txt
lnx.txt: ASCII text

tim@chaos:~/tmp$ file win.txt
win.txt: ASCII text, with CRLF line terminators

tim@chaos:~/tmp$ dos2unix -n win.txt win2unix.txt
dos2unix: converting file win.txt to file win2unix.txt in Unix format...

tim@chaos:~/tmp$ file win2unix.txt
win2unix.txt: ASCII text

因此,可以將獲取輸入文件的腳本設置為檢查不同的行尾,並即時修改它們,或者它可以簡單地獲取任何輸入文件並通過dos2unix.

差異只是\r\n比較\n。因此,可以想像在 shell 腳本中處理輸入流可以擷取任何 CRLF 類型的行結尾,而無需進行任何文件轉換。

但是,您的 shell 腳本選擇逐行讀取文件來處理它們,您只需添加一個額外的sed步驟。

你可以這樣做:

IFS=\n
# Word splitting is intended here
# shellcheck disable=2046
set -- $(printf '%s\n' "$_response" | sed -e s'/\r//g' | jq -r '
   .error,
   .access_token,
   .token_type,
   .expires_in,
   .refresh_token,
   .scope')
IFS=$oifs

[ "$1" = "null" ] && ...

如果它們存在,那將刪除 CRLF,如果不存在,則不會更改輸入行。

通過讓腳本自動轉換輸入的不同行尾,那麼文件具有什麼樣的行尾實際上並不重要,您的腳本就會變得更加便攜。或者至少,輸入不可知。

引用自:https://unix.stackexchange.com/questions/664837