I have a basic chatbox module on my website which is updating the chatbox every 3 seconds with Jquery Ajax call, plus another jquery call for sending new message. Nothing fancy. Normally each jquery ajax request takes only 0.2seconds. But on the server when 20+ people is connected server CPU goes very high and each ajax request starts to take 12-14 seconds, which is not acceptable. And also each httpd process consumes 3% – 4% CPU.
Update chatbox code:
updatechatbox = $.getJSON("/chat/update",{ lastid: $("#messageBox li:last-child").attr("id") }, function(json) {
$.each(json, function(key, val) {
var m = val['message'];
var id = val['id'];
var messagebox = $("#messageBox ul");
messagebox.append("<li id="+id+"><span class='msg'>"+m+"</span></li>");
var myDiv = $("#messageBox");
myDiv.animate({ scrollTop: myDiv.prop("scrollHeight") - myDiv.height() }, 0);
});
});
Server is Fedora 15 running nginx as proxy and apache for web service with following configuration:
Timeout 120
KeepAlive On
MaxKeepAliveRequests 100
KeepAliveTimeout 15
IfModule prefork.c
StartServers 8
MinSpareServers 5
MaxSpareServers 20
ServerLimit 256
MaxClients 256
MaxRequestsPerChild 400
IfModule
IfModule worker.c
StartServers 2
MaxClients 150
MinSpareThreads 25
MaxSpareThreads 75
ThreadsPerChild 25
MaxRequestsPerChild 0
IfModule
Questions:
– Is this normal that apache using that much CPU for each httpd process?
– How can i fix this?
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
20089 apache 20 0 57524 16m 5840 S 7.3 0.8 0:18.16 httpd
19715 apache 20 0 56828 16m 5852 S 6.6 0.8 0:21.58 httpd
19749 apache 20 0 58536 16m 5864 S 6.6 0.8 0:22.29 httpd
19732 apache 20 0 62880 21m 5856 S 5.6 1.0 0:19.14 httpd
19803 apache 20 0 62076 21m 5840 S 5.3 1.1 0:17.94 httpd
19821 apache 20 0 61856 21m 5828 S 5.0 1.0 0:17.81 httpd
21574 apache 20 0 61584 18m 4664 S 3.3 0.9 0:00.69 httpd
19772 apache 20 0 61856 21m 5864 S 2.6 1.1 0:18.53 httpd
19932 apache 20 0 61856 20m 5844 S 2.6 1.0 0:17.07 httpd
14307 mysql 20 0 306m 52m 4576 S 2.3 2.6 81:32.57 mysqld
13175 nginx 20 0 15532 2284 1032 S 0.3 0.1 0:04.61 nginx
Edit: My PHP update function. Using Zend Framework v1.11.11
public function updateAction()
{
$auth = Zend_Auth::getInstance();
$user_info = $auth->getStorage()->read();
$adminsess = new Zend_Session_Namespace("admin");
$referrer = $_SERVER['HTTP_REFERER'];
$user_id = $user_info->id;
$query = "SELECT m.id, m.message, m.user_id
FROM messagebox m
LEFT JOIN users u ON m.user_id = u.id";
if(isset($_GET['lastid']) && $_GET['lastid'] != ""){
$lastId = $_GET['lastid'];
$query .= "WHERE m.id > $lastId";
}
$r = $db->query($query);
$result = $r->fetchAll();
$data = array();
if(count($result) > 0) {
foreach($result as $row) {
$data[$row['id']]['id'] = $row['id'];
$data[$row['id']]['message'] = $row['message'];
$data[$row['id']]['user_id'] = $user_id;
}
}
echo json_encode($data);
$this->_helper->layout->disableLayout();
}
I have had a similar problem before and it turned out to be to do with session locking. When a session is opened by the PHP script that starts the session this session file is locked. What this means is that if your web page makes numerous requests to PHP scripts, for instance, for loading content via Ajax, each request could be locking the session and preventing the other requests from completing. This is described in detail here.
Therefore you will need to do:
If this isn’t the cause check you are not doing anything computationally intensive like, big SQL calls lots of recursion etc.