2011-08-10 16 views
9

Googleコードサイトでコミット後のURLとして使用するindex.phpスクリプトがあります。このスクリプトはディレクトリをクローンし、何らかの作業が必要なプロジェクトをビルドします。私は、このスクリプトを複数回並行して実行することを避けたいと考えています。Apacheを介してPHPスクリプトを実行するインスタンスを1つしか持たないようにするにはどうすればよいですか?

もう1つは既にセッション中であれば、そのスクリプトの実行を避けるために使用できるメカニズムはありますか?

答えて

21

あなたは、ファイルの排他的ロックを獲得するためにLOCK_EXflockを使用することができますスクリプトは、あなたがこのような何かを行うことができます実行している場合は、保存するために例えば

。手動 群れ($ fpは、LOCK_UN)を使用してロックを解除する必要がある5.3.2の後にPHPのバージョンについては

例えば:

<?php 
$fp = fopen('/tmp/php-commit.lock', 'r+'); 
if (!flock($fp, LOCK_EX | LOCK_NB)) { 
    exit; 
} 

// ... do stuff 

fclose($fp); 
?> 

+0

これまでのところ、flock()を使用したことはありません。 – powtac

+0

@LongEarsこのコードでは、 'LOCK_NB'は' flock'のPHPマニュアルに従って動作しないので、実際にはWindows上で別のインスタンスを実行します。前のインスタンスが終了するまで 'flock'を待ってからコード全体を実行します。 –

+0

また、期待どおりに動作するようにするには、fopenモードを次のように変更することをお勧めします。 '$ fp = fopen( '/ tmp/php-commit.lock'、 'c'); ' 'r +'を使用すると、commit.lockファイルが存在しない場合にPHPエラーが発生します。 – DoctorFox

1

実行中のスクリプトの状態を保存し、他のスクリプトが現在アクティブな場合にスクリプトがいつ起動するかを確認した場合のみ。

$state = file_get_contents('state.txt'); 

if (!$state) { 
    file_put_contents('state.txt', 'RUNNING, started at '.time()); 

    // Do your stuff here... 

    // When your stuff is finished, empty file 
    file_put_contents('state.txt', ''); 
} 
1

実行にはどれくらい時間がかかりますか。タスクは、あなたがmemcacheのからクリアする必要があります。失敗した場合

はmemcacheの

<?php 
$m = new Memcache(); // check the constructor call 

if($m->get('job_running')) exit; 

else $m->set('job_running', true); 



//index code here 

//at the end of the script 

$m->delete('job_running'); 

?> 

を使用することができます。群れも良い選択肢です...実際にはおそらくもっと良いでしょう。

+1

タスクの失敗時に手動でクリアするのを避けるために、タスクの実行時間のいくつかの上限に応じて、時間制限を使用することができます。 – Noam

関連する問題