Angular compilation fails after upgrade to Angular v9 and enabling Ivy - javascript

We have recently upgraded our angular app to the latest version of Angular (Angular v9).
All our dependencies are also upgraded, "ng update" says all our dependencies are "in order".
When we build the application with Ivy enabled the compilation process fails with a ton of errors, which we've never encountered before:
"angularCompilerOptions": {
"enableIvy": true
}
Some of the errors are very odd, saying that you can't bind 'ngClass' or 'ngModel' since it's not a know property of 'div'. It seems like it's missing some of its main modules.
For example:
src/app/register/register.component.html:34:48 - error NG8002: Can't bind to 'ngClass' since it isn't a known property of 'div'.
<div class="form-group has-feedback" [ngClass]="{ 'has-error': f.submitted && !fname.valid }">
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
src/app/modals/modal-recommendations/modal-recommendations.component.html:12:25 - error NG8002: Can't bind to 'ngClass' since it isn't a known property of 'div'.
<div class="modal-body" [ngClass]="{'text-center': recommendationNotVisible()}">
12 <div class="modal-body" [ngClass]="{'text-center': recommendationNotVisible()}">
src/app/dashboard/dashboard.component.html:53:17 - error NG8002: Can't bind to 'accountId' since it isn't a known property of 'app-metric-box'.
53 [accountId]="accountId"
Or it doesn't recognize some of the components, like:
src/app/export/export-base/export-base.component.html:2:5 - error NG8001: 'router-outlet' is not a known element:
1. If 'router-outlet' is an Angular component, then verify that it is part of this module.
2. If 'router-outlet' is a Web Component then add 'CUSTOM_ELEMENTS_SCHEMA' to the '#NgModule.schemas' of this component to suppress this message.
2 <router-outlet></router-outlet>
The errors are mainly of two types:
Can't bin to [some-property], since it isn't a known property of [some-element]. The properties can be angular properties (ngClass, ngModel) or our custom ones on our components.
[some-component] is not a known element (again this occurs for both our custom components and angular components)
If we disable "Ivy" everything works without any errors, the code compiles and runs smoothly.
We want to start using Ivy so we're searching for an explanation about these errors and how to fix them.
Thanks!

You need add CUSTOM_ELEMENTS_SCHEMA to schemas array in your module
import { NgModule, CUSTOM_ELEMENTS_SCHEMA } from '#angular/core';
#NgModule({
...
schemas: [ CUSTOM_ELEMENTS_SCHEMA ]
})
export class AppModule { }

My issue was I had a component defined as an entry component. Since this is being deprecated with Ivy, I removed the entryComponents property from our modules. However, in one case, this resulted in a similar error as you.
error NG8002: Can't bind to 'ngClass' since it isn't a known property of 'div'
Let's say this occurred in text.component.html (TextComponent). It has a TextModule containing the import for CommonModule which enables ngClass. It sits under ParentComponent, and previously in ParentModule, it had an entry property with TextComponent. I suspect Ivy is only pulling in TextComponent and not TextModule. So I updated ParentModule to import the text module and it resolved the error.
Before:
#NgModule({
imports: []
entryComponents: [TextComponent]
})
export class ParentModule { }
After:
#NgModule({
imports: [TextModule]
})
export class ParentModule { }
So your individual issue may be different, but I would look at how your modules and imports are structured.

Related

Getting ng model is not a known property of input in Angular

Getting this error below only in 2 components out of 12 components.
ng model is not a known property of input
Even after importing for Forms module and reactive forms module in app.modules.ts. I am getting the err I am using ngModel in other components also but they are working fine.
Why I am getting the error only in 2 components?
How to get rid of it?
If you'd like to use your input, not in a form, you can use it with ngModelOptions and make standalone true...
[ngModelOptions]="{standalone: true}"
app.module.ts
You have already done this.
import { FormsModule } from '#angular/forms';
But just check with you have any other modules rather than app.module.ts Then you should imported only in one place.Give a try and see.
#NgModule({
imports: [
FormsModule
],
})
If these components are registered in another module not in appModule so you need to import FormsModule in that module same as appModule.

How to enable Angular animations?

I've done everything by the tutorial (https://angular.io/guide/animations), but I have the error: menu-navigation.component.html:1 ERROR Error: Found the synthetic property #slideTop. Please include either "BrowserAnimationsModule" or "NoopAnimationsModule" in your application.
I read everything about it but did not find the answer on how to resolve it.
Files:
app.ts: https://gist.github.com/yakimchuk/d2458a26e0a8b9a31f7d92d15885ee08
parent-component-html: https://gist.github.com/yakimchuk/63ece812957a67a243cc2ab7cb03fd0a
parent-component-ts: https://gist.github.com/yakimchuk/ea857a109a5c2cc644c16d800990d469
animated-component.ts: https://gist.github.com/yakimchuk/71c7f3d756742e7e6d98d26f27e889d0
transitions.ts: https://gist.github.com/yakimchuk/2ef55221aaeaf382d34aee7e77d31d3d
So I did:
Imported animation modules in the root module (and added them into imports section)
Described animation of the animated element
Defined attribute about animation
Did everything according to documentation
I tried:
Replace BrowserAnimationsModule with NoopAnimationsModule: no result
Replace "data: boolean" with "data: any" (in parent component): no result
Check all NPM-modules versions: they are all 8.0.0 version, no result
Check tutorial steps many times: no result
Copy animation metadata from the tutorial and do everything like there, and still: no result
Guys, help me :)
I am stuck for already a few days.
UPDATE:
Finally, I found the answer after testing on a new empty project
If you defined "animations" to the component (prop), then you can use them only inside its component (its own html), but not within a parent layout.
Instead of "" you must move its amination inside that component (app-animated-comp).
BrowserAnimationsModule is an package you need to add in your app.module
https://material.angular.io/guide/getting-started
import {BrowserAnimationsModule} from '#angular/platform-browser/animations';
#NgModule({
...
imports: [BrowserAnimationsModule],
...
})
export class PizzaPartyAppModule { }

WebStorm not recognising some Angular components - mat-toolbar unknown element

I am using Angular 5 with Angular material and WebStorm version 2017.3.1
When I try to use the <mat-toolbar> element with the following code
app.module.ts
import { BrowserModule } from '#angular/platform-browser';
import { NgModule } from '#angular/core';
import {MatToolbarModule} from '#angular/material';
import { AppComponent } from './app.component';
#NgModule({
declarations: [
AppComponent
],
imports: [
BrowserModule,
MatToolbarModule
],
providers: [],
bootstrap: [AppComponent]
})
export class AppModule { }
app.component.html
<mat-toolbar>
<span>Title</span>
</mat-toolbar>
WebStorm gives me an error:
'mat-toolbar' is not a known element:
1. If 'mat-toolbar' is an Angular component, then verify that it is part of this module.
However, this renders correctly in the browser:
Because it is included in the module with this line import {MatToolbarModule} from '#angular/material'; and
imports: [
BrowserModule,
MatToolbarModule
],
Is there something I'm missing here? Why does WebStorm (and also when running tests via ng test) give me this error? How can I prevent this error/warning?
This error is generated via TypeScript.
You can see the error in the console if you click on the TypeScript tab at the bottom.
It's possible to make this error go away if you force the TypeScript service to restart by clicking on the arrow in a circle.
This requires a compile first.
So far, I cannot find a way to map this to a shortcut.
Thanks to #lena and #Z.Bagley for helping me figure this out.
The error comes from Angular language service.
Looks related to https://github.com/angular/angular/issues/14961; see if updating Typescript to 2.5.2+ helps
I know this isn't the problem the OP had, but wanted to share this in case someone comes across this post and is still experiencing this problem in WebStorm and are not getting TypeScript compile errors, here's what worked for me: In WebStorm select menu item File > Invalidate Caches / Restart. This problem happened to me in WebStorm 2019.3 .

How do I declare a dependency on an ng-metadata module?

I have a project that is using ng-metadata (https://github.com/ngParty/ng-metadata) to build a handful of Angular 1.5 modules. I have a test module/component that looks like this:
import { NgModule, Component, Inject, Input, Output, EventEmitter } from 'ng-metadata/core'
import { platformBrowserDynamic } from 'ng-metadata/platform-browser-dynamic'
#Component({
selector: 'test',
template: require('./test.template.html')
})
class TestComponent {
#Input() type: string;
constructor() {
console.log(`test: ${this.type}`)
}
}
#NgModule({
declarations: [TestComponent]
})
class HeroModule {}
platformBrowserDynamic().bootstrapModule(HeroModule)
Everything seems happy when compiled and I'm now attempting to use the module in another project (that is not using ng-metadata but has a compatible version of Angular).
I'm simply including the shims as directed by the ng-metadata docs and the JavaScript file that contains the module described above (built by webpack). I have a new module in this project that wants to list the HeroModule as a dependency. I've tried a few things:
// attempt 1:
angular.module('my-consuming-module', ['ui.router', 'hero'])
// attempt 2:
angular.module('my-consuming-module', ['ui.router', 'heroModule'])
// attempt 3:
angular.module('my-consuming-module', ['ui.router', 'hero-module'])
All always end up with the same Error: $injector:nomod Module Unavailable error from Angular.
If I'm using ng-metadata to build my modules, what are the names I use to list them as dependencies in another project?
Finally figured this out! It's amazing what happens when you carefully read documentation...
Found in the Manual Angular 1 Bootstrap section of ng-metadata's docs:
You can still leverage ng2 way of components registration without ng-metadata bootstrap, but you have to manually create your Angular 1 module from an ng-metadata #NgModule using the bundle helper function.
I ended up being able to do the following:
// REMOVED platformBrowserDynamic().bootstrapModule(HeroModule)
const Ng1AdminModule = bundle(HeroModule).name;
export const AppModule = angular.module('hero', [Ng1AdminModule]);
And then my hero module becomes accessible to the my-consuming-module just as I expected. The bundle helper function was the key to figuring this out.
You need to import those module from their respective locations and inject it inside your angular module
//ensure `angular`, `angular-ui-router` should be there in `map` of systemjs.config.js
import * as angular from 'angular';
import * as uiRouter from 'angular-ui-router';
import { heroModule} from './hero.module';
angular.module('app',[ uiRouter, heroModule]);
Check references here

How to setup angular 2 material design 2.0.0-beta.2

I'm trying to use angular material design (2.0.0-beta2), but I cannot get it to work. For example, if I try to use
<md-input-container>
<input mdInput name="value">
</md-input-container>
With the following added to app.module.ts
import {MaterialModule} from '#angular/material';
#NgModule({
...
imports: [ MaterialModule, ...],
...
})
But I get the following error:
'md-input-container' is not a known element:
Note: The component using the above code lives somewhere in my app a couple of modules deep!
When I also add MdInputContainer to the declarations I get a different error:
Type MdInputContainer is part of the declarations of 2 modules: MdInputModule and AppModule!
I think I'm getting close, but I'm missing something, any help would be appreciated
In order to use angular material components you need to import the MaterialModule in the module you are using it. Importing it only from parent modules won't recognize it.

Categories