1

I'm testing an Angular 18 standalone component using TestBed and running into this error when the component is initialized during a unit test: Error: NG0203: inject() must be called from an injection context such as a constructor, a factory function, a field initializer, or a function used with runInInjectionContext. Find more at https://angular.dev/errors/NG0203

Below are the test cases for the component:

import { ComponentFixture, TestBed } from '@angular/core/testing';
import { SomeComponent } from './some-component.component';
import { ActivatedRoute } from '@angular/router';
import { of } from 'rxjs';

describe('SomeComponent', () => {
  let component: SomeComponent;
  let fixture: ComponentFixture<SomeComponent>;
  let mockRoute: jasmine.SpyObj<ActivatedRoute>;

  beforeEach(async () => {
    mockRoute = jasmine.createSpyObj('ActivatedRoute', ['fragment'], { fragment: of('test-anchor') });

    await TestBed.configureTestingModule({
      imports: [SomeComponent], 
      providers: [{ provide: ActivatedRoute, useValue: mockRoute }],
    }).compileComponents();

    fixture = TestBed.createComponent(SomeComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

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

Component code:

import { Component, OnDestroy } from '@angular/core';
import { LibCommonService, PLATFORM_BEHAVIOR_TYPE_ENUM, PreferencesDashboardComponent } from '@pseudoLib/pseudo-common-elements';
import { TranslateModule } from '@ngx-translate/core';
import { ActivatedRoute } from '@angular/router';
import { Subject, takeUntil } from 'rxjs';
import { NgIf } from '@angular/common';
import { DetailsService } from 'src/shared/services/details.service';
import { MEMBER_TYPE_ENUM } from 'src/shared/models/enums/details.enum';

@Component({
  selector: 'app-some',
  standalone: true,
  imports: [TranslateModule, NgIf, PreferencesDashboardComponent],
  templateUrl: './some.component.html',
  styleUrl: './some.component.scss',
})
export class SomeComponent implements OnDestroy {
  private destroy$ = new Subject<void>();

  PLATFORM_BEHAVIOR_TYPE_ENUM = PLATFORM_BEHAVIOR_TYPE_ENUM;

  projectId!: string;

  memberId!: string;

  memberType!: PLATFORM_BEHAVIOR_TYPE_ENUM;

  constructor(
    private activatedRoute: ActivatedRoute,
    private libCommonService: LibCommonService,
    private DetailsService: DetailsService,
  ) {
    this.projectId = this.libCommonService.projectIdBehaviorSub.getValue();
    this.activatedRoute.parent?.params?.pipe(takeUntil(this.destroy$)).subscribe((params) => {
      this.memberId = params.id;
    });
    this.DetailsService.memberDetails$.pipe(takeUntil(this.destroy$)).subscribe(async (memberDetails) => {
      if (memberDetails?.memberType === MEMBER_TYPE_ENUM.PRIMARY) {
        this.memberType = PLATFORM_BEHAVIOR_TYPE_ENUM.PRIMARY_MEMBER;
      } else if (memberDetails?.memberType === MEMBER_TYPE_ENUM.ASSOCIATE) {
        this.memberType = PLATFORM_BEHAVIOR_TYPE_ENUM.ASSOCIATE_MEMBER;
      }
    });
  }

  ngOnDestroy(): void {
    this.destroy$.next();
    this.destroy$.complete();
  }
}

How can I resolve the NG0203: inject() error in the test environment? Any advice on how to properly configure the test environment for a standalone component using this service would be appreciated.

Angular Version: Angular 18

1
  • 1
    issue not reproducible stackblitz please modify the stackblitz reproduce the issue and update the question Commented Apr 30 at 6:30

1 Answer 1

0

Your component code itself does not produce the error as there is no injectcall. The error must come from one of the injected services LibCommonService or DetailsService or from code you deleted for SO from the component.

Sticking with the assumption it is caused by the services:

As you want to unit test your component, you should mock those services.

await TestBed.configureTestingModule({
  imports: [SomeComponent], 
  providers: [
    { provide: ActivatedRoute, useValue: mockRoute },
    { provide: LibCommonService, useValue: { projectIdBehaviorSub: new BehaviorSubject<string>('someProjectId') } },
    { provide: DetailsService, useValue: { memberDetails$: new BehaviorSubject<MemberDetails>({ memberDetails: MEMBER_TYPE_ENUM.PRIMARY }) } },
  ],
}).compileComponents();

The error should be eliminated by eliminating those dependencies

Sign up to request clarification or add additional context in comments.

1 Comment

Don't mock ActivatedRoute, use the RouterTestingHarness instead blog.angular.dev/…

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.