2015-10-15 68 views
1

我正在使用PHP在我的服務器上開發一些apis。我有一個腳本,用於查詢數據庫,並且在查詢結果的某些邏輯之後,如果需要,它會更新數據庫中的另一個表。每當有新的特定api請求時,都會執行此腳本。跨會話執行php腳本,請求和範圍之外

我的目標是在腳本開始時設置一個布爾值== true,並且腳本結束時將其重置爲false。因此,所有新的請求都可以讀取布爾值並僅在布爾值== false時啓動腳本。否則,腳本將不會從這個請求中執行,這對我的目的非常有用。

我知道,在PHP中的靜態變量保持他們只在當前範圍和會話變量值只能在同一會話持久性,但應該有辦法做到這一點。

我的第一個解決方案是寫在服務器上(或數據庫)txt文件更新布爾值當腳本開始/結束和啓動腳本之前閱讀。我沒有測試過,但如果有很多請求,txt文件(或數據庫行)可以同時更多的請求異步更新,因爲當一個請求設置爲true時,布爾值,另一個請求可能已經讀取該值並再次運行腳本。

的也許不是布爾我會保存日期或時間戳,所以用一些邏輯的腳本只有

(last execution timestamp + 5 minutes) < now() 

是否有實現這個解決方案被執行? 感謝

+0

在計算機科學方面......「讀一個表,並更新另一個」是關鍵的部分。你想獨家訪問它。但是,如果進程(會話)無法訪問,則不希望它們被阻止。這個問題是一個競爭條件。 PHP有這個問題的解決方法。見雞羣功能。您想要使用選項LOCK_EX | LOCK_NB進行非阻塞鎖定。 – kainaw

+1

直接在MySQL表上寫入鎖定可能會更好(假設您使用的是MySQL)。請參閱:https://dev.mysql.com/doc/refman/5.7/en/lock-tables.html – Mike

回答

3

使用羊羣。在獨佔/非阻塞狀態下,當且僅當您的進程具有獨佔鎖時,纔可以執行代碼。

$lock = fopen('/var/tmp/your.lock', 'a'); 
if (flock($lock, LOCK_EX|LOCK_NB)) { 
    // Do your read/update stuff 
    flock($lock, LOCK_UN); // Release the lock 
} 

這樣可以避免競爭條件,讓您獨佔訪問讀取/寫入所需的數據。但是,涉及的每個腳本都必須使用相同的鎖定文件。

編輯:基於下面的評論,我確信,說明你需要解除鎖定。

+0

我是否應該用flock($ lock,LOCK_UN)或此實現版本文件本身釋放鎖定? – lubilis

+0

是的!如果您不釋放鎖定,則沒有其他人可以使用它。現在編輯答案... – kainaw