Monday, August 6, 2012

How to deal with asynchronous request with Symfony2 and other PHP frameworks

As well as most of PHP frameworks, Symfony2 manages user session by locking it during request treatment. It avoids concurrent access to session file but makes requests to be queued until session lock is freed...

This behaviour is really well explained in this post from Gareth McCumskey.

As Gareth describes his solution, we need to manually free session lock after all session modifications happen in the request treatment. Here is a pattern for controllers that handle AJAX calls (solution provided by Matt on stackoverflow) :

<php

    // ...

    public function myControllerAction()
    {
        //Actions that modify session
        // ...
     
        //We free session lock as no more session modifications will happen in next actions !
        $session = $this->get('session');
        $session->save();
        // session_write_close(); // Only required before Symfony 2.1
     
        //Actions that don't modify session
        // ...
     
        $this->return('...');
    }

Here is the result for an action that process a 10 seconds sleep() :
Before :
After :

8 comments :

Stéphane Lagrange - Dev said...

AHAH ! Thank You !

Jérôme Tam said...

You should not call the PHP function directly, but instead use the session service :

$this->get('session')->save();

AlterPHP said...

You're right. This article has been written for Symfony 2.0 and that call was not processed with this former version of Symfony. I updated the post, thanks for info !

Unknown said...

is it work on symfony3?

AlterPHP said...

This behaviour seems PHP framework agnostic, so I guess yes, this is the same with Sf3... Did you try ?

fuad suyudi said...

i'm using sf3, and not work for me
any idea?

AlterPHP said...

What does not work ?

R. Arfa said...

Tahnk you , this was the solution to my stream videos. I save the video name in the session to protect video name in the Tag. The Player Tracking event was sent via ajax but the session lock prevent any ajax call. the save() method during streaming was the solution. Tahnk you again:

$vid= $request->query->get('vid');
$video_name_mp4 = $session->get($vid);
$session->save();
//then stream video using the name

Post a Comment

Comments are moderated before being published.