Angular Hot Module Replacement
Angular-HMR
Hot Module Reloading for Webpack 2 and Angular 4. All versions of Angular will work with this module
npm install @angularclass/hmr @angularclass/hmr-loader
Please see repository AngularClass/angular-seed for a working example.
Also download AngularClass/angular-hmr-loader
![hmr-state-dom](https://cloud.githubusercontent.com/assets/1016365/18380378/e573320e-762b-11e6-99e0-cc110ffacc6a.gif)
main.browser.ts
import { removeNgStyles, createNewHosts, bootloader } from '@angularclass/hmr';
@NgModule({
bootstrap: [ App ],
declarations: [ App ],
imports: [
BrowserModule,
FormsModule,
HttpModule,
RouterModule.forRoot([], {
useHash: true
}),
appModule
],
providers: []
})
class MainModule {
constructor(public appRef: ApplicationRef) {}
hmrOnInit(store) {
if (!store || !store.state) return;
console.log('HMR store', store);
console.log('store.state.data:', store.state.data)
if ('restoreInputValues' in store) {
store.restoreInputValues();
}
this.appRef.tick();
delete store.state;
delete store.restoreInputValues;
}
hmrOnDestroy(store) {
var cmpLocation = this.appRef.components.map(cmp => cmp.location.nativeElement);
store.disposeOldHosts = createNewHosts(cmpLocation)
store.state = {data: 'yolo'};
store.restoreInputValues = createInputTransfer();
removeNgStyles();
}
hmrAfterDestroy(store) {
store.disposeOldHosts()
delete store.disposeOldHosts;
}
}
export function main() {
return platformBrowserDynamic().bootstrapModule(MainModule);
}
bootloader(main);
bootloader
is only needed to detect that the dom is ready before bootstraping otherwise bootstrap. This is needed because that dom is already ready during reloading.
Important Helpers
- removeNgStyles: remove angular styles
- createNewHosts and disposeOldHosts: recreate root elements for bootstrapping
- bootloader: boot on document ready or boot if it's already ready
- createInputTransfer and restoreInputValues: transfer input DOM state during replacement
Production
In production you only need bootloader which just does this:
export function bootloader(main) {
if (document.readyState === 'complete') {
main()
} else {
document.addEventListener('DOMContentLoaded', main);
}
}
You would bootstrap your app the normal way, in production, after dom is ready. Also, in production, you should remove the loader:
{
test: /\.ts$/,
loaders: [
'awesome-typescript-loader',
].concat(prod ? [] : '@angularclass/hmr-loader')
},
enjoy — AngularClass
##AngularClass
Learn AngularJS, Angular 2, and Modern Web Development from the best.
Looking for corporate Angular training, want to host us, or Angular consulting? patrick@angularclass.com