2012-03-08 25 views

回答

3

有幾種方法來實現這一目標:

  • 如果可以,請從腳本啓動該過程。當進程終止時,腳本將繼續運行,這意味着它無法再向該文件寫入更多數據。

  • 如果您無法控制進程但您知道進程在寫入文件後終止,則可以找出進程標識,然後檢查進程是否仍在運行kill -0 $PID。如果$?之後爲0,則該過程仍然存在。

  • 如果這是不可能的,那麼您可以使用lsof -np $PID來獲取此進程的所有打開文件的列表,並檢查您的文件是否在列表中。雖然這有點慢。

[編輯]注意,所有這些方法都是有點脆。正確的解決方案是讓外部進程使用臨時名稱寫入文件,然後在完成後立即對其進行重命名。

重命名確保每個人都可以看到整個文件的所有數據或沒有。

+0

'! lsof -/path/to/file'? – RubyTuesdayDONO 2013-12-24 04:39:00

+0

@RubyTuesdayDONO:那呢? – 2014-01-08 09:27:44

+0

我認爲它是一種更直接的方式來查詢是否有任何進程打開該特定文件(與通過最可能進程打開的所有文件的列表進行「grep」打開)。你的第二個建議是在完成後重新命名臨時文件,看起來像是一個更好的選擇 - 我只想強調一下,'lsof'是一個複雜的命令,帶有多個向量,用於準確地獲取所需的信息。 – RubyTuesdayDONO 2014-01-09 01:19:20

2

簡單的方法:讓腳本執行程序並等待它完成。

1

這是不是很好,這讓我覺得髒寫它...... /tmp/foo.txt在文件正在測試...

#!/bin/bash 

until [ "$(find /proc/*/fd 2> /dev/null | 
    xargs -i{} readlink {} | 
    grep -c '^/tmp/foo.txt$')" == "0" ]; do 

    sleep 1; 
done; 
0

循環直到文件處於穩定狀態的方法,如果你正在等待實驗結果(所以你不需要實時事件處理)這應該工作:

EXPECTED_WRITE_INTERVAL_SECONDS=1 
FILE="file.txt" 
while : ; do 
     omod=$(stat -c %Y $FILE) 
     # echo "OLD: $omod" 
     sleep $EXPECTED_WRITE_INTERVAL_SECONDS 
     nmod=$(stat -c %Y $FILE) 
     # echo "NEW: $nmod" 
     if [ $omod == $nmod ] ; then 
       break 
     fi 
done 
1

創建使用inotify一個小的C程序。程序應該:

  1. 創建一個inotify實例。
  2. 爲感興趣的文件路徑添加關於IN_CLOSE_WRITE事件的實例的手錶。
  3. 等待事件發生。
  4. 使用適當的代碼退出。

然後在您的腳本中,以文件路徑作爲參數調用該程序。

您可以通過添加一個超時參數來擴展它,並允許指定不同的事件。