Javascript setInterval working in local but on the server - javascript

I am using Angular 10 and have the following setInterval code working in my local:
ngOnInit() {
this.myfunc();
setInterval(this.myfunc.bind(this), 120000);
}
However, the same code is not working on the server.
In other words, myfunc() is not triggering after 2 mins when running on the server.
Debugging Details:
In my local, this.myfunc() is called when the component is loaded for the first time. It is called again after 2 mins as per the setInterval()
However, when running on the server, this.myfunc() is called when the component is loaded for the first time. But it is not called again after 2 mins as per the setInterval()

Problem
setInterval sometimes drifts, as seen in this post.
Solution
Taken from this solution, you would first make a non-drifting class:
function AdjustingInterval(workFunc, interval) {
let that = this;
let expected, timeout;
this.interval = interval;
this.start = function() {
expected = Date.now() + this.interval;
timeout = setTimeout(step, this.interval);
}
this.stop = function() {
clearTimeout(timeout);
}
function step() {
let drift = Date.now() - expected;
workFunc();
expected += that.interval;
timeout = setTimeout(step, Math.max(0, that.interval - drift));
}
}
and then, you would just use this instead for your code:
ngOnInit() {
let ticker = new AdjustingInterval(this.myfunc.bind(this), 120000);
this.myfunc();
ticker.start();
}

I was able to resolve the issue by changing setInterval() to callback as follows:
setInterval(() => {
this.myfunc(); }, 120000);
}
Updated ngOnInit() looks as below:
ngOnInit() {
this.myfunc();
setInterval(() => {
this.myfunc(); }, 120000);
}
}

Related

How to manually stop a watcher?

I need to stop watch() but the docs don't really explain how to do that.
This watcher runs until the loop is finished (1000 seconds):
const state = reactive({
val: 0
})
watch(() => state.val, () => {
console.log(state.val)
})
for (let i = 1; i < 1000; i++) {
setTimeout(function timer() {
state.val = state.val + 1
}, i * 1000);
}
How do I stop the watcher after running once? Using watchEffect is not an option because for my use case the watcher needs to run several times before stopped, which is not described in this simplified example. From my understanding watchEffect runs only once (after initiation).
The "watch" function returns a function which stops the watcher when it is called :
const unwatch = watch(someProperty, () => { });
unwatch(); // It will stop watching
To watch a change only once:
const unwatch = watch(someProperty, () => {
// Do what your have to do
unwatch();
});

how to stop setInterval in react native

i am running a setinterval function to check for a payment from coinbase in my react native app, i run the function after every 10 seconds, after the payment has been made, i clear the setinterval and navigate to the homepage, but still the setinteval keeps running how can i stop this?
useEffect(() => {
getData();
myinterval();
}, []);
const myinterval= () => setInterval(function () {
checkCharge();
}, 10000);
const stopCounter = () => {
clearInterval(myinterval);
}
const checkCharge = async () => {
try {
...SOME_CODE_HERE...
stopCounter()
navigation.navigate("HomeScreen");
} catch (e) {
console.log(e);
}
};
i ran into a similar problem some months back, this soluion should work perfectly:
const myinterval = setInterval(function () {
checkCharge();
}, 10000);
but in my case, since I store the setInterval in a variable instead of a function, I had some weird problems, like the setInterval might run three times or keep on running even after I used clearInterval(INTERVAL_NAME); so if you want to check if a payment has been made, create a button that would tell the user to click when they have made the payment, this would be a lot safer than to run the function inside of setInterval
I believe it's because myinterval is assigned to a function and not the actual return value of the setInterval() function. So try to change
const myinterval = () => setInterval(function () {
checkCharge();
}, 10000);
to
const myinterval = setInterval(function () {
checkCharge();
}, 10000);
and then canceling the myinterval variable with clearInterval(myinterval);
You aren't using the return from myinterval() to clear the setInterval. setInterval() returns an id that is used to clear the interval. When you call the function myinterval, it is returning that ID. What you need to do is store that ID in a variable that you can use to clear the interval.
...
function createInterval(){
return setInterval(checkCharge, 10000);
}
function stopCounter(id){
clearInterval(id);
}
...
var id = createInterval();
...
function checkCharge(){
try {
...
stopCounter(id);
...
} catch(e){
console.error(e);
}
}

Why does this interval stop ticking in react?

I was playing with this example timer and then wanted to see if I could capture/pass data into the timer so I started with a simple message. If I remove the message to timer it ticks accordingly. I started logging other lifecycle methods but I am curious if this is JS thing which I don't think it is versus something in react life cycle. I forked a JS bin here with ex
'code'
var Timer = React.createClass({
getInitialState: function() {
return {secondsElapsed: 0};
},
tick: function(msg) {
console.log('msg is',msg);
this.setState({secondsElapsed: this.state.secondsElapsed + 1});
},
componentDidMount: function() {
this.interval = setInterval(this.tick('hi'), 1000);
},
componentWillUnmount: function() {
clearInterval(this.interval);
},
render: function() {
return (
<div>Seconds Elapsed: {this.state.secondsElapsed}</div>
);
}
});
React.render(<Timer />, document.getElementById("content"));
All you need to do is to change this bit in your code:
this.interval = setInterval(() => this.tick('hi'), 1000);
Alternatively, you can also send in this to the callback:
this.interval = setInterval(function(t) {t.tick('hi')}, 1000, this);
See the updated fiddle, here.
setInterval() takes (at least) two parameters, the first one is the callback and needs to be a function. You had provided the code directly; that code must be inside a function.
var intervalID = scope.setInterval(func, delay);
func
A function to be executed every delay milliseconds. The function is not passed any parameters, and no return value is expected.
Change code to:
componentDidMount: function() {
this.interval = setInterval(()=>this.tick('hi'), 1000);
}

Vue.JS countdown not works

I have a vue application, but the countdown not work good.
Actually i dont know why.
View {{ $parent.timer }} i see the good value.
Vue data:
data: function() {
return {
timer : 3,
...
and here is my countdown function:
countdown : function(time,callback)
{
//time is equal 5
this.timer = time;
//this.timer is equal 5
var timerInterval = undefined;
timerInterval = setInterval(function() {
if(this.timer == 1) {
this.timer = 0;
callback();
return clearInterval(timerInterval);
}
// First time undefined, in 2nd is NaN
this.timer -= 1;
// NaN
}, 1000);
}
call function:
this.countdown(data.time,function(){ //smtng });
What i do bad? Its work in my older Vue application.
I hope someone can help to me :)
Thanks so much!
It is an issue with scope of this, as explained below:
function() {...} creates a new scope inside. If you use this inside this function, it does not refer to outer scope. Therefore your this.timer of Vue component does not get updated from inside your setInterval().
() => {...} works like a function but does not create a new scope inside.
Check if the following code works:
timerInterval = setInterval(() => {
if(this.timer == 1) {
this.timer = 0; // `this` points to the scope of Vue component
callback();
// ...
}
// ...
}, 1000);
More info on arrow functions: https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Functions/Arrow_functions

Calling a function every 60 seconds

Using setTimeout() it is possible to launch a function at a specified time:
setTimeout(function, 60000);
But what if I would like to launch the function multiple times? Every time a time interval passes, I would like to execute the function (every 60 seconds, let's say).
If you don't care if the code within the timer may take longer than your interval, use setInterval():
setInterval(function, delay)
That fires the function passed in as first parameter over and over.
A better approach is, to use setTimeout along with a self-executing anonymous function:
(function(){
// do some stuff
setTimeout(arguments.callee, 60000);
})();
that guarantees, that the next call is not made before your code was executed. I used arguments.callee in this example as function reference. It's a better way to give the function a name and call that within setTimeout because arguments.callee is deprecated in ecmascript 5.
use the
setInterval(function, 60000);
EDIT : (In case if you want to stop the clock after it is started)
Script section
<script>
var int=self.setInterval(function, 60000);
</script>
and HTML Code
<!-- Stop Button -->
Stop
A better use of jAndy's answer to implement a polling function that polls every interval seconds, and ends after timeout seconds.
function pollFunc(fn, timeout, interval) {
var startTime = (new Date()).getTime();
interval = interval || 1000;
(function p() {
fn();
if (((new Date).getTime() - startTime ) <= timeout) {
setTimeout(p, interval);
}
})();
}
pollFunc(sendHeartBeat, 60000, 1000);
UPDATE
As per the comment, updating it for the ability of the passed function to stop the polling:
function pollFunc(fn, timeout, interval) {
var startTime = (new Date()).getTime();
interval = interval || 1000,
canPoll = true;
(function p() {
canPoll = ((new Date).getTime() - startTime ) <= timeout;
if (!fn() && canPoll) { // ensures the function exucutes
setTimeout(p, interval);
}
})();
}
pollFunc(sendHeartBeat, 60000, 1000);
function sendHeartBeat(params) {
...
...
if (receivedData) {
// no need to execute further
return true; // or false, change the IIFE inside condition accordingly.
}
}
In jQuery you can do like this.
function random_no(){
var ran=Math.random();
jQuery('#random_no_container').html(ran);
}
window.setInterval(function(){
/// call your function here
random_no();
}, 6000); // Change Interval here to test. For eg: 5000 for 5 sec
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="random_no_container">
Hello. Here you can see random numbers after every 6 sec
</div>
setInterval(fn,time)
is the method you're after.
You can simply call setTimeout at the end of the function. This will add it again to the event queue. You can use any kind of logic to vary the delay values. For example,
function multiStep() {
// do some work here
blah_blah_whatever();
var newtime = 60000;
if (!requestStop) {
setTimeout(multiStep, newtime);
}
}
Use window.setInterval(func, time).
A good example where to subscribe a setInterval(), and use a clearInterval() to stop the forever loop:
function myTimer() {
}
var timer = setInterval(myTimer, 5000);
call this line to stop the loop:
clearInterval(timer);
Call a Javascript function every 2 second continuously for 10 second.
var intervalPromise;
$scope.startTimer = function(fn, delay, timeoutTime) {
intervalPromise = $interval(function() {
fn();
var currentTime = new Date().getTime() - $scope.startTime;
if (currentTime > timeoutTime){
$interval.cancel(intervalPromise);
}
}, delay);
};
$scope.startTimer(hello, 2000, 10000);
hello(){
console.log("hello");
}
function random(number) {
return Math.floor(Math.random() * (number+1));
}
setInterval(() => {
const rndCol = 'rgb(' + random(255) + ',' + random(255) + ',' + random(255) + ')';//rgb value (0-255,0-255,0-255)
document.body.style.backgroundColor = rndCol;
}, 1000);
<script src="test.js"></script>
it changes background color in every 1 second (written as 1000 in JS)
// example:
// checkEach(1000, () => {
// if(!canIDoWorkNow()) {
// return true // try again after 1 second
// }
//
// doWork()
// })
export function checkEach(milliseconds, fn) {
const timer = setInterval(
() => {
try {
const retry = fn()
if (retry !== true) {
clearInterval(timer)
}
} catch (e) {
clearInterval(timer)
throw e
}
},
milliseconds
)
}
here we console natural number 0 to ......n (next number print in console every 60 sec.) , using setInterval()
var count = 0;
function abc(){
count ++;
console.log(count);
}
setInterval(abc,60*1000);
I see that it wasn't mentioned here if you need to pass a parameter to your function on repeat setTimeout(myFunc(myVal), 60000); will cause an error of calling function before the previous call is completed.
Therefore, you can pass the parameter like
setTimeout(function () {
myFunc(myVal);
}, 60000)
For more detailed information you can see the JavaScript garden.
Hope it helps somebody.
I favour calling a function that contains a loop function that calls a setTimeout on itself at regular intervals.
function timer(interval = 1000) {
function loop(count = 1) {
console.log(count);
setTimeout(loop, interval, ++count);
}
loop();
}
timer();
There are 2 ways to call-
setInterval(function (){ functionName();}, 60000);
setInterval(functionName, 60000);
above function will call on every 60 seconds.

Categories

Resources