When building my angular app for production (ng serve no problem) I am getting the following error when loading one of the children modules:
ERROR Error: Uncaught (in promise): TypeError: o.ngOnDestroy is not a function
TypeError: o.ngOnDestroy is not a function
at Fi (core.js.pre-build-optimizer.js:9573)
at Mi (core.js.pre-build-optimizer.js:9541)
at Ri (core.js.pre-build-optimizer.js:9531)
at fo (core.js.pre-build-optimizer.js:10593)
at go (core.js.pre-build-optimizer.js:10719)
at vo (core.js.pre-build-optimizer.js:10662)
at fo (core.js.pre-build-optimizer.js:10591)
at go (core.js.pre-build-optimizer.js:10719)
at mo (core.js.pre-build-optimizer.js:10641)
at fo (core.js.pre-build-optimizer.js:10592)
at Fi (core.js.pre-build-optimizer.js:9573)
at Mi (core.js.pre-build-optimizer.js:9541)
at Ri (core.js.pre-build-optimizer.js:9531)
at fo (core.js.pre-build-optimizer.js:10593)
at go (core.js.pre-build-optimizer.js:10719)
at vo (core.js.pre-build-optimizer.js:10662)
at fo (core.js.pre-build-optimizer.js:10591)
at go (core.js.pre-build-optimizer.js:10719)
at mo (core.js.pre-build-optimizer.js:10641)
at fo (core.js.pre-build-optimizer.js:10592)
at P (zone.js:814)
at P (zone.js:771)
at zone.js:873
at e.invokeTask (zone.js:421)
at Object.onInvokeTask (core.js.pre-build-optimizer.js:3815)
at e.invokeTask (zone.js:420)
at t.runTask (zone.js:188)
at d (zone.js:595)
at t.invokeTask [as invoke] (zone.js:500)
at k (zone.js:1540)
I am using angular & angular cli 6.1.2. Any ideas what might be leading to this?
Below are the two code snippets where ngOnDestroy is found in the generated main.js file:
var pi = function () {
function t(t, e, n, r) {
this._moduleType = t, this._parent = e, this._bootstrapComponents = n, this._def = r, this._destroyListeners = [], this._destroyed = !1, this.injector = this, function (t) {
for (var e = t._def, n = t._providers = new Array(e.providers.length), r = 0; r < e.providers.length; r++) {
var i = e.providers[r];
4096 & i.flags || void 0 === n[r] && (n[r] = qr(t, i))
}
}(this)
}
return t.prototype.get = function (t, e, n) {
void 0 === e && (e = D.THROW_IF_NOT_FOUND), void 0 === n && (n = 0);
var r = 0;
return 4 & n ? r |= 1 : 2 & n && (r |= 4), Hr(this, {token: t, tokenKey: $n(t), flags: r}, e)
}, Object.defineProperty(t.prototype, "instance", {
get: function () {
return this.get(this._moduleType)
}, enumerable: !0, configurable: !0
}), Object.defineProperty(t.prototype, "componentFactoryResolver", {
get: function () {
return this.get(Bt)
}, enumerable: !0, configurable: !0
}), t.prototype.destroy = function () {
if (this._destroyed)throw new Error("The ng module " + k(this.instance.constructor) + " has already been destroyed.");
this._destroyed = !0, function (t, e) {
for (var n = t._def, r = new Set, i = 0; i < n.providers.length; i++)if (131072 & n.providers[i].flags) {
var o = t._providers[i];
if (o && o !== Fr) {
var a = o.ngOnDestroy;
"function" != typeof a || r.has(o) || (a.apply(o), r.add(o))
}
}
}(this), this._destroyListeners.forEach(function (t) {
return t()
})
}, t.prototype.onDestroy = function (t) {
this._destroyListeners.push(t)
}, t
}(), fi = $n(function () {
}), di = $n(ke), yi = $n(Oe), mi = $n(Ae), vi = $n(je), gi = $n(Pe), _i = $n(D), bi = $n(P);
and
function Fi(t, e, n, r) {
var i = Hn(t, e);
if (i) {
var o = i.instance;
o && (Gn.setCurrentNode(t, e), 1048576 & n && Bn(t, 512, r) && o.ngAfterContentInit(), 2097152 & n && o.ngAfterContentChecked(), 4194304 & n && Bn(t, 768, r) && o.ngAfterViewInit(), 8388608 & n && o.ngAfterViewChecked(), 131072 & n && o.ngOnDestroy())
}
}
The data does not persist! ngOnDestroy doesn't get called because some components do not get destroyed when navigating to a different route.
ngOnDestroy() gets called when a component is about to be destroyed. Notice how the example "destroys" the child component via the conditional ngIf='showChild'. By toggling the value of showChild, Angular creates and destroys the child component each time this value changes.
Only when Angular2 removes the component from the DOM because you move away or you call destroy() on a dynamically created component, then ngOnDestroy() is called. You can listen to beforeunload and unload yourself if you need some action to happen before the application is destroyed by the browser.
Angular Services also have an ngOnDestroy method, just like Angular components. This lifecycle can be helpful when we create and destroy services that need to run some cleanup work when the component is destroyed.
My solution for the issue was to run the build process without the build-optimizer. Either force the flag to false:
ng build --prod --build-optimizer=false
or in angular.json set it to false in the configurations section:
"configurations": {
"production": {
"optimization": true,
"outputHashing": "all",
"sourceMap": false,
"extractCss": true,
"namedChunks": false,
"aot": true,
"extractLicenses": true,
"vendorChunk": false,
"buildOptimizer": false,
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.prod.ts"
}
],
"serviceWorker": true
}
Problem is fixed with Angular 7
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With