2010-04-26 35 views
6

我想檢查某個進程已經在使用中的臨時文件demo.lock運行:檢查如果PHP進程已經運行

demo.php:

<?php 
    $active=file_exists('demo.lock'); 
    if ($active) 
    { 
     echo 'process already running'; 
    } 
    else 
    { 
     file_put_contents ('demo.lock', 'demo'); 
     sleep(10); //do some job 
     unlink ('demo.lock'); 
     echo 'job done'; 
    } 
?> 

但是它不似乎沒有用:如果我打開demo.php兩次,它總是顯示「工作已完成」,也許是因爲它認爲它是相同的過程?有沒有辦法做到這一點?我也用getmypid()嘗試了類似的結果。

謝謝

+0

我會建議你使用一個命名的互斥體這樣的事情,但我不知道這些是在PHP可用.. – 2010-04-26 16:12:36

+0

還,你的操作系統是什麼? – zneak 2010-04-26 16:20:54

+0

我已經在Windows和Linux機器上嘗試過它,結果相同 – Borgtex 2010-04-27 07:50:14

回答

0

好吧,發送一些頭文件和刷新似乎對我來說(不知道爲什麼),所以現在當我加載頁面顯示「開始」,如果我在完成該過程之前點擊瀏覽器上的刷新按鈕,警告消息:

<?php 

$file = @fopen("demo.lock", "x"); 
if($file === false) 
{ 
    echo "Unable to acquire lock; either this process is already running, or permissions are insufficient to create the required file\n"; 
    exit; 
} 

header("HTTP/1.0 200 OK"); 
ob_start(); 
echo "Starting"; 
header('Content-Length: '.ob_get_length(),true); 
ob_end_flush(); 
flush(); 

fclose($file); // the fopen call created the file already 
sleep(10); // do some job 
unlink("demo.lock");  
?> 

感謝所有的答案和建議,到目前爲止

2

適合我。

確保腳本可以在目錄中創建一個文件。取消註釋「取消鏈接」行並運行腳本並檢查目錄中是否存在鎖定文件。如果你沒有看到它,那麼這是一個目錄權限問題。

+0

對我來說似乎很奇怪,它也不起作用。但是,如果權限錯誤,PHP應該發出警告。 – zneak 2010-04-26 16:20:25

+0

您是否嘗試過評論「取消鏈接」這一行? (對不起,這是@Borgtex)@zneak也許他沒有看到警告/錯誤... – zaf 2010-04-26 16:22:39

+0

權限是正確的,在一次運行中,該文件被創建,然後刪除,它似乎沒有任何問題。問題是,當我在瀏覽器中運行這個文件,並讓我們說5秒後,我再次調用另一個選項卡中,第二個實例,而不是顯示警告消息(因爲第一個已經運行,該文件已被創建)再次完成整個過程。如果我創建一個名爲demo2.php的精確副本並且一個接一個地運行,它將按預期工作;演示等待10秒,demo2立即顯示警告 – Borgtex 2010-04-27 07:39:32

2

假設一個「正常,容易」的環境,不能確定你的具體情況有什麼問題,因爲它適用於我,但至少你的代碼中有競爭條件。如果你在同一時間啓動兩個進程,並且發現demo.lock不存在?

您可以使用fopenx模式來防止這種情況發生。 X模式嘗試創建文件;如果它已經存在,它就會失敗,並生成一個E_WARNING錯誤(因此閉鎖操作符)。由於文件系統操作在驅動器上是原子的,因此可以保證一次只有一個進程可以保存文件。

<?php 

$file = @fopen("demo.lock", "x"); 
if($file === false) 
{ 
    echo "Unable to acquire lock; either this process is already running, or permissions are insufficient to create the required file\n"; 
    exit; 
} 

fclose($file); // the fopen call created the file already 
sleep(10); // do some job 
unlink("demo.lock"); 
echo "Job's done!\n"; 

?> 

我在這裏測試過它,它似乎工作。

+0

+1原子測試和設置 – oedo 2010-04-26 16:28:04

+0

感謝您的建議的,我看到使用的fopen如何增加檢查安全的另一個層面。但是,我仍然有同樣的問題;這就像二審等待第一個結束和刪除文件,再次 – Borgtex 2010-04-27 07:47:06

+0

@Borgtex創建:那麼你的問題,我百思不得其解。我看不出爲什麼會失敗。 :/呃,至少我希望我有用。 – zneak 2010-04-27 22:10:05

相關問題