What is the best way to implement the trackBy function in Angular 14 with strict-mode enabled?

I am facing an issue while trying to use trackBy in angular 14 with strict-mode: true,

Here is the code (which works perfectly fine in strict-mode: false)

app.component.html:

<div *ngFor="let item of items; index as i; trackBy: trackByFn">
  {{ i + 1 }} {{item.name}}
</div>


<br>

<button (click)="addSomething()">Load Data</button>

app.components.ts

import { Component } from '@angular/core';

interface DemoArray {
  id: number;
  name: string;
}

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css'],
})
export class AppComponent {
  title = 'angular-sandbox';

  public items: DemoArray[] = [
    { id: 0, name: 'Apfel' },
    { id: 1, name: 'Mango' },
    { id: 2, name: 'Birne' },
  ];

  public addSomething(): void {
    this.items = [
      { id: 0, name: 'Apfel' },
      { id: 1, name: 'Mango' },
      { id: 2, name: 'Birne' },
      { id: 3, name: 'Kiwi' },
      { id: 4, name: 'Mandarine' },
      { id: 5, name: 'Banane' },
    ];
  }

  trackByFn(item) {
    return item.id;
  }
}

While using strict-mode:true and changing the trackByFn to:

  trackByFn(item: { id: any }) {
    return item.id;
  }

VSCode indicates the following error:

Type '(item: { id: any; }) => any' is not assignable to type 'TrackByFunction'.ngtsc(2322) app.component.ts(8, 44): Error occurs in the template of component AppComponent.

Answer №1

Utilizing strict mode in Angular offers various benefits:

  • Enforces strict mode in TypeScript
  • Implements a strict angular compiler with strictTemplates, strictInjectionParameters, and strictInputAccessModifiers
  • Reduces bundle size budget

The usage of strictTemplates ensures that types on templates are rigorously checked, similar to how it is done in TypeScript.

In the example provided, the trackBy method expects a function of type TrackByFunction. However, the current implementation of trackByFn does not adhere to this type.

interface TrackByFunction<T> {
  <U extends T>(index: number, item: T & U): any
}

To resolve this issue, the trackByFn function should align with the signature defined by the TrackByFunction interface.

trackByFn(index: number, item: { id: any }) {
   return item.id;
}

Answer №2

By making a simple alteration to the function:

  updateId(index: any, item: { id: any }) {
    if (item) {
      return item.id;
    } else {
      return undefined;
    }
  }

This modification worked perfectly for me!

Answer №3

If you prefer not to use the Type any, your second parameter must align with the Type of iterable element in ngFor.

An example is when iterating over a FormGroup:

<div *ngFor=let formGroup of formArray.controls; trackBy: trackById>
    <!-- insert code here -->
</div>
public formArray: FormArray;

public trackById(_index: number, item: FormGroup | AbstractControl) {
    return item.value.id;
}

Check out the Angular Documentation

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

Deploying a Typescript node application using pm2 for process management

When it comes to deploying a node app written in typescript using pm2, the process can be a bit tricky. The source code is typically stored on a git repository, with the remote machine having an ssh connection to git. The standard workflow for deployment ...

Angular Dynamic Alert Service

Is it possible to customize the text in an Angular Alert service dynamically? I'm looking to make certain words bold, add new lines, and center specific parts of the text. Specifically, I want the word "success" to be bold and centered, while the rest ...

Managing Your State: Implementing a Full State Replacement Using ngrx

Looking for guidance on loading app state from localStorage after successfully saving it using ngrx operators. While I've managed to save the data, I'm unsure about how to properly load it back. export class DataService { constructor(private s ...

What causes the lack of minlength validation when the form is in its initial state?

Check out the code snippet below: <input [(ngModel)]="someProperty" minlength="5" /> I recently ran my app and used the browser debugger tool to inspect the state of this input field. Surprisingly, I noticed that it was marked as ...

Tips for positioning dropdown to the right in Bootstrap and Angular?

Could you please provide some guidance on how to align a dropdown to the right in Bootstrap and Angular? Below is the code that I have been working on: https://stackblitz.com/edit/angular-4risp3?file=src%2Fapp%2Fapp.component.html https://i.sstatic.net/kB ...

Using TypeScript with Vue: Safely accessing component properties in a type-safe manner

I am currently exploring Vue's setup API and there is one aspect that I am struggling with: I need to retrieve properties of a child component from a parent component. Everything seems to be functioning correctly, but I am facing difficulties with the ...

Importing and viewing an Excel spreadsheet containing images in a specific column

I am currently working on an Angular project where I am implementing a feature to upload an excel file. The excel file contains text data in one column, and another column specifically contains images labeled as D1, D2, D3, and so on. While attempting to ...

Dealing with asynchronous operations in a pipeline with fp-ts

I'm currently exploring fp-ts and have been contemplating how to restructure my functions in order to steer clear of nested folds. While many online examples showcase a clean invocation of the pipe function, I am struggling to eliminate the nested fol ...

Using TypeScript to conditionally type input arrays

My goal is to create a function that accepts an array of variables that can belong to a few different types. For each specified type, the second argument (callback) of the function will receive an array of corresponding types. The relationship is such th ...

position the tooltip within the ample available space of a container in an angular environment

In my editor, users can create a banner and freely drag elements within it. Each element has a tooltip that should appear on hover, positioned on the side of the element with the most space (top, left, bottom, right). The tooltip should never extend outsid ...

Component not appearing in Storybook during rendering

I'm trying to incorporate the MUI Button Component into my storybook and then dynamically change MUI attributes like variant, color, and disabled status directly from the storybook. While I was successful in doing this with a simple plain HTML button, ...

Can you explain the process of downloading a file using Rest API in spring boot?

I have a Spring Boot backend and an Angular 7 frontend application. I am looking to implement file upload and download functionalities in my backend code. @Entity @Table public class File extends BaseEntity { private String fileName; priva ...

Encountered a problem while installing an npm package for Angular 2

I seem to be encountering an error when trying to run the npm install command in the command prompt behind my corporate proxy firewall. Previously, I was able to edit the npm file with the proxy settings, but now I receive this error no matter what npm com ...

Error: XYZ has already been declared in a higher scope in Typescript setInterval

I've come across an interesting issue where I'm creating a handler function and trying to set the current ref to the state's value plus 1: const useTimer = () => { const [seconds, setSeconds] = useState(0); const counterRef = useRef(n ...

How can I retrieve JSON data that is specific to the selected item in an Ionic Angular application?

Exploring the world of ionic-angular framework, I have a home page with a modal embedded within it. The home page displays a list of items fetched from a JSON file, and upon clicking on a specific item, I wish to display all the information related to that ...

Is it possible for Typescript to encounter an error when using console.log() with a variable of type "any"?

When using console.log(variable: any) in Typescript, I am concerned about potential errors and avoiding the need for try{}catch blocks throughout my code. Will console.log(any) trigger any errors or will it successfully print any input provided? public ...

Sending geographic coordinates from a child component in a React application using Google Maps to its parent component within a functional

My current project involves creating a map component in my React application using @googlemaps/react-wrapper. I followed the example from Google Maps and successfully added an event to refresh coordinates when dragging the marker. Now, I need to call the m ...

Displaying data on a webpage using interpolation in HTML

I'm struggling to display user information on my HTML template. I can't seem to figure out what I'm doing wrong. Essentially, I want to retrieve values from the database and dynamically insert them into the main page for display. My issue li ...

What is the official name of the key type for the Built-in Object?

There was a built-in type that I used in the past which represented the union of all possible object keys. It was named objectKey or something similar. Here is an example: type objectKey = string | number | symbol Unfortunately, I am drawing a blank on t ...

Nested validation schema featuring conditional validation - yes, we've got it covered!

In my Formik object, I have set initial values as follows: {customerDetails: {id: "", name: "", mobileNumber: ""}, notes: {id: "", text: "", type: ""}} How can I create a conditional Yup validati ...