Function in Typescript that accepts an extended interface as a parameter

I am facing an issue with my interface named "Example" which has a function type called "exampleFunction". The problem arises when this function takes a super class as an input parameter because TypeScript is reporting an error. It states that I cannot use subtypes as inputs due to some properties that are not present in the superclass.

Here's an illustration:

interface SuperType {
   propertyA: string
}

interface SubTypeA extends SuperType {
   subPropertyA: number
}

interface SubTypeB extends SuperType {
   subPropertyB: number
}

interface Example {
   exampleFunction: (input: SuperType) => void
}

The issue occurs when I write:

const example: Example = {
   exampleFunction: (input: SubTypeA) => {console.log("nothing")}
}

Answer №1

If you modify your function to utilize only the property of SubTypeA, the issue becomes more apparent.

const example: Example = {
   exampleFunction: (input: SubTypeA) => {console.log(input.subPropertyA.toFixed())}
}

The function itself is technically correct (it takes a SubTypeA argument and accesses one of its properties). However, the type definition of Example can only ensure that a SuperType will be passed in. Therefore, the additional unique properties of SubTypeA cannot be guaranteed to be present.

For instance:

const superType: SuperType = { propertyA: 'foo' }
example.exampleFunction(superType)
// This call is valid but crashes as `subPropertyA` is missing

One possible solution could be to adjust your function to handle either a SuperType or a SubTypeA:

const example: Example = {
   exampleFunction: (input: SuperType | SubTypeA) => {
       if ('subPropertyA' in input) {
            console.log(input.subPropertyA.toFixed())   
       }
    }
}

const superType: SuperType = { propertyA: 'foo' }
example.exampleFunction(superType) // works

const subTypeA: SubTypeA = { propertyA: 'foo', subPropertyA: 123 }
example.exampleFunction(subTypeA) // works

Playground

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

How to convert typescript path aliases into relative paths for NPM deployment?

I am currently working on a typescript project that utilizes paths for imports. For instance: "paths": { "@example/*": ["./src/*"], } This allows the project to import files directly using statements like: import { foo } from "@example/boo/foo"; Whe ...

Express.js - Monitoring for server closure

I have a Node.js application that utilizes Express. Within this application, there is a section of code structured as follows: const app = require('./app'); const port = process.env.PORT || 8080; const server = app.listen(port); server.on(&apos ...

Updating the content within the main body of the page rather than the sidebar in react-router v5

I have a question regarding the functioning of my sidebar and content. So, when I click on any item in the sidebar, the content changes accordingly. But what if I want to change the route directly from the content itself? That's where I'm facing ...

The Jasmine test is having trouble locating the imported variable

In my Angular project, I have a class set up as follows: import { USERS } from "./data/users"; // imports an Array of Objects export class User { constructor(name: string) { const user = USERS.find(e => e.name === name); } ... } Every ...

Positioning Avatar component at the center of Card component

Hello there, I am currently trying to center my <Avatar> elements using Material UI with React within the <Card> components. The layout appears very crowded right now. What would be the most effective method to achieve this? I attempted setti ...

Displaying data on the user interface in Angular by populating it with information from the form inputs

I am working on a project where I need to display data on the screen based on user input received via radio buttons, and apply specific conditions. Additionally, I require assistance in retrieving the id of an object when the name attribute is chosen from ...

Firefox has various problems, but it functions flawlessly in Chrome without any problems

I seem to be encountering various issues in Firefox that do not occur in Chrome. 1) I am facing a TypeError: response.body is null. 2) Another issue arises when uploading images, resulting in a TypeError: Argument 1 of FormData.constructor does not imple ...

The Firefox tab continues to load endlessly due to an embedded iframe

As I test an HTML page on Firefox Developer, I encounter an issue with an iframe. While the iframe works fine on Google Chrome, it causes the parent page to continuously load on Firefox. This leads to a degradation in performance after a few minutes. The i ...

Tips for stopping TypeScript code blocks from being compiled by the Angular AOT Webpack plugin

Is there a way to exclude specific code from Angular's AOT compiler? For instance, the webpack-strip-block loader can be utilized to eliminate code between comments during production. export class SomeComponent implements OnInit { ngOnInit() { ...

Adding a custom class to a select2 dropdown: How can it be done?

I have customized select2 using CSS with its general classes and IDs. Currently, I am attempting to customize a specific class that will be assigned to select2 and then applied in the CSS. The problem lies not within the select itself, but within its dro ...

Animating number counters in Ionic 3 with Angular

Displayed in my user interface is a simple number, nothing fancy. <ion-label>{{myCount}}</ion-label> Next to the number, there is a button labeled "reset." When pressed, the counter resets to 0. This functionality works well with a basic func ...

Activate CSS element with a click

Is there a way to add a click event to a CSS class so that when it is clicked, it changes to a different class? I am specifically looking to change the character class on li items when they are clicked. Here is the code snippet: <!DOCTYPE html> <h ...

Obtain JSON data through an HTTP POST call

Here is a function that I have, which was mainly borrowed from the solution to another problem on SO: function sendPostRequest(url, data) { request( { url: url, method: "POST", json: true, body: data }, function(error, response, body) ...

Is it beneficial to vary the time between function calls when utilizing setInterval in JavaScript?

My website is displaying two words one letter at a time, with a 0.1s delay between letters and a 3s pause after each full word. I attempted using setTimeout, but it's not functioning as expected. What could be the issue in my code? var app = angular. ...

Is the Vue "Unchecking" feature not properly deleting data from the array?

I need to update my function to handle the removal of a networkAudience when its corresponding checkbox is unchecked. Currently, the networkAudience is being added to the array when checked, but not removed when unchecked. What changes should I make to en ...

I am utilizing Python Django to display a message from a Python file in HTML. While the current code is functional, I would like the message to be showcased as a pop-up or alert notification

Using Python Django. The message is coming from a Python file and I would like to display it in HTML. The current code is functioning, but I would like the message to appear as a pop-up or alert. Register {% if messages %} {% for result in messages %} < ...

In JavaScript, the "this" keyword points to a different object

Here is a script that needs attention: Bla = function() { this.prop = 123; } Bla.prototype.yay = function() { console.log(this,this.prop); } X = new Bla(); $(document).ready(X.yay); // output: #document undefined --> why? $(document).ready(functio ...

How do I customize the appearance of console.log messages stored in a string variable?

Looking to enhance the appearance of my console log output in a JavaScript script by utilizing different styling options. Here's a sample scenario: s=`Title 1 \n This is some text that follows the first title`; s=`${s} \n Title 2 \n T ...

The feature of scrolling to a specific element within a bootstrap modal is not functioning as expected

I recently encountered an issue while using a Bootstrap modal. The problem arose when I tried to scroll to a specific element within the modal, but my code didn't produce the desired results. $('#centralModalLg').on('show.bs.modal&apo ...

Angular 2: Implementing a Class Addition with a Delay

I'm attempting to animate a list of items in Angular 2, but for some reason, it's not working at all. What I'm doing is retrieving a HTMLCollection using getClass and then adding a class with a timeout. platform.ready().then((readySour ...