PHP Semaphore Example

How to use semaphone with PHP

PHP Semaphore ExampleSemaphore is a protected variable that can be used to control access to a resource. I’ve used a semaphore to prevent a PHP script from running simultaneously. For example I have a PHP script that runs every Tuesday to process a weekly newsletter. This script first selects a list of recipients to send. The script then sends each recipient a copy of the newsletter. The list is more than 10,000 subscribers and each subscriber is processed individually in order to customize the newsletter content. As each subscriber is processed the script updates the database for that subscriber with a last sent date of today. If the script runs a second time the subscribers will not be selected since they were updated with a last sent date of today. However if the script is run a second time before the first instance completes the initial list is repopulated and the newsletter is sent twice. To prevent the script from running simultaneously I use a semaphore to “lock” the process.

Semaphore usage is pretty straight forward. There are 4 functions:

  • sem_acquire() – Attempt to acquire control of a semaphore.
  • sem_get() – Creates (or gets if already present) a semaphore.
  • sem_release() – Releases the a semaphore if it is already acquired.
  • sem_remove() – Removes (deletes) a semaphore.

The following pared down script shows a basic example usage of a semaphore to lock the script and prevent it from running simultaneously.

<?php

// exclusive control
	$semaphore_key = 2112;		// unique integer key for this semaphore (Rush fan!)
	$semaphore_max = 1;		// The number of processes that can acquire this semaphore
	$semaphore_permissions = 0666;	// Unix style permissions for this semaphore
	$semaphore_autorelease = 1;	// Auto release the semaphore if the request shuts down
 
// open a new or get an existing semaphore
	$semaphore = sem_get($semaphore_key, $semaphore_max, $semaphore_permissions, $semaphore_autorelease);
	if(!$semaphore) 
	{
		echo "Failed to get semaphore - sem_get().\n";
		exit();
	}

// acquire exclusive control - wait for semaphore availability	
	if (sem_acquire($semaphore, false))
	{

// get the MySQL result set of recipients ($result) - omitted for readability

// bail if no one to process - double run
		if (count($result) == 0)
		{
			echo "Zero members to process - cancelling";
			// release exclusive control	
			sem_release($semaphore);
			exit();
		}

// process members
		if (count($result) > 0)
		{
			foreach ($result as $row)
			{
				// send the newsletter - omitted for readability
			}
		}

// release exclusive control	
		sem_release($semaphore);

	} // semaphore acquired

?>

Copy Code

References

PHP Semaphore
PHP if
PHP echo
PHP count
PHP foreach
PHP exit

4 Replies to “PHP Semaphore Example”

  1. This does not work! You’re checking if the resource to the semaphore is set, which is always true, even though the process is already running. You need to check if you can actually get the resource…

    so: if( !sem_aquire( $semaphore, true )) exit( “we’re already running” );

    if you set the ‘true’ to ‘false’ the process will wait until the semaphore is released by the running process before it continues, if set to true is will return false immediately if the semaphore is already aquired

    1. Patrick, you are correct and thank you for your feedback. I have updated the code snippet to reflect testing the semaphore acquisition.

  2. Attention all planets of the Solar Federation
    Attention all planets of the Solar Federation
    Attention all planets of the Solar Federation
    We have assumed control
    We have assumed control
    We have assumed control

Leave a Reply

I appreciate and welcome your comments. Please keep in mind that comments are moderated according to my comment policy.
Your email address will not be published. Required fields are marked *