Can someone lead me down the right way to make a live notifications
e.g Knowing when a new Row in Added in Mysql
know if a php file has changed ???
how should i go about it?
You could routinely check the server for updates using setInterval(), or you could employ long-polling with javascript. The benefit of setInterval() is that it doesn't keep connections opened on your server for too long, but you may have updates during the 'downtime' between server-calls. Long-polling will give you near-instant updates, as it waits with the connection opened until it receives new information. But obviously, the down side is that you've got connections staying opened all over the place.
Routine Checks...
setInterval(function(){
$.get("updates.php", {}, function(results){
if ($(results).length) {
$("results").each(function(){
// do something with update messages
});
}
});
}, 30000); // Every 30 seconds.
Long Polling with PHP/jQuery Example:
You can find an example of long polling with PHP and jQuery at http://blog.perplexedlabs.com/2009/05/04/php-jquery-ajax-javascript-long-polling/
You can use db triggers to watch for changes in certain tables and insert notification data into a new table. Then. query that db table periodically with Jquery and ajax.
Workflow:
Create trigger that watched table users for inserts, updates, and deleted
Once users is altered, the trigger inserts a new record into notifications detailing what was changed
Using a periodical updater, check the notifications table for new records and display them to the user.
This simple workflow might not be as easy to implement as you would hope but it would get the job done in an efficient manner.
Related
For some reasons (that I think it is not the point of my question, but if it help, ask me and I can describe why), I need to check MySQL tables continuously for new records. If any new records come, I want to do some related actions that are not important now.
Question is, how I should continuously check the database to make sure I am using the lowest resources and getting the results, close to the realtime.
For now, I have this:
$new_record_come = false;
while(! $new_record_come) {
$sql = "SELECT id FROM Notificatins WHERE insert_date > (NOW() - INTERVAL 5 SECONDS)";
$result = $conn->query($sql);
if ($result)
{
//doing some related actions...
$new_record_come = true;
}
else
{
sleep(5); //5 seconds delay
}
}
But I am worry that if I get thousands of users, it will make the server down, even if the server is a high price one!
Do you have any advice to make it better in performance or even change the way completely or even change the type of query or any other suggestion?
Polling a database is costly, so you're right to be wary of that solution.
If you need to scale this application up to handle thousands of concurrent users, you probably should consider additional technology that complements the RDBMS.
For this, I'd suggest using a message queue. After an app inserts a new notification to the database, the app will also post an item to a topic on the message queue. Typically the primary key (id) is the item you post.
Meanwhile, other apps are listening to the topic. They don't need to do polling. The way message queues work is that the client just waits until there's a new item in the queue. The wait will return the item.
A comment suggested using a trigger to invoke a PHP script. This won't work, because triggers execute while the transaction that spawned them is not yet committed. So if the trigger runs a PHP script, which probably needs to read the record from the database. But an uncommitted record is not visible to any other database session, so the PHP script can never read the data that it was notified about.
Another angle (much simpler than message queue I think):
I once implemented this on a website by letting the clients poll AND compare it to their latest id they received.
For example: You have a table with primary key, and want to watch if new items are added.
But you don't want to set up a database connection and query the table if there is nothing new in it.
Let's say the primary key is named 'postid'.
I had a file containing the latest postid.
I updated it with each new entry in tblposts, so it contains alsways the latest postid.
The polling scripts on the clientside simply retrieved that file (do not use PHP, just let Apache serve it, much faster: name it lastpostid.txt or something).
Client compares to its internal latest postid. If it is bigger, the client requests the ones after the last one. This step DOES include a query.
Advantage is that you only query the database when something new is in, and you can also tell the PHP script what your latest postid was, so PHP can only fetch the later ones.
(Not sure if this will work in your situation becuase it assumes an increasing number meaning 'newer'.)
This might not be possible with your current system design but how about instead of using triggers or a heartbeat to poll the database continuously that you go where the updates, etc happen and from there execute other code? This way, you can avoid polling the database continuously and code will fire ONLY IF somebody initiates a request?
Current situation: I have a web page that uses AJAX/JQUERY to refresh all the content on the page every 17 seconds. Every time this happens the server queries the database for data from two tables, one of which is large (450MiB in size, 11 columns) and processes all the data.
This is too resource intensive. I want:
The server queries the database only when one of the two tables have changed.
The page then reloads the page through AJAX only when the tables have been updated and the server has re-processed the data.
I think this falls under the category of comet programming. I'm not sure.
2 is easy. The webpage calls 'update.php' every 17 (or maybe less) seconds. The PHP script returns no data if no changes have been made. Only if data is returned then the current page is replaced with the new data. Please advise me if there is a better way.
As for 1 my googling tells that every time one of my two tables is updated I can put a notification in a table (or maybe just a single byte in a file) to indicate that I must query the database again and then the next time that the webpage sends an AJAX request I return the data.
The problem is that I'm working with a rather large code base I didn't write and I don't know of all the places that either of the two tables may be updated. Is there an easier way to check when the database is modified.
I'm working with PHP, Apache, Drupal and MYSQL.
You can chekout Server Sent Events
A server-sent event is when a web page automatically gets updates from a server.
there is an excellent article on HTML5rocks.com - Server Sent Events
All You have to do is create an object
var source = new EventSource('xyz.php'); //Your php files which will return the updates.
Once you create an object,you can listen to the events
source.addEventListener('message', function(e) {
console.log(e.data);
}, false);
I'm thinking about a webchat working with PHP, JQuery and MySQL but I'm in some trouble about how the queries should be send to the db.
Structure:
MySQL receives all data from chat and saves it like in a table "conversation" with columns from/to.
Jquery do the queries and verifies if there is any new message for the current user.
Problem:
How to do the queries with Jquery in a way to not overload the db server (in consideration to have a lot of users)? I think to query the db with a timer in Jquery, so within some secs. a new query will be done and it will be repeated for all users at same time.
The best way to do it (according to me) is to have a 1 second interval in jquery. Once a second you call a php file (fetch_new.php for example).
In your database, you have two tables:
users
messages
When a user client makes a call to fetch_new.php (through JavaScript), you update the users table and set a column (last_sync) to the current time (preferably in microtime, that way the user will never get two of the same messages sent to them). The new message(s) get appended to the conversation.
When you execute your query, it should look something like this:
SELECT * FROM `messages` WHERE `to` = $user_id AND `timestamp` > $last_sync
It is perfectly fine to send many questions per second to MySQL as long as it can handle many connections (enough RAM and CPU). Keep an eye on the "Status" tab in PHPMyAdmin to see how much CPU and RAM is being used.
In the chat applications I've built I've added some "intelligence" features. If a user hasn't received any messages in the last (let's say) 20 seconds, I increase the interval to make a request to fetch_new.php every 2 seconds instead of every second. If over a minute has passed, I increase it to 3 seconds and so on. This way you won't slow down your application by having a lot of idle users.
my approach would be something like:
$(document).ready(function()
{
setTimeout(function()
{
// do something here
}, 2000);
});
The above code will execute your function every 2 seconds. Don't know about efficiency though. So perhaps another approach would work better.
I am trying to integrate node.js app into an existing PHP/MySQL system. node-mysql is used to allow node.js to access the MySQL database. A table named tableA in the MySQL database updates with new data every 10 minutes.
Problem: Using node, I need the node server to continuously check tableA for changes whenever tableA gets updated. What is a good way to achieve this?
I am thinking if I used setInterval(checkDb(tableA), 10*60*1000), or an infinite loop, the checkDbquery function may not coincide with the database update.
I also happen to be using socket.io so will a good method be for the PHP system to emit('dbUpdated') to the node server if it is even possible for PHP to send a message to node.js?
Node Code
var dbCheckQueue = function(callback) {
client.query('SELECT * from tableA',
function(error, results, fields) {
if error
throw error;
callback(results);
});
}
// 10mins-interval checking of table
setInterval(function() {
dbCheckQueue(function(results) {
console.log('Fresh meat!')
});
}, 10*60*1000);
Ideally you would trigger the event from the where ever the update is being made from after completion.
Since you are using sockets you could create an "Events" connection or similar (authenticate or some other method to indicate it is connecting to trigger an event) which would connect to your socket and trigger an update and disconnect. This could be called from anywhere regardless of platform as long as you are able to create the connection. Once connected the script would send whichever command you want to be triggered and disconnect/finish the updating process.
You could either do this directly from where the update is made or setup a trigger on mysql with sys_exec() to execute another script which does the same as above.
I am trying to create a live orders page for my website. I need the page to auto-update to show that a new order has been placed and to display an alert/sound whenever a new order row is in the database.
Any ideas on how i can easily achieve this?
Thanks,
-AJay
You will need to use something like Comet to be able to push data to the client.
Then, use a MySQL trigger to somehow raise an event in your server application that's holding the Comet connection open to push the appropriate data.
The less elegant way that many developers use (at least until WebSockets become popular) is to poll with AJAX for changes, but this has a high bandwidth overhead and a longer latency.
From AJAX view you should use timers in javascript like this...
// First parameter is an expression and second is a interval as miliseconds.
setTimeout ( "UpdateFunction()", 2000 );
Also i recommended to you use this code...
setTimeout ( "UpdateFunction()", 5000 );
function UpdateFunction( )
{
// (do something here)
setTimeout ( "UpdateFunction()", 5000 );
}
your UpdateFunction() should call a php or asp page which renew list of orders.
I would think a polling approach would do you well, as server push has many negative implications for the browser.
If going with a polling-route, I would suggest having a timed event occur on your page that will call a web method. The web method would then return data (something small like an ID) about queued orders. Compare the list of IDs to what's currently fleshed out on the page, and assuming you have something in the newly given list that doesn't exist (or vice versa), call a separate method to retrieve the additional details to display display new orders from or delete old entries.
This way, you do not need to keep a steady stream to the server (which can block the user's browser from making additional content requests).
I hope that helped at all.