Creating a component with @input for unit tests in Angular can be achieved through the following steps

I'm encountering issues while attempting to create a testing component with an @input. The component utilizes properties from the feedback model, and although I imported them into the test file, errors are being displayed. Can anyone offer assistance?

feedback-card.component.ts

import { Component, OnInit, Input, HostBinding } from '@angular/core';
import { FeedbackCommentsComponent } from '../feedback-comments/feedback-comments.component';
import { routerAnimation } from '../../../../utils/page.animation';
import { AuthService } from '../../../../services/auth.service';
import { Feedback } from '../../../../models/feedback';
import { FirestoreService } from '../../../../services/firestore.service';
import * as firebase from 'firebase/app';
import 'firebase/firestore';
import { first } from 'rxjs/operators';
import { MatBottomSheet } from '@angular/material/bottom-sheet';
import { MatSnackBar } from '@angular/material/snack-bar';

@Component({
  selector: 'app-feedback-card',
  templateUrl: './feedback-card.component.html',
  styleUrls: ['./feedback-card.component.scss'],
  animations: [routerAnimation]
})

export class FeedbackCardComponent implements OnInit {

  @HostBinding('@routerAnimation') routerAnimation = true;
  @Input() feedback: Feedback
  @Input() isAdmin = false
  input
  userId
...

feedback-card.component.spec.ts

import { ComponentFixture, TestBed, waitForAsync } from '@angular/core/testing';
import { MatBottomSheet } from '@angular/material/bottom-sheet';
import { MatSnackBar } from '@angular/material/snack-bar';
import { FirestoreService } from '../../../../services/firestore.service';
import { AuthService } from '../../../../services/auth.service';
import { FeedbackCardComponent } from './feedback-card.component';
import { CommonModule } from '@angular/common';
import { Feedback } from '../../../../models/feedback';
import { FormBuilder, FormsModule, ReactiveFormsModule } from '@angular/forms';
import { AppModule } from 'src/app/app.module';
import { MatDialogModule } from '@angular/material/dialog';
import { TranslateFakeLoader, TranslateLoader, TranslateModule, TranslateService } from '@ngx-translate/core';
import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/compiler';
import { FunctionsService } from 'src/app/services/functions.service';
import { MatProgressBarModule } from '@angular/material/progress-bar';
import { Skill } from 'src/app/models/skill';

fdescribe('FeedbackCardComponent', () => {
  let component: FeedbackCardComponent;
  let fixture: ComponentFixture<FeedbackCardComponent>;

  beforeEach(waitForAsync(() => {
    TestBed.configureTestingModule({
        imports: [
          CommonModule,
          ReactiveFormsModule,
          FormsModule,
          AppModule,
          MatDialogModule,
          TranslateModule.forRoot({
              loader: {
                provide: TranslateLoader,
                useClass: TranslateFakeLoader
              }
          })
      ],
      schemas: [
        CUSTOM_ELEMENTS_SCHEMA
      ],
      declarations: [ 
        FeedbackCardComponent,
      ],
      providers: [
        FirestoreService
        MatSnackBar,
        MatProgressBarModule,
        FirestoreService,
        FunctionsService,
        TranslateService,
    ]
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(FeedbackCardComponent);
    fireStoreServiceMock = TestBed.inject(FirestoreService);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

  it('should create', () => {
    expect(component).toBeTruthy();
  });
});

Error Log:

TypeError: Cannot read property 'skill' of undefined
TypeError: Cannot read property 'skill' of undefined
    at FeedbackCardComponent_Template (ng:///FeedbackCardComponent.js:305:52)
    at executeTemplate (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:9545:1)
    at refreshView (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:9414:1)
    at refreshComponent (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:10580:1)
    at refreshChildComponents (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:9211:1)
    at refreshView (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:9464:1)
    at renderComponentOrTemplate (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:9528:1)
    at tickRootContext (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:10754:1)
    at detectChangesInRootView (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:10779:1)
    at RootViewRef.detectChanges (http://localhost:9876/_karma_webpack_/webpack:/node_modules/@angular/core/__ivy_ngcc__/fesm2015/core.js:22792:1)

Answer №1

When using fixture.detectChanges(), remember that it triggers the calling of ngOnInit. Therefore, ensure that your inputs are defined beforehand.

You can follow this approach:

beforeEach(() => {
    fixture = TestBed.createComponent(FeedbackCardComponent);
    fireStoreServiceMock = TestBed.inject(FirestoreService);
    component = fixture.componentInstance;
    component.feedback = // create a mock for feedback
    component.isAdmin = // set to false by default, but you may want to mock it here as well.
    fixture.detectChanges();
  });

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Encountering a "args" property undefined error when compiling a .ts file in Visual Studio Code IDE

I've created a tsconfig.json file with the following content: { "compilerOptions": { "target": "es5" } } In my HelloWorld.ts file, I have the following code: function SayHello() { let x = "Hello World!"; alert(x); } However ...

Navigate to the middle of a DIV container in Angular 7

Is there a way to programmatically scroll to the center of my element on both the Y and X axes when a specific function is executed? My HTML structure includes the following (I am aiming to scroll to the middle of #viewport): </div> <div # ...

Generate an alert with a numerical input field - Ionic

How can I create an input with type number in AlertController? I attempted to implement this, but the input only accepts text and not numbers. const alert = this.alertCtrl.create({ title: 'Add Ingredient', inputs: [ { name: ' ...

My inquiry was met with silence from the Angular project

I have encountered an issue with my dockerized angular project. Upon starting my container, it appears that the 4200 port is already in use, even though the CMD command within the container does not initiate the application startup. Here is how my Docke ...

Migration of Angular dynamic forms project - The error "input" does not have an initializer or a constructor, and another issue with Type T | undefined

Angular dynamic forms project migration - encountering Type T | undefined error In my quest to find a sample project demonstrating the creation of Angular forms using JSON datasets, I stumbled upon this repository: https://github.com/dkreider/advanced-dyn ...

Tips for creating a universal event listener for keyPress events in Angular 5

This question pertains to the Angular 5 framework. Despite extensive research on topics like ElementRef and EventEmitter, I have been unable to find a straightforward method to programmatically trigger a global "Document scope" keyPress or keyDown event s ...

Is it possible to update the text within a button when hovering over it in Angular?

I'm looking to update the text displayed inside a button when hovering over it, similar to the examples in these images. I have already implemented the active state, but now I just need to change the text content. <button type="submit" ...

In the given situation, which would be the preferable option - making use of useEffect or opting for

My custom hook fetches data from a smart contract as shown below: export const usePoolLength = () => { const [length, setLength] = useState(0); const _getPoolLength = useCallback(async () => { const poolLength = await getPoolLength() ...

struggling with configuring dependency injection in NestJS and TypeORM

Struggling with integrating nestjs and typeorm for a simple CRUD application, specifically facing issues with dependency injection. Attempting to modularize the database setup code and import it. Encountering this error message: [ExceptionHandler] Nest ...

Guide on submitting a form through the Angular 2 HTTP post method with JavaScript

Currently working on grasping the concepts of Angular2, but facing challenges when attempting to utilize http.post() for submitting a form to my Web API. ...

Display the highlighted text within the input field

Is there a library available that can create an input field with a suggestions dropdown for Male and Female where typing "M" will highlight the letters "ale," allowing for autopopulation when clicked or tabbed? The same functionality should apply for typin ...

TypeOrm is struggling to identify the entities based on the directory path provided

Currently, I am utilizing TypeORM with NestJS and PostgreSql to load entities via the datasource options object. This object is passed in the useFactory async function within the TypeORM module as shown below: @Module({ imports: [TypeOrmModule.forRootAsy ...

Verify whether an email is already registered in firestore authentication during the signup process using Angular

When a user signs up for our app, I want them to receive immediate feedback on whether the email they are attempting to sign up with already exists. Currently, the user has to submit the form before being notified if the email is taken or not. This desire ...

Understanding how to interpret error messages received from a server within an Angular component

Below is the code I am using for my backend: if (err) { res.status(400).send({ error: "invalid credentials", data: null, message: "Invalid Credentials" }); } else { res.status ...

Identify numbers and words within a sentence and store them in an array

Looking to split a string into an array based on type, extracting numbers and floats. The current code is able to extract some values but not complete. var arr = "this is a string 5.86 x10‘9/l 1.90 7.00" .match(/\d+\.\d+|\d+&bsol ...

ion-grid featuring alternate columns

As someone who is not very familiar with Angular, I am trying to create a grid layout like the one shown here: https://i.stack.imgur.com/nBavk.png The desired layout includes alternating rows with one image followed by two images. My current attempt at a ...

Personalizing the arrow positioning of the Angular8 date picker (both top and bottom arrow)

I am interested in enhancing the design of the Angular 8 date picker by adding top and bottom arrows instead of the default left and right arrows. Can someone guide me on how to customize it? Check out the Angular 8 date picker here ...

Verify if the Contact Number and Email provided are legitimate

Is it possible to determine if the phone number or email entered by a user is valid or not? Using Angular 7 and Firebase? ...

How can I perform email validation using Angular 6?

I am working on an Angular6 form that includes a field for email input. Currently, the email field has proper validation which displays an error message when an invalid email is entered. However, even if the error message is shown, the form is still saved ...

Enhancing a UMD module definition with TypeScript 2: A step-by-step guide

Currently, I am in the process of creating TypeScript definition files for two libraries that are meant to be used with the new @types approach. Both libraries adhere to the UMD pattern, allowing them to be consumed either as modules or by referencing them ...