Tips for creating unit tests for my Angular service that utilizes the mergeMap() function?

As a beginner with the karma/jasmine framework, I am currently exploring how to add a test case for my service method shown below:

public getAllChassis(): Observable<Chassis[]> {
      return this.http.get('chassis').pipe(
            mergeMap((result: Chassis[]) => {
               for (const chassis of result) {
                  chassis.healthStatus = 45;
                  chassis.complianceStatus = 81;
               }
               return of(result);
            }));
   }

I noticed that the current tests do not adequately cover the callback/inside pipe statement. Can someone guide me on the proper way to test the mergeMap pattern in this scenario?

Answer №1

Not quite sure if using mergeMap is the best approach here. It would be wise to verify that.

Here is my method of testing a function from a service that executes an HTTP request and returns an observable.

1 - Create a Mock HTTP client

Below is an illustration of how I handle this in an Angular project, leveraging TestBed for dependency injection.

let httpClient: HttpClient;
let service: YourService;
beforeEach(() => {
    TestBed.configureTestingModule({
        imports: [HttpClientTestingModule],
        ...
        }).compileComponents();
    httpClient = TestBed.get(HttpClient);
    service = TestBed.get(YourService);
});

2 - Spy on the mock function

To ensure the expected result from the get request, it's crucial to spy on it and provide a simulated outcome.

describe("WHEN: getAllChassis", () => {
  beforeEach(() => {
    const RESPONSE_MOCK = of(
      new HttpResponse({
        body: {
          /* sample data your service provides */
        },
      })
    );
    spyOn(httpClient, "get").and.returnValue(RESPONSE_MOCK);
  });

  // Your test goes here
});

3 - Validate your function output

When testing your feature, ensure that it produces the expected result (considering the anticipated response from http.get).

Note the use of done due to the async nature of the function. The test will only conclude when done is called (or upon timeout).

it("THEN: should return data", (done) => {
  getAllChassis()
    .pipe(take(1))
    .subscribe((data) => {
      expect(data).toEqual({
        /* expected outcome */
      });
      done();
    });
});

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

Validating dynamic textboxes in Angular with custom rules

Creating dynamic textboxes with *ngFor in Angular <tr *ngFor="let computer in _Computers; let i = index;"> <td>{{computer.Name}}</td><td>{{computer.Optional}}</td> <td> <input matInput [formControl] = " ...

Develop a TypeScript class in a distinct file

I currently have ag-grid implemented in an Angular project with a CustomFilter. The problem is that the file containing the code for the CustomFilter function is becoming quite large and difficult to manage. I am now looking to move the CustomFilter to a s ...

Encountering a TypeScript error when using Redux dispatch action, specifically stating `Property does not exist on type`

In my code, there is a redux-thunk action implemented as follows: import { Action } from "redux"; import { ThunkAction as ReduxThunkAction } from "redux-thunk"; import { IState } from "./store"; type TThunkAction = ReduxThunk ...

The Angular 2 service is not transmitting the POST data in the correct format, although it functions properly when transmitted through PostMan

When the POST data is transmitted from the Angular 2 service in this manner: const data = new FormData(); data.append('date', '12/01'); data.append('weight', '170'); return this.http.post(this.u ...

Create an observable array that contains both outer and inner response properties within an Angular application

How can I create an Observable array in Angular by making API calls based on the response of another API call, which returns an array of elements? For example: queryThatReturnsArray().pipe( switchMap((outerResponse) => { return forkJoin(out ...

Facing a problem with running npm start on jHipster

I am currently working on a jhipster project on my MacBook Pro running macOS Mojave v.10.14.4. After successfully compiling with npm start, the code continues to compile multiple times without any changes. Eventually, it throws the following error: DONE ...

What could be causing my data to undergo alterations when transitioning from a frontend form submission to a backend API?

In my experience with Next.js 13 and Prisma, I encountered a peculiar issue. I had set up a basic form to collect user information for an api request. Oddly enough, when I printed the data right before sending it, everything seemed fine. However, upon arri ...

One way to ensure a necessary check on the mat-expansion-panel

Currently, I am working on a form that includes an upload panel (mat-expansion-panel) for uploading documents. My goal is to indicate that this panel is required by adding an asterisk (*) next to it. While I know how to add the asterisk to <textarea&g ...

Exploring the generalization of class member initialization in TypeScript

I am looking to make some modifications to the Blog constructor provided in the "Minimal working example" linked below. The objective is to refactor it using pseudo-code by leveraging a generic ModelHelper class to initialize the members of the "Blog" clas ...

Unable to enhance Request using Typscript in nodejs

In my middleware, I am attempting to enhance the Request by adding a property called user. However, I encountered this error: Property 'user' does not exist on type 'Request<ParamsDictionary, any, any, ParsedQs>' I am trying to u ...

Deactivate specific choices from a dynamically generated dropdown menu in Angular 8

I am working on a dynamic dropdown feature with multiple fields. By pressing the + button, a new row is generated. Users can add any number of rows. My challenge is to prevent users from selecting previously chosen values in the dropdown list. I have ma ...

Converting custom JSON data into Highcharts Angular Series data: A simple guide

I am struggling to convert a JSON Data object into Highcharts Series data. Despite my limited knowledge in JS, I have attempted multiple times without success: Json Object: {"Matrix":[{"mdate":2002-02-09,"mvalue":33.0,"m ...

Chart.js Axis Labels Orientation Guidelines

I am currently utilizing chart.js within an Angular 8 environment using Primeng. I am looking to customize the options for my chart as follows: For the y-axis ticks, set textDirection to 'ltr' For the x-axis ticks, set textDirection to 'rtl ...

Updating FontAwesome icon in Angular 10

I have successfully configured and implemented FontAwasome Pro in my Angular 10 project. <div class="update-split" [class]="testClass"><fa-icon [icon]="['fad', 'sync-alt']"></fa-icon></ ...

Troubleshooting issue with Angular 2 form values not binding correctly when set and disabled

Here is my code for updating the form if the user's information is available. if (this.user.landmark) this.uploadForm.controls['landmark'].setValue(this.user.landmark || ''); // Uncommenting disable will result in the landmark ...

Conceal a designated column within a material angular data table based on the condition of a variable

In the morning, I have a question about working with data tables and API consumption. I need to hide a specific column in the table based on a variable value obtained during authentication. Can you suggest a method to achieve this? Here is a snippet of my ...

The Angular/Express application is in search of outdated JavaScript files within the Chrome browser

When updating and deploying my Angular web app on Google App Engine with an Express server, I encounter a peculiar issue. Upon refreshing the browser, I sometimes face a blank page accompanied by the following error: main.f2b54282bab6f51a.js:1 Failed to lo ...

What is the method for accessing HttpEvent progress during a file upload in Angular 5?

Despite going through the angular.io documentation and other responses on Stack Overflow, I am still struggling to understand how to track file upload progress for my POST request from Angular 5 to NodeJS and then display it to the user. Here is what my c ...

Protractor experiencing difficulty recognizing Angular functionality

Recently, I made the switch to using Protractor for running end-to-end tests on my Angular application. However, the e2e tests have suddenly started failing because Protractor is unable to detect Angular on the website. I raised this issue in their GitHub ...

What causes the variable assigned in the outer subscription's scope to change as the inner subscriptions change?

In my Angular 6 code snippet provided below, I am facing an issue: ngOnInit() { this.route.queryParams.subscribe((params: Params) => { const stuffId: string = params.stuffId; this.service.getState().subscribe((state) => { ...