Using Typescript to overload functions with varying first parameters

I am facing a scenario where I have a parent class that requires a method implementation with either one or two parameters depending on the child class.

class MyClass { 
    update(obj: HashMap);
    update(id: ID, obj: HashMap);
    update(objOrId: HashMap | ID, obj?: HashMap) {
      console.log('I need to use only the first parameter here');
    }
}

class SubClass extends MyClass {
    update(id: ID, obj: HashMap) {
      console.log('Here I need to utilize both parameters');
    }
}

The issue arises when the SubClass raises an error indicating that the update signature does not match the base class. How can this situation be resolved?

Answer №1

Upon execution, an error will be generated with the following message:

The property 'update' within the type 'SubClass' cannot be assigned to the same property in the base type 'MyClass'.

The type

'(id: ID, obj: HashMap) => void'
is not compatible with the type
'{ (obj: HashMap): any; (id: ID, obj: HashMap): any; }'
.

The reason behind this error lies in the requirement that when overriding a method, it must possess the exact identical type as the original method. As the method in `MyClass` is of an overloaded type with two alternatives, while the overridden method only has one.

Hence, it is imperative to explicitly specify the exact overloads even if they are not strictly needed in the subtype:

class SubClass extends MyClass {
    update(obj: HashMap);
    update(id: ID, obj: HashMap);
    update(objOrId: HashMap | ID, obj?: HashMap) {
      console.log('here I want to use both params');
    }
}

Keep in mind that TypeScript will solely emit the ultimate function definition, without any runtime validation for the parameter types. Therefore, you still need to handle scenarios where only a `HashMap` may be passed to your instance of `SubClass`. This consideration is especially crucial in light of the Liskov substitution principle, which dictates that any instance of `SubClass` should be usable as an instance of `MyClass`; hence passing just a `HashMap` is perfectly acceptable.

Example on TypeScript playground

Answer №2

To ensure compatibility, it is essential to include the public overload signatures in your class. The visibility of the implementation signature is limited, and only the public signatures are checked for compatibility. If these signatures are missing, an error will be triggered by the compiler:

class CustomClass extends BaseClass {
    update(obj: Record<string, any>): void;
    update(id: number, obj: Record<string, any>): void;
    update(objOrId: Record<string, any>, obj?: Record<string, any>): void{
    console.log('Here I intend to utilize both parameters');
    }
}

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 Typescript error when trying to pass a function as a prop that returns SX style

Imagine a scenario where a parent component needs to pass down a function to modify the styles of a reusable child component: const getStyleProps: StyleProps<Theme> = (theme: Theme) => ({ mt: 1, '.Custom-CSS-to-update': { padding ...

Steps for creating a TypeScript class that can implement an interface

As a beginner in TypeScript, I am looking for help with the following code snippet: async function sleep(ms: number) { return new Promise((resolve, reject) => { setTimeout(() => resolve(), ms) }) } async function randomDelay() { ...

Delay the execution until all promises inside the for loop are resolved in Angular 7 using Typescript

I am currently working on a project using Angular 7. I have a function that contains a promise which saves the result in an array as shown below: appendImage(item){ this.imageCompress.compressFile(item, 50, 50).then( result => { this.compressedI ...

Reduce the size of log messages in cypress

I am looking to shorten the cypress messages to a more concise string, for instance: Cypress log Transform to: -assert expected #buy-price-field to have value 17,169.00. Is there a way to achieve this? I have searched through the documentation but hav ...

Ensure your Vue components have type-checked props at compile time when using TypeScript

I have encountered an issue while using Vue.js with Typescript. The code I am working with is pretty straightforward, utilizing vue-class-component and vue-property-decorator. <script lang="ts"> import { Component, Prop, Vue } from 'vue-pro ...

The 'Set-Cookie' response header failed to be recognized for a subsequent HTTP request

When a user successfully logs in, their information is stored in a cookie using the "Set-Cookie" response header. However, I am facing an issue where the cookie seems to get lost when making subsequent requests from the client. As a result, the server trea ...

Error: Unable to call function onPopState from _platformLocation due to TypeError

After building an angular application, I encountered a strange issue where it runs smoothly in non-production mode but throws an error when running with --prod: Uncaught TypeError: this._platformLocation.onPopState is not a function I have double-checked ...

Enhance your TypeScript code using decorators with inheritance

Exploring the realm of Typescript decorators has led me to discover their intriguing behavior when combined with class inheritance. Consider the following scenario: class A { @f() propA; } class B extends A { @f() propB; } class C exten ...

Having trouble with Angular 2 when submitting a form

Whenever I try to submit a form with two input fields and one select list, the submitted value for the select list is always 0. I am unsure where I am making a mistake. When I post this form to an API, all values are correct except for the select list valu ...

RxJS BehaviorSubject allows you to retrieve the current value or obtain a new one depending on a specific condition

I am managing a subject that consumers subscribe to: private request$: Subject<Service> = new BehaviorSubject(null); Upon initialization, my components utilize this function: public service(id: number): Observable<Service> { return this. ...

Encountering Issues with TypeScript Strict in Visual Studio Code Problems Panel

I have discovered that I can optimize my TypeScript compilation process by utilizing the --strict flag, which enhances type checking and more. Typically, I compile my TypeScript code directly from Visual Studio Code with a specific task that displays the c ...

VS Code failing to detect Angular, inundated with errors despite successful compilation

Having some issues with loading my angular project in vscode. It used to work fine, but suddenly I'm getting errors throughout the project. I have all the necessary extensions and Angular installed. https://i.stack.imgur.com/qQqso.png Tried troubles ...

Struggling to iterate through JSON data in Office Scripts?

My task involves parsing JSON data in Office Scripts to extract the headings and row details on a spreadsheet. While I have successfully fetched the data, I am encountering an error message stating that my information is not iterable at the "for" loop. ...

Utilizing mapped types in a proxy solution

As I was going through the TS Handbook, I stumbled upon mapped types where there's a code snippet demonstrating how to wrap an object property into a proxy. type Proxy<T> = { get(): T; set(value: T): void; } type Proxify<T> = { ...

I'm struggling to get a specific tutorial to work for my application. Can anyone advise me on how to map a general URL to the HTTP methods of an API endpoint that is written in C

I am struggling to retrieve and display data from a C# Web API using Typescript and Angular. As someone new to Typescript, I followed a tutorial to create a service based on this guide: [https://offering.solutions/blog/articles/2016/02/01/consuming-a-rest- ...

Ways to specify the T (Generic type) associated with the class

I am working with a class that uses a generic type like this: SomeGenericClass<T>{ constructor(){ } } Within some of the functions, I log messages and want to refer to the current type T of the generic class in my logs. I have attempted t ...

The discord.js TypeScript is throwing an error stating that the 'index.ts' file is missing when trying to run 'ts-node index.ts'

I have been working on creating a discord bot using discord.js and TypeScript. However, when I attempt to start the bot by running 'ts-node index.ts', I encounter the following error: Error: Cannot find module 'node:events' Require stac ...

Exclude the key-value pair for any objects where the value is null

Is there a way to omit one key-value pair if the value is null in the TypeScript code snippet below, which creates a new record in the Firestore database? firestore.doc(`users/${user.uid}`).set({ email: user.email, name: user.displayName, phone: ...

The argument provided needs to be a function, but instead, an object instance was received, not the original argument as expected

I originally had the following code: const util = require('util'); const exec = util.promisify(require('child_process').exec); But then I tried to refactor it like this: import * as exec from 'child_process'; const execPromis ...

Tips for successfully typing the backtick character when transitioning to Typescript:

I am currently working on a Typescript Vue project involving Leaflet. I came across some code for lazy-loading map markers, but it was written in Javascript. Although the code works fine, I keep receiving errors and warnings from VSCode because this is not ...