哈嘍大家好,我是鹹魚 在文章《三劍客之 sed》中鹹魚向大家介紹了文本三劍客中的 sed sed 全名叫 stream editor,流編輯器,用程式的方式來編輯文本 那麼今天鹹魚打算講一下我在用 sed 原地替換文件時遇到的趣事 sed 讓文件屬性變了? 有這麼一個普通文件 test.txt ,內 ...
哈嘍大家好,我是鹹魚
在文章《三劍客之 sed》中鹹魚向大家介紹了文本三劍客中的 sed
sed 全名叫 stream editor,流編輯器,用程式的方式來編輯文本
那麼今天鹹魚打算講一下我在用 sed 原地替換文件時遇到的趣事
sed 讓文件屬性變了?
有這麼一個普通文件 test.txt
,內容如下:
[root@localhost /opt]# cat test.txt
My name is Ammon
hello world!
hahahahaha
link_test.txt
是一個軟鏈接(Symbolic Link,也可以叫符號鏈接)文件,指向 test.txt
文件
軟鏈接文件類似於 Windows 的快捷方式,它實際上是一個特殊的文件。關於軟鏈接相關的內容這裡不過多介紹
如果我們對軟鏈接文件內容進行修改,源文件是會跟著改變的
當我使用 sed
對軟鏈接文件link_test.txt
進行內容修改時,命令如下
[root@localhost /opt]# sed -i 's/Ammon/Edsion/g' link_test.txt
有趣的現象發生了:使用 sed 對軟鏈接文件link_test.txt
進行內容修改之後,源文件test.txt
內容沒有變化,軟鏈接文件link_test.txt
的內容發生變化且變成了普通文件
怎麼樣,是不是很神奇?sed
不但把文件內容改了,還把文件屬性也給改了
我們用 strace
工具來查看一下在執行 sed
命令時操作系統做了哪些操作
strace 一個系統調用跟蹤工具,它會跟蹤並記錄命令運行期間的系統調用和信號
[root@localhost /opt]# strace sed -i 's/Ammon/Edsion/g' link_test.txt > strace.log 2>&1
具體內容有點多,我們著重看下關鍵內容
由上圖可以知道,如果我們使用 sed
對一個文件進行原地替換,需要有一個臨時文件,sed
先把修改內容寫入到這個文件,最後將文件 rename 到原來的地方
那我的需求是對軟鏈接文件 link_test.txt
進行內容修改,軟鏈接文件屬性不變,且源文件的內容也跟著改變,有沒有什麼方法呢?
也就是說我們希望命令在執行的時候能夠解析出來軟鏈接文件後面指向的源文件,直接對源文件進行讀--處理--寫,最後 rename
sed
命令有一個選項 --follow-symlinks
--follow-symlinks:
follow symlinks when processing in place
我們在執行的時候加上這個選項:
[root@localhost /opt]# strace sed -i --follow-symlinks 's/Ammon/Edsion/g' link_test.txt > strace.log 2>&1
總結一下:
- sed 替換的底層邏輯是把更新後的內容寫入一個臨時文件裡面,然後再 rename 這個臨時文件
- 這樣就會使得如果沒有添加
–follow-symlinks
選項的話,對軟鏈接文件進行 sed 操作就會使得軟鏈文件變成了一個常規文件(其實是那個臨時文件重命名導致的) - 如果要對軟鏈接文件指向的源文件進行操作,就需要添加
–follow-symlinks
選項