簡體   English   中英

如何在單元測試中注入 Input()?

[英]How to inject Input() in unit testing?

所以我嘗試對一個組件進行一些單元測試。 但是我對 Input() 參數有一些問題。 然后特別是組件中的一個組件

所以我有這個組件:


export class EcheqDisplayComponent implements OnInit {
  echeq: EcheqSubmissionApi;


  constructor(
    private route: ActivatedRoute
  ) {
    this.echeq = this.route.snapshot.data['submission'];
  }

  ngOnInit() {
  }

  getAnswers(page: EcheqPageApi): any[] {
    return page.elements.map(element => this.echeq.answers[element.name]);
  }
}

和模板:


<div class="echeq-display" *ngIf="echeq">
  <header class="echeq-display-header header">
    <div class="echeq-display-info">
      <h1 class="heading echeq-display-heading">
        {{ echeq.definition.title }}
      </h1>
      <div class="sub-heading echeq-display-subheading">
        <span class="echeq-display-creator">
          Toegekend door:
          {{ echeq.assignedByProfName ? echeq.assignedByProfName : 'Het Systeem' }}
        </span>
        <span class="echeq-display-date">{{
          echeq.definition.createdOnUtc | date: 'dd MMM'
        }}</span>
      </div>
    </div>
    <app-meta-box
      [metadata]="{
        numPages: echeq.definition.numPages,
        vPoints: echeq.definition.awardedVPoints
      }"
    ></app-meta-box>
  </header>
  <main class="echeq-display-questions body">
    <app-echeq-question
      *ngFor="let page of echeq.definition.pages; let i = index"
      [page]="page"
      [readonly]="true"
      [number]="i + 1"
      [answers]="getAnswers(page)"
    ></app-echeq-question>
  </main>
</div>


和單元測試:


import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { EcheqDisplayComponent } from './echeq-display.component';
import { ParticipantEcheqModule } from '../../participant-echeq.module';
import { RouterModule, ActivatedRoute } from '@angular/router';
import { MockActivatedRoute } from 'src/app/shared/mocks/MockActivatedRoute';
import { MetaData } from '../meta-box/meta-box.component';

describe('EcheqDisplayComponent', () => {
  let component: EcheqDisplayComponent;
  let fixture: ComponentFixture<EcheqDisplayComponent>;
  const metaData: MetaData = new MetaData();
  // const metaDataInfo = fixture.debugElement.componentInstance;


  beforeEach(async(() => {
    TestBed.configureTestingModule({
      declarations: [ ],
      providers: [
        { provide: ActivatedRoute, useClass: MockActivatedRoute }
      ],
      imports:[
        ParticipantEcheqModule

      ]
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(EcheqDisplayComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

  fit('should create component', () => {
    metaData.numPages = 20;
    expect(component).toBeTruthy();
  });
});



但它一直在說:

TypeError:無法讀取未定義的屬性“numPages”。

那么我必須改變它的工作原理嗎?

謝謝

所以 MetaData 來自 app-meta-box 組件。它看起來像這樣:


export class MetaData {
  numPages: number;
  vPoints: number;
}

@Component({
  selector: 'app-meta-box',
  templateUrl: './meta-box.component.html',
  styleUrls: ['./meta-box.component.scss']
})
export class MetaBoxComponent implements OnInit {
  @Input() metadata: MetaData;

  constructor() {}

  ngOnInit() {}

}


這是模擬 class:

export class MockActivatedRoute {
  public snapshot = {
      data: {
         submission: {
           answers: {}
         }
      }
  };
}

我現在有這樣的:

import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { EcheqDisplayComponent } from './echeq-display.component';
import { ParticipantEcheqModule } from '../../participant-echeq.module';
import { RouterModule, ActivatedRoute } from '@angular/router';
import { MockActivatedRoute } from 'src/app/shared/mocks/MockActivatedRoute';
import { MetaData } from '../meta-box/meta-box.component';

describe('EcheqDisplayComponent', () => {
  let component: EcheqDisplayComponent;
  let fixture: ComponentFixture<EcheqDisplayComponent>;
  const metaData: MetaData = new MetaData();
  // const metaDataInfo = fixture.debugElement.componentInstance;


  beforeEach(async(() => {
    TestBed.configureTestingModule({
      declarations: [ ],
      providers: [
        { provide: ActivatedRoute, useValue: new MockActivatedRoute().withData({submission:{ answers:{} } }) }
      ],
      imports:[
        ParticipantEcheqModule
      ]
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(EcheqDisplayComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

  fit('should create component', () => {
    component.echeq = {
      definition: {
        title: 'test title',
        awardedVPoints: 0,
        numPages: 9
      }
   }
    expect(component).toBeTruthy();
  });
});

But then I get this error:


Property 'answers' is missing in type '{ definition: { title: string; awardedVPoints: number; numPages: number; }; }' but required in type 'EcheqSubmissionApi'.ts(2741)
echeqSubmissionApi.ts(59, 5): 'answers' is declared here.

我現在有這樣的:

fit('should create component', () => {
    component.echeq = {
      definition: {
        title: 'test title',
        awardedVPoints: 0,
        numPages:9
      }
    } as EcheqSubmissionApi;
    expect(component).toBeTruthy();
  });
export interface EcheqSubmissionApi { 
    /**
     * Primary key of this submission (server set).
     */
    id?: string;
    definition?: EcheqDefinitionApi;
    /**
     * Id of the prof who assigned this eCheq (server set).
     */
    assignedByProfId?: string;
    /**
     * Name of the prof who assigned this eCheq (server set). Only set on get operations. May be null if assigned by the system.
     */
    assignedByProfName?: string;
    /**
     * Id of the organisation who assigned this eCheq (server set).
     */
    assignedByOrgId?: number;
    /**
     * Participant ID of the patient this eCheq is assigned to (server set).
     */
    assignedToId?: string;
    /**
     * When this submission was assigned (UTC, server set).
     */
    assignedOnUtc?: Date;
    /**
     * If set until when the eCheq can be submitted.
     */
    validUntilUtc?: Date;
    /**
     * Whether the eCheq has been started and whether it has been submitted (server set).
     */
    status?: EcheqSubmissionApi.StatusEnum;
    /**
     * When this submission was completed (UTC, server set).
     */
    submittedOnUtc?: Date;
    /**
     * Answers of form.  In the form of a json object with name and value of the questions  {      \"nameOfQuestion\" : \"valueOfQuestion\"  }
     */
    answers: object;
    /**
     * initialValues of form.  In the form of a json object with name and value of variables  {      \"nameOfQuestion\" : \"valueOfQuestion\"  }
     */
    initialValues?: object;
    /**
     * The page the participant is currently on
     */
    currentPage?: number;
    /**
     * The progress of the echeq in percentage
     */
    progress?: number;
}
export namespace EcheqSubmissionApi {
    export type StatusEnum = 'New' | 'Active' | 'Submitted';
    export const StatusEnum = {
        New: 'New' as StatusEnum,
        Active: 'Active' as StatusEnum,
        Submitted: 'Submitted' as StatusEnum
    };
}

但是,如果我運行單元測試,我仍然會收到此錯誤:

TypeError: Cannot read property 'numPages' of undefined

要回答您的問題:

component.metadata = /// whatever you want this to be

您對numPages: echeq.definition.numPages有錯誤。 Endeed, echeq也是未定義的。

你可以試試:

component.echeq = {
   definition: {
     numPages: 9
   }
}

或者更好的方法是從this.route.snapshot.data['submission'];返回這個值。 所以從MockActivatedRoute

更新

並更新MockActivatedRoute以允許動態參數:

export class MockActivatedRoute {
  snapshot = {
      data: {}
  };

  constructor(){}

  withData(data:any): MockActivatedRoute {
     this.snapchot.data = data;
     return this;
 }
}

所以現在在你的測試中,你可以使用它:

{ provide: ActivatedRoute, useValue: new MockActivatedRoute().withData({submission:{ answers:{} } }) }

沒問題。 這很容易:

beforeEach(async(() => {
    TestBed.configureTestingModule({
      providers: [
      ],
      imports:[
        ParticipantEcheqModule,
        RouterTestingModule
      ]
    })
    .compileComponents();
  }));

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM