Research
Security News
Quasar RAT Disguised as an npm Package for Detecting Vulnerabilities in Ethereum Smart Contracts
Socket researchers uncover a malicious npm package posing as a tool for detecting vulnerabilities in Etherium smart contracts.
Flexible Javascript timers which can be paused and modified on-the-fly
Flexible timers for Javascript which can be paused and modified on-the-fly.
Clockmaker is inspired by Mozilla's MiniDaemon and provides an alternative to the built-in setTimeout
and setInterval
functions. It is
especially useful when you are running multiple timers and wish to exercise
better control over them.
Demo: http://hiddentao.github.io/clockmaker/
Features:
Install using npm:
$ npm install clockmaker
Use bower:
$ bower install clockmaker
These examples are all running in node.js. At the top of each example assume you have the following:
var Timer = require('clockmaker').Timer,
Timers = require('clockmaker').Timers;
The basic Timer
works in the same way as setTimeout
:
Timer(function(timer) {
console.log(timer.getDelay() + ' millseconds done');
}, 2000).start();
Notice how start()
needs to be called to kick-off the timer. Also notice how the Timer
instance is passes as an argument to the handler, allowing us to query and control the timer from within our handler.
You can also explicitly construct the Timer
object:
var timer = new Timer(function() {
console.log('2 seconds done');
}, 2000);
timer.start();
Once a basic timer has ticked and invoked its handler it cannot be started again:
var timer = new Timer(function() {
console.log('2 seconds done');
}, 2000);
timer.start();
timer.isStopped(); // false
// ... >2 seconds later
timer.start(); // has no effect
timer.isStopped(); // true
And you can stop a timer from executing its handler in the first place:
var timer = new Timer(function() {
console.log('You should never see this line');
}, 2000);
timer.start();
timer.isStopped(); // false
// ... <2 seconds later
timer.stop();
timer.isStopped(); // true
You can simulate setInterval
behaviour by setting repeat: true
in the options.
Timer(function(timer) {
console.log('Another 2 seconds passed. Number of ticks so far: ' + timer.getNumTicks());
}, 2000, {
repeat: true
}).start();
The getNumTicks()
method tells you how many times the timer has ticked. Let's stop the timer after 10 ticks:
Timer(function(timer) {
console.log('Another 2 seconds passed');
if (10 === timer.getNumTicks()) {
timer.stop();
}
}, 2000, {
repeat: true
}).start();
You can change the delay interval in real-time:
Timer(function(timer) {
console.log('Next tick will take 1 second longer');
timer.setDelay(timer.getDelay() + 1000);
}, delayMs, {
repeat: true
}).start();
Let's stop and restart the timer using a second timer:
var timer = new Timer(function() {
console.log('Another 2 seconds done');
}, 2000, {
repeat: true
});
timer.start();
// This second timer which will stop/start the first timer every 5 seconds
Timer(function() {
if (timer.isStopped()) {
timer.start();
} else {
timer.stop();
}
}, 5000, {
repeat: true
}).start();
A timer does not keep track of how much time has elapsed when it gets stopped. So when it gets started again it resumes with the full time delay.
The timer waits for the handler to finish executing before scheduling the next tick. But what if the handler is asynchronous? you can inform the timer of this and be given a callback:
var timer = new Timer(function(timer, cb) {
// ... do some stuff
cb();
}, 2000, {
repeat: true,
async: true
});
timer.start();
In this case, until your handler invokes the cb()
callback (see above) the timer will not schedule the next tick. This allows you to decide whether you want to schedule
the next tick straight away (i.e. calling cb()
straight away) or once all necessary work inside the handler is done (i.e. calling cb()
at the end).
You can also use the callback to handle errors.
The this
context for the handler function can be set:
var ctx = {
dummy: true
};
new Timer(function() {
console.log(this.dummy); // true
}, 2000, {
thisObj: ctx
}).start();
Sometimes you may want to reset a timer that's already running, i.e. stop and then restart it without actually having to do so:
/*
In this example the second timer keeps 'resetting' the first one every 100ms.
The net effect is that the first timer never actually completes a tick.
*/
var timer = new Timer(function() {
console.log('hell world'); // this never gets executed
}, 2000);
timer.start();
Timer(function() {
timer.synchronize();
}, 100).start();
You can pass in an onError
handler to be informed of errors:
new Timer(function() {
throw new Error('A dummy error');
}, 2000, {
onError: function(err) {
console.error(err); // A dummy error
}
}).start();
Error handling works for asynchronous handlers too:
new Timer(function(timer, cb) {
cb(new Error('A dummy error'));
}, 2000, {
async: true,
onError: function(err) {
console.error(err); // A dummy error
}
}).start();
Note: If you don't pass in an onError
handler then errors are ignored.
You can control multiple timers at a time by using the Timers
interface.
var timers = new Timers();
var timer1 = timers.create(handlerFn, 2000, { repeat: true });
var timer2 = timers.create(aletFn, 1000);
var timer3 = ...
timer1.start(); // you can start them one a a time, or...
timers.start(); // ...start them all at once
... // some time later
timers.stop(); // stop all timers
If you're using Clockmaker in a browser app and are not using an AMD or CommonJS module system then it will add two new items into the global scope:
Timer
Timers
If these clash with existing values in your global scope then you can use the
.noConflict()
method calls to restore your existing values:
// assume we're running in browser global scope, i.e. window
var Timer = 'my timer class';
var Timers = 'my timers class';
// ... load clockmaker ...
console.log(Timer); // Function
console.log(Timers); // Function
// restore my definitions
var ClockmakerTimer = Timer.noConflict();
var ClockmakerTimers = Timers.noConflict();
console.log(Timer); // 'my timer class'
console.log(Timers); // 'my timers class'
To build the code and run the tests:
$ npm install -g gulp
$ npm install
$ gulp build
Contributions are welcome! Please see CONTRIBUTING.md.
MIT - see LICENSE.md
FAQs
Flexible Javascript timers which can be paused and modified on-the-fly
We found that clockmaker demonstrated a not healthy version release cadence and project activity because the last version was released a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Research
Security News
Socket researchers uncover a malicious npm package posing as a tool for detecting vulnerabilities in Etherium smart contracts.
Security News
Research
A supply chain attack on Rspack's npm packages injected cryptomining malware, potentially impacting thousands of developers.
Research
Security News
Socket researchers discovered a malware campaign on npm delivering the Skuld infostealer via typosquatted packages, exposing sensitive data.