I'm operating a listener in CasperJS that visits a few private websites & waits for certain configurations of data. Right now, this operates adequately, but not optimally, on a numbered For loop, along these lines:
for (var p = 20000; p-- > 0;) {
// ... c.900 lines of code ....
}
While loops & Do-While loops don't work, due to scoping issues with several instances of Casper.then.
What I'm really looking to do is cron the code over a day timer, to operate between 6am and midnight, something like:
// as global variable
function militarytime () {
var currentTime = new Date();
var hours = currentTime.getHours();
var minutes = currentTime.getMinutes();
var military = (hours*100)+minutes
return military;
}
var p = militarytime();
// then within code,
for (t=p; (t=p) && (p>600); t++)
This particular way of doing it (and I've tried many) just hangs in CasperJS.
The code has been operating, suboptimally, in a production environment for several weeks, and I've been searching stackoverflow & casperjs/api during that time to no avail. Any suggestions?
Thanks in advance.
This may be a stupid question, but are you firing the run() function? I've forgotten to include that which caused my program to just hang, generally it's the only reason I've seen for it to hang without error.
Related
I am currently having an issue with the setinterval function and was wondering if anyone could help. So oddly enough, it works for short intervals like 10 or 20 seconds but when I scale it to a day or half a day it fails to run. I'm on version 11.5.1 of discord.js
bot.setInterval(function(){
var Holiday = new Date();
var month = Holiday.getMonth()+1;
var day = Holiday.getDate();
var check = month+'/'+day;
var greeting = "";
for(var i = 0; i < Events.length; i++){
if(check == Object.keys(Events[i]) && check != "12/25"){
greeting = "Happy "+Object.values(Events[i]);
}
if(check == "12/25"){
greeting = "Merry Christmas";
}
}
for(var j = 0; j < c.length;j++){
var channel = bot.channels.get(c[j]);
if(greeting != ""){
channel.sendMessage(greeting);
}
//channel.sendMessage('test');
}
}, 3600000,)
This is the function in the ready event. Events is a json file with an array of key value pairs. c is an array with channel ids. so in the json file I have a test date that when I ran for the current day it would work, but when I change the day to the next and then wait for that time to come, nothing happens but the time should have passed and the variables should have all been reset so any ideas? Also, I have the bot hosted on glitch sending itself ping requests as well as using uptime robot which has indicated there has not been a down for 60 hours. The only reason I could think of for the cause is that maybe glitch puts the bot to sleep for a split second and it causes the interval to constantly reset, but then that would mean the pings and uptime robot are having no effect. Also, if anyone has a clever work around I would be grateful. The best I could do was just have a command that does this.
maybe because you didn't break function at the end like this
}
//channel.sendMessage('test');
}
}, 3600000);
and maybe that comma making the value act as an integer and more value going to be put in there.
Since I've updated to the new version of the library things have changed. However, this was long ago and I was hosting on glitch at the time, and that ended up being the problem. Glitch will still put to sleep the bot even if you are pinging it with uptime robot as they prevent ping spam.
I am implementing a live clock in front-end of a large application. For that I have came up with following approach -
JavaScript
var span = document.getElementById('span');
function time() {
var d = new Date();
var s = d.getSeconds();
var m = d.getMinutes();
var h = d.getHours();
span.textContent = h + ":" + m + ":" + s;
}
setInterval(time, 1000);
HTML
<span id="span"></span>
This approach works perfectly fine in isolation, but when this code is integrated in the application which is having several events and function calls, the clock starts lagging by few minutes after say couple of hours until the page is refreshed.
I think this delay is because of setInterval being a web (browser) API and is handled asynchronously it may not execute exactly after 1 second as written in the code every time, if the call stack is not empty after 1 second from time being setInterval is registered due to other function calls/ events present in the call stack of event loop.
So if the page is not refreshed for long time the delay continues to grow. Also the application is written in Angular which is a Single Page application where the page never reloads on navigation because of routing until the page is forcefully refreshed.
So how to build a precise clock in JavaScript which will never delay when integrated in a large application?
Update: Thanks everyone for the response. I think some of you are right, I may be missing some of the details. Actually I was implementing this few days back at work, but have to left this due to some reason and lost track of it. But there was some delay issue for sure working with Date and Timers. Suddenly now this came to my mind and thought asking it here. Extremely sorry for not providing concrete details.
Still I will try to recollect the details and update the question accordingly if possible.
the clock starts lagging by few minutes after say couple of hours until the page is refreshed.
Thats impossible with the code you've shown, new Date should return the correct time, no matter how often you reflect its value to the page.
So if the page is not refreshed for long time the delay continues to grow.
Most browsers today will adjust the timers slightly, so that they are quite accurate on average (e.g. if one timer gets called to late by 1ms, the next will be called 1ms earlier), therefore you can only cause a drift over a longer time if you will leave the page, which will pause the timer. That still shouldn't affect new Date though.
Have a look at the Chromium source
Timers in web browsers get dialled back when the page doesn't have focus. You can't change or prevent that. You're already doing the primary thing that's important: Using the current time to update the clock, so that even if your time function isn't called for three seconds, when it runs it updates with the then-current time, skipping over the intermediate values. (You often see people assuming the timer will run at exactly 1000ms intervals and just adding to the seconds value rather than using the current time, which is incorrect.)
If I were doing this, I'd probably decrease the interval (run the callback more often) and use a chained series of setTimeout rather than a single setInterval, not least because different browsers have historically handled setInterval in different ways.
So for instance:
function time() {
var d = new Date();
var s = d.getSeconds();
var m = d.getMinutes();
var h = d.getHours();
span.textContent = h + ":" + m + ":" + s;
setTimeout(time, 250);
}
time();
But if the page is inactive, the clock will get out of date, because the browser will either completely suspend timer execution or at least markedly dial it back. When the page becomes active again, though, hopefully it'll correct itself after no more than 250ms.
As a newcomer to Javascript coming from a background in C#, I conducted a basic performance test to compare the performance of JS with that of C#. To my surprise, the same code produced different performance results across different fiddles. Can you explain why this may be the case?
var start = performance.now();
var iterations = 100000000;
for (var i = 0; i < iterations; i++)
{
var j = i * i;
}
var end = performance.now();
var time = end - start;
alert('Execution time: ' + time);
https://jsfiddle.net/sfcu2vo6/4/
https://es6console.com/
I noticed that most websites take around 3 seconds to execute the code, but on Jsfiddle it only takes around 80ms. What is the reason for this difference in performance?
Update
After writing the same code in an HTML file and executing it in Chrome, I still see the same discrepancy. Can you explain why this may be happening?
<html>
<head></head>
<body>
<script>
var start = performance.now();
var iterations = 100000000;
for (var i = 0; i < iterations; i++)
{
var j = i * i;
}
var end = performance.now();
var time = end - start;
alert('Execution time: ' + time);
</script>
</body>
</html>
I am surprised to see that it takes more than 3 seconds to execute the code on most websites, but Jsfiddle is able to run it faster. Can you explain why Jsfiddle may have faster performance in this scenario?
Update 2
I found it interesting that when I saved the code as an .htm file on my desktop and ran it, it took around 80ms like Jsfiddle. However, when I ran the same code from another .htm file, it took around 3 seconds like the other websites. I am confused by this discrepancy. Can someone please try this and confirm if they experience the same results?
Update 3
I have discovered that the reason the code was running faster on Jsfiddle is because it was wrapped in window.onload = function() {}. As a beginner, I made a mistake by not including this code in my initial tests. I am relieved to have found the reason for the difference in performance.
If you take a trace in the Chrome performance tab while executing this code, you'll see that most of the time spent is in es6console.com's code bundles, rather than your function.
I didn't dig into exactly what they are doing, but it's possibly related to the fact that es6console transpiles the code using Babel. In general it's best not to rely on fiddles for performance testing since there are several ways they can add additional overhead on top of your code.
This is my code:
var d = new Date();
function myFunction() {
ifNewDay();
}
function ifNewDay() {
var currentTime = d.toLocaleTimeString();
if(currentTime == "3:21:00:00 AM EDT"){
Logger.log("It is 3:21 PM");
} else {
ifNewDay();
}
}
I am trying to write code that will only continue once it hits a certain time, I'm sure there's a way easier way to do this, but I'm brand new. Thanks.
There's a limit on how deep you can recurse, and in you case, that's A LOT of calls in a short period.
When you call a function it gets added to the stack in memory, and there's a limit on how big the stack can be. You can read more here about how it works.
You could use sleep and call that function only every second or so, or at least half a second or something.
It seems like using a time driving trigger is what would work best. Have you looked into triggers?
https://developers.google.com/apps-script/guides/triggers/installable
I was wondering if it were possible to implement some kind of crude JavaScript anti-flood protection.
My code receives events from a server through AJAX, but sometimes these events can be quite frequent (they're not governed by me).
I have attempted to come up with a method of combating this, and I've written a small script: http://jsfiddle.net/Ry5k9/
var puts = {};
function receiverFunction(id, text) {
if ( !puts[id] ) {
puts = {};
puts[id] = {};
}
puts[id].start = puts[id].start || new Date();
var count = puts[id].count = puts[id].count + 1 || 0;
var time = (new Date() - puts[id].start) * 0.001;
$("text").set("text", (count / time.toFixed()).toString() + " lines/second");
doSomethingWithTextIfNotSpam(text);
}
};
which I think could prove effective against these kinds of attacks, but I'm wondering if it can be improved or perhaps rewritten?
So far, I think everything more than 3 or 2.5 lines per second seems like spam, but as time progresses forward (because start mark was set... well... at the start), an offender could simply idle for a while and then commence the flood, effectively never passing 1 line per minute.
Also, I would like to add that I use Mootools and Lo-Dash libraries (maybe they provide some interesting methods), but it would be preferable if this can be done using native JS.
Any insight is greatly appreciated!
If you are concerned about the frequency a particular javascript function fires, you could debounce the function.
In your example, I guess it would be something like:
onSuccess: function(){ _.debounce(someOtherFunction, timeOut)};
where timeout is the maximum frequency you want someOtherFunction to be called.
I know you asked about native JavaScript, but maybe take a look at RxJS.
RxJS or Reactive Extensions for JavaScript is a library for
transforming, composing, and querying streams of data. We mean all
kinds of data too, from simple arrays of values, to series of events
(unfortunate or otherwise), to complex flows of data.
There is an example on that page which uses the throttle method to "Ignores values from an observable sequence which are followed by another value before dueTime" (see source).
keyup = Rx.Observable.fromEvent(input, 'keyup').select(function(ev) {
return ev.target.value;
}).where(function(text) {
return text.length > 2;
}).throttle(500)
.distinctUntilChanged()
There might be a similar way to get your 2.5-3 per second and ignore the rest of the events until the next second.
I've spent many days pondering on effective measures to forbid message-flooding, until I came across the solution implemented somewhere else.
First, we need three things, penalty and score variables, and a point in time where last action occured:
var score = 0;
var penalty = 200; // Penalty can be fine-tuned.
var lastact = new Date();
Next, we decrease score by the distance between the previous message and current in time.
/* The smaller the distance, more time has to pass in order
* to negate the score penalty cause{d,s}.
*/
score -= (new Date() - lastact) * 0.05;
// Score shouldn't be less than zero.
score = (score < 0) ? 0 : score;
Then we add the message penalty and check if it crosses the threshold:
if ( (score += penalty) > 1000 ) {
// Do things.
}
Shouldn't forget to update last action afterwards:
lastact = new Date();