views:

345

answers:

3

Hello,

I've a problem with my application when an ajax call on the server takes too much time : it queue all the others queries from the user until it's done server side (I realized that canceling the call client side has no effect and the user still have to wait).

Here is my test case :

<script type="text/javascript" src="jquery-1.4.1.min.js"></script>

<a href="another-page.php">Go to another page on the same server</a>


<script type="text/javascript">
    url = 'http://localserver/some-very-long-complex-query';
    $.get(url);
</script>

So when the get is fired and then after I click on the link, the server finish serving the first call before bringing me to the other page. My problem is that I want to avoid this behavior.

I'm on a LAMP server and I'm looking in a way to inform the server that the user aborted the query with function like connection_aborted(), do you think that's the way to go ? Also, I know that the longest part of this PHP script is a MySQL query, so even if I know that connection_aborted() can detect that the user cancel the call, I still need to check this during the MySQL query... I'm not really sure that PHP can handle this kind of "event".

So if you have any better idea, I can't wait to hear it.

Thank you.


Update : After further investigation, I found that the problem happen only with the Symfony framework (that I omitted to precise, my bad). It seems that an Ajax call lock any other future call. It maybe related to the controller or the routing system, I'm looking into it.

Also for those interested by the problem here is my new test case : -new project with Symfony 1.4.3, default configuration, I just created an app and a default module. -jquery 1.4 for the ajax query.

Here is my actions.class.php (in my unique module) :

class defaultActions extends sfActions
{
  public function executeIndex(sfWebRequest $request)
  {
    //Do nothing
  }

  public function executeNewpage()
  {
    //Do also nothing
  }

  public function executeWaitingaction(){
    // Wait
    sleep(30);
    return false;
  }

}

Here is my indexSuccess.php template file :

<script type="text/javascript" src="jquery-1.4.1.min.js"></script>

<a href="<?php echo url_for('default/newpage');?>">Go to another symfony action</a>


<script type="text/javascript">
    url = '<?php echo url_for('default/waitingaction');?>';
    $.get(url);
</script>

For the new page template, it's not very relevant... But with this, I'm able to reproduce the lock problem I've on my real application.

Is somebody else having the same issue ?

Thanks.

A: 

Does it need to be aborted on the server, or do you just want the user redirected immediately?

Perhaps something like AJAXQueue would work for you? (with obvious required changes to your client-side code..)

jasonbar
A: 

Ok, I finaly figured why the application is waiting : the session system of PHP queue the other query until session is closed. So my ajax call doesn't need to use session I do a $this->getUser()->shutdown() before my action takes too long.

Every details here : http://garethmccumskey.blogspot.com/2009/10/php-session-write-locking-and-how-to.html

Remiz
A: 

Hello i have the same problem, with a similar script.

Jquery script

$.ajax({url :'/map/test1',  async:true ,complete: function(){alert("test1")}});
$.ajax({url :'/map/test2',  async:true ,complete: function(){alert("test2")}});

Symfony php

public function executeTest1()
{
 $this->getUser()->shutdown();
 usleep(10000000);
 return $this->renderText("Oki");
}

public function executeTest2()
{
 return $this->renderText("Oki");
}

When the page load, test1 requete is waiting the end usleep(10000000) but test2 is waiting test1's execution ending.

I have juste this problem with symfony.

Julien
Yes, in fact I notice that the getUser()->shutdown() was not enough to close the session for me too, I had to add a session_write_close() after. You can try this, but be sure that you don't need to access anything in the session after.
Remiz