code hot reload

Overview

Node.js code hot reload can bring a lot of benifits, for example, you can hot update code in production, fix an emergency bug, change the logic of code. Especially when in a long connection service, restarting server will make users logout and then reconnect, it is bad for user experiences. However, by default, hot code reload is not supported in Node.js, because when doing hot reload, it is necessary to keep the reference of the objects, which may cause memory leak.
Bearcat provides a way for hot reload code, of course, there are some limits, not all codes updated will be hot reloaded.

Theory

Bearcat hot reload is based on bearcat’s powerful IoC container, to watch some events, when hot reload files changed, Bearcat will dynamically replace the updated POJO’s prototype functions. Therefore, because objects are shared with the same prototype object, when dynamically update the prototype object, all objects will be hot updated, without any influence to the objects’ private fields.

That is to say that what bearcat hot reload is actually the prototype functions, when you want to update a private field, it is not supported.

Enable hot reload

pass params to bearcat.createApp

1
2
3
4
bearcat.createApp([contextPath], {
BEARCAT_HOT: 'on',
BEARCAT_HPATH: 'setup your hot reload source path'
})

Watch directory

Bearcat will watch your application runtime source directory by default it is app, when it’is updated, bearcat will do hot reload for the updated files

app/car.js

1
2
3
4
5
6
7
8
9
10
var Car = function() {
this.$id = "car";
}
Car.prototype.run = function() {
console.log('run hot car...');
return 'car hot';
}
module.exports = Car;

Because bearcat updates the prototype, the updated files need to provide the updated bean’s id and func, to imply which bean need to be updated and the newest prototype function definitions.

Add file

when hot adding files, bearcat will add this file into bearcat IoC container

Add attribute dependency

app/car.js

1
2
3
4
5
6
7
8
9
10
11
12
var Car = function() {
this.$id = "car";
this.$wheel = null;
}
Car.prototype.run = function() {
console.log('run hot car...');
this.$wheel.run();
return 'car hot';
}
module.exports = Car;

suppose you want car with a wheel dependency, just add it, bearcat will hot add this dependency for all Car instances

reload events

listen to bearcat reload event, when watch codes changed, it will be fired

1
2
3
bearcat.on('reload', function() {
console.log('reload occured...');
});

Note

1
node app hpath=xxx

or

1
node app --hpath=xxx

Examples

Conclusion