I have a big problem to make a progress bar in AJAX. The whole page is in AJAX, inside one of the webpage is AJAX which loads a function to get some big rows from the database.
I tried to make progress bar in this script in a foreach loop a flush() method and by writing/reading to $_SESSION, but still nothing. I really tried everything I don`t know how to do this. Need only this to complete my project. Could someone help me with this?
It is anyway which script I want to load, how is the template for this progress bar to use it in GET or POST ajax, for any AJAX.
<script>
jQuery(document).ready(function($) {
$(document).on('click','#save',function () {
setTimeout(getProgress,1000);
$(this).text('Pobieram analizę...');
$.urlParam = function(name){
var results = new RegExp('[\?&]' + name + '=([^&#]*)').exec(window.location.href);
if (results==null){
return null;
}
else{
return decodeURI(results[1]) || 0;
}
}
var id = $.urlParam('id');
var idt = $.urlParam('idt');
$.ajax({
url: "views/getresults.php?id="+id+"&idt="+idt,
success: function(data) {
$("#loadresults").append(data);
}
});
setTimeout(getProgress,3000);
return false;
});
function getProgress(){
$.ajax({
url: 'views/listen.php',
success: function(data) {
if(data<=100 && data>=0){
console.log(data);
$('#loadresults').html('<div id="progress"><div class="progress-bar" role="progressbar" style="width:'+ (data / 100)*100 +'%">'+ data + '/' +100+'</div></div>');
setTimeout(getProgress,1000);
console.log('Repeat');
} else {
$('#loadresults').text('Pobieram dane');
console.log('End');
}
}
});
}
});
</script>
and here is a getresults.php
foreach($result as $resul) {
$count++;
session_start();
$_SESSION['progress'] = $count;
$_SESSION['total'] = 100;
session_write_close();
sleep(1);
}
unset($_SESSION['progress']);
and a get progress function listen.php
<?php
session_start();
echo (!empty($_SESSION['progress']) ? $_SESSION['progress'] : '');
if (!empty($_SESSION['progress']) && $_SESSION['progress'] >= $_SESSION['total']) {
unset($_SESSION['progress']);
}
?>
Writing and reading session doesn't work because the standard behavior of PHP is to lock the session file while your main code is being executed.
Try to create a file and update the its content with the percentage done during the execution of your function. Something like:
<?php
function slowFunction() {
$file = uniqid();
file_put_contents($file, 0);
// Long while that makes your stuff
// you have to know how many loops you will make to calculate the progress
$total = 100;
$done = 0;
while($done < $total) {
$done++;
// You may want not to write to the file every time to minimize changes of being writing the file
// at the same time your ajax page is fetching it, i'll let it to you...
$progress = $done / $total;
file_put_contents($file, $progress);
}
unlink($file); // Remove your progress file
}
?>
You can't get the progress of the data download from ajax. Once you request you to the server, the next response will be only after fetching the data or when the error occurs.
The solution to you is, get the data as fractions. Such as first download the 1/10th of the data, and in the success callback, recursively call the ajax again requesting the 2/10th data. On each success callback, you could change the progress bar.
Take a look at Server Side Events or Long polling as options
Related
I designed a site that gets news from another site's RSS and saves it to my DB. To do this I must send request to another site and save changes to my DB.
this is my code for sending request:
$q = $d->query("select * from site_setting where id=1");
$setting = $d->fetch($q);
$start = $setting['last'];
$q = $d->query("select *from newsagency order by id limit ".$start.",1");
while($agency = $d->fetch($q)){
$url = $agency['link'];
$size = 20;
$agencyId = $agency['id'];
$time = time();
RSS_RetrieveLinks($url);
if($size > 0)
$recents = array_slice($RSS_Content, 0, $size + 1);
$MaxTime = $d->getrowvalue("time","select `time` from news where agency={$agencyId} order by time DESC limit 0,1",true);
foreach($recents as $article)
{
$articleTime = strtotime($article["date"]);
if($articleTime > ($MaxTime+1)){
$d->iquery("news",array(
'title'=>htmlspecialchars($article["title"]),
'time'=>$articleTime,
'link'=>$article["link"],
'type'=>$article["type"],
'img'=>$article["media"],
'regTime'=>$time,
'agency'=>$agencyId
));
$return .= $article['title']."<br>";
}
}
}
$last = $start +1;
$agencyCount = $d->getrowvalue("agenC","select count(id) as agenC from newsagency",true);
$agencyCount--;
if($last>$agencyCount) $last = 0;
$d->uquery("site_setting",array('last'=>($last)),"id=1");
this code gets rss link one by one from db and then gets data from rss and saves it to db, and everything in OK. to refresh the php page, we have a code like this :
<script type="text/javascript">
$(document).ready(function() {
$.ajaxSetup({ cache: false }); // This part addresses an IE bug. without it, IE will only load the first number and will never refresh
setInterval(function() {
$.ajax({
url: "load.php",
context: document.body,
success: function(vars){
document.getElementById("imge").innerHTML+=vars;
}
})
}, 500);
});
</script>
</head>
<body dir="rtl">
<div id="imge"></p>
</body>
I refresh this code every 500 ms and get content from rss. The problem is that this page must forever be open and I don't have any idea to solve this problem. How can I send this request without getting the client's computer busy?
I'm currently using this code on my webpage:
<?php
$url = "https://www.toontownrewritten.com/api/invasions";
$data = json_decode(file_get_contents($url));
if (!empty($data->invasions)) {
echo "<h1 style='text-align:center;margin:auto;padding:2px;font-size:16px;font-weight:bold;text-decoration:underline;padding:2px;'>Invasion Tracker</h1>";
$i = 0;
foreach($data->invasions as $title => $inv) {
print "<h3 style='text-align:center;margin:auto;'><b>District:</b> {$title}
</h3><br style='font-size:1px;'><h3 style='text-align:center;margin:auto;'><b>Cog:</b> {$inv->type}
</h3><br style='font-size:1px;'><h3 style='text-align:center;margin:auto;'><b>Progress:</b> {$inv->progress}
</h3>";
if (count(($data->invasions) > 1)) {
if (end($data->invasions) !== $inv) {
print "<hr>";
} else {
print "<br style='font-size:2px;'>";
}
}
}
} else {
echo "<h1 style='text-align:center;margin:auto;padding:2px;color:darkred;font-weight:bold;'>No invasions!</span>";
}
?>
I'm looking to make it refresh every 10 seconds via AJAX. However, I keep reading you need to make a function, but I'm not sure how I'd do that with the API? Every 10 seconds, that API is being updated, which is why I'd like this to be updated with AJAX every 10 seconds. Currently, I have it so the user has to manually refresh. Any help is appreciated!
You can simply reload the page with the method proposed here
But if you wanna have an AJAX implementation which just refereshes a part of your html nice and tidy, You gonna have to
Almost forget your PHP code
use the following code to implement the request to the url
$.ajax({
url: "https://www.toontownrewritten.com/api/invasions",
})
.done(function( data ) {
if ( console && console.log ) {
console.log( data );
}
});
Make a JS code which would convert the data got in the previous section to a readable html and show it on your page. It should be implemented in the the block where console.log(data) is.
Put that part of code in a setInterval
setInterval(function(){
//$.ajax();
}, 10000);
And be aware that you are gonna go to hell if your request doen't complete in the interval. see this .
I have a better suggestion, again it is same as using setInterval.
setInterval(function () {
if (isActive) return; // so that if any active ajax call is happening, don't go for one more ajax call
isActive = true;
try {
$.ajax("URL", params,function() { isActive = false;//successcallback }, function () {
isActive = false; // error callback
});
} catch (ex) { isActive = false;}
}, 10000);
Your problem is a failure to understand AJAX. Below is a $.post() example.
First let's make the page that you want your Client (the Browser user) to see:
viewed.php
<?php
$out = '';
// you could even do your initial query here, but don't have to
?>
<!DOCTYPE html>
<html xmlns='http://www.w3.org/1999/xhtml' xml:lang='en' lang='en'>
<head>
<meta http-equiv='content-type' content='text/html;charset=utf-8' />
<style type='text/css'>
#import 'whatever.css';
</style>
<script type='text/javascript' src='//ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js'></script>
<script type='text/javascript' src='whatever.js'></script>
</head>
<body>
<div id='output'><?php /* if initial query took place */ echo $out; ?></div>
</body>
</html>
Now you need your JavaScript in whatever.js.
$(function(){
function getData(){
$.post('whatever.php', function(data){
// var htm = do a bunch of stuff with the data Object, creating HTML
$('#output').html(htm);
});
}
getData(); // don't need if PHP query takes place on original page load
setInterval(getData, 10000); // query every 10 seconds
});
On whatever.php:
<?php
// $assocArray = run database queries so you can create an Associative Array that can be converted to JSON
echo json_encode($assocArray);
?>
The JSON generated by PHP shows up in the data argument, back in the JavaScript that created your PHP request:
$.post('whatever.php', function(data){
Im trying to do near real time graph update within my site. To do this im trying to basically reload a php file every 30 seconds. I made the data of PHP dynamically echo out json code as shown below. Ad inside the file is also <meta http-equiv="refresh" content="30"> which refreshes the file to recheck database.
{"todayCalculateCR":"5%"}{"todayEPC":"0.20"}{"todayCTR":"34%"}{"yesterdayCalculateCR":"35%"}{"yesterdayEPC":"0.03"}{"yesterdayCTR":"24%"}{"monthCalculateCR":"14%"}{"monthEPC":"0.07"}{"monthCTR":"24%"}
Basically now i want some jquery code to place on my index.php page to load this file, interpret the json code and append the data to the correct divs.
Example:
<div class="yesterdayEPC">0.03</div>
Ive been looking on jquery.com and on stack overflow for ways to basically take the above json data and append it.
$.get( "dashboard-stats.php", function( data ) {
$( "body" )
.append( "yesterdayEPC: " + data.yesterdayEPC ) // John
.append( "Time: " + data.yesterdayEPC ); // 2pm
}, "json" );
This is brief of PHP file making json:
$month_visits = mysql_num_rows(mysql_query("SELECT * FROMlocker_reportsWHEREuid= '$user_id' ANDmonth= '$month_date'"));
$month_clicks = mysql_num_rows(mysql_query("SELECT * FROMreportsWHEREuid= '$user_id' ANDmonth= '$month_date' ANDstatus= '1'"));
$month_leads = mysql_num_rows(mysql_query("SELECT * FROMreportsWHEREuid= '$user_id' ANDmonth= '$month_date' ANDstatus= '2'"));
if($month_leads == "" || $month_clicks == "")
{
echo json_encode(array("monthCalculateCR"=>"n/a"));
echo json_encode(array("monthEPC"=>"n/a"));
}
else
{
$monthCalculateCR = number_format($month_clicks / $month_leads)."%";
echo json_encode(array("monthCalculateCR"=>"".$monthCalculateCR.""));
$monthEPC = number_format($month_leads / $month_clicks, 2)."";
echo json_encode(array("monthEPC"=>"".$monthEPC.""));
}
if($month_visits == "")
{
echo json_encode(array("monthCTR"=>"n/a"));
}
else
{
$monthCTR = number_format($month_clicks / $month_visits, 2) * 100 . "%";
echo json_encode(array("monthCTR"=>"".$monthCTR.""));
}
Try with the setTimeout function to call the $.get() jQuery method to recall the php file that echos the JSON.
reload();
function reload(){
$.get( "yourFile.php", function( data ) {
//update table based on data
var jsonData = $.parseJSON(data);
$('#myDiv').append('callback called').append(data);
});
setTimeout(reload, 30000);
}
I fixed my problem by basically making the json in 1 bracket.
Then using a tutorial I found out I can do below.
Todayclicks: <span id="clicks">
<script>
var JSONObject = {"todayEarnings":"2.60","todayVisits":"62","todayClicks":"26","todayLeads":"3","todayCalculateCR":"9%","todayEPC":"0.12","todayCTR":"42%","yesterdayEarnings":"0.40","yesterdayClicks":"35","yesterdayVisits":"148","yesterdayLeads":"1","yesterdayCalculateCR":"35%","yesterdayEPC":"0.03","yesterdayCTR":"24%","monthEarnings":"3.00","monthClicks":"65","monthVisits":"242","monthLeads":"4","monthCalculateCR":"16%","monthEPC":"0.06","monthCTR":"27%"}
document.getElementById("clicks").innerHTML=JSONObject.todayClicks;
</script>
I have a web application that use notification to inform user about anything new (just like Facebook).
My solution is that I send a request every three seconds to check the database if there is anything new to display (jQuery and AJAX). However, this makes the application slow, since a request is sent to check tables every three seconds.
I want to know how to make these notifications work without interrupting the application.
So this is my JS code:
jQuery(document).ready(function(){
LoopNotificationCRM();
});
function LoopNotificationCRM(){
setTimeout('LoopNotificationCRM();',3000);
$.ajax({
async: false,
type: "POST",
url: "controllers/c_ajax_notification.php",
data: "ordre=check_new_notification",
success: function(msg){
if(msg != 'NAN'){
var t = msg.split('***');
$('.sNotification').html(t[0]);
$('.ul-notification').html(t[1]);
$('.alert-notification').css('display','block');
}else{
$('.sNotification').html(0);
$('.alert-notification').css('display','none');
$('.ul-notification').html('');
}
},
error: function (xhr, status) {
alert('Erreur: ' + status);
}
});
}
And this is my PHP Code:
$notification->getNewNotification("*");
if($notification->db_num_row != 0){
$listNoti = '';
while($resN = $notification->fetch_array()){
$today = new DateTime(date('Y-m-d H:i:s'));
$datNoti = new DateTime($resN['date_not_crm']);
$diff = $datNoti->diff($today);
if($diff->d == 0){
if($diff->h == 0){
if($diff->i == 0){
$intervale = 'il y a '.$diff->s.' sec';
}else{
$intervale = 'il y a '.$diff->i.' min';
}
}else{
$intervale = 'il y a '.$diff->h.' heure(s)';
}
}else{
$intervale = 'il y a '.$diff->d.' jour(s)';
}
$listNoti .= '<li>
<a onclick="link(event,\''.$resN['url_not_crm'].'\');updateEtatNoti(this,'.$resN['id_not_crm'].');" style="cursor:pointer;">
<span class="label label-icon label-success"><i class="'.$resN['icon_not_crm'].'"></i></span>
'.$notification->csNotification($resN['description_not_crm']).'
<span class="time">'.$intervale.'</span>
</a>
</li>';
}
echo $notification->getCountNewNotification().'***'.$listNoti;
}else{
echo 'NAN';
}
When I remove the notification code my application become more fast !
If your application is slowing down when you run the ajax every 3 seconds, try simplifying/shrinking the amount of work the page loaded by the ajax needs to do. Rather than reading an entire table, for example, try selecting only notifications with a "read" status of 0. That way, the .php file is faster to execute, meaning the ajax will not slow down the page as much.
To simplify the problem, all I want is passing 3 variable from javascript to PHP. So let say I have 4 varible : a,b,c,message.
I have tried the following ways:
1)The code below is in my javascript file
window.location.href="somewebsite.php?x=" + a + "&y=" + b + "&z=" + c + "&msg=" + message;
I saw that it actually passing the values to URL, it jump to the PHP website that specifies in the code above but somehow nothing is getting from $_POST['x'] ( I even try $_GET['x'] and $_REQUEST('x') but none of them works at all)
2) Then I tried with ajax
$.post("somewebsite.php",{x:a, y:b, z:c, msg:message})
And same as above nothing are passed to the PHP website.
3) I tried with form submit
I put everything into a form and submit it to the PHP website but what I get from $_POST is an empty array.
So I conclude that something is wrong with azurewebsites server. This is the first time I used window azure so I don't know how it even works. Any suggestion would be appreciated.
you can try out ajax function
$.ajax({
url:"url",
method:"post",
data:{x:a, y:b, z:c, msg:message},
success:function(data)
{
// success code
},
error:function(error)
{
// error code ;
}
});
Should work:
Your js file:
$(document).ready(function(){
var aval = "testas";
var bval = "testas2";
var cval = "testas3";
var msg = "testas4";
$.post('test.php',{a:aval,b:bval,c:cval,message:msg},function(resp){
alert(resp);
});
});
php file should look like:
<?php
$resp = "";
foreach($_POST as $key => $val){
$resp .= $key.":".$val." \n";
}
echo $resp;
?>
After post alert should give response of all sent post values.
I hope it helped you. If yes, don't forget resp. Thanks.
Try sending an array to your somewebsite.php write this inside a function on jquery code.
It must work if you place it on a good place on your code.
var x=new Array();
x[0]='field0';
x[1]='field1';
x[2]='fieldN';
$.post('somewebsite.php',x,function(x){
alert(x);
});
Your somewebsite.php could be like this.
<?php
if(!isset($_POST['x']))$x=array();else $x=#$_POST['x'];
for($i=0;$i<count($x);$i++)
echo "X ($i) = ".$x[$i];
?>
Happy codings!