Ensure that both functions share identical signatures by utilizing types exclusively

Is it possible to enforce the copy function to extend the original function, even when the parameters of the fnGenerator are in reverse order?

Can this be achieved?

function fnGenerator<Original extends Copy, Copy extends Function>(copy:Copy,original:Original){}

function original(props:{a?:number,z:number}):number { return 2}
function copy(props:{a:number}):number { return 1}

// Currently, `original` is facing compilation errors instead of `copy`
fnGenerator(copy,original)

Real usecase:

function fallback<OriginalFn extends Function>(props: {fallback:OriginalFn}) {
  return function (target: any,
   propertyKey: string, 
   descriptor: Omit<PropertyDescriptor,'value'> & { value?: OriginalFn}
) {
    return descriptor
  };
}

class MyClass1 {
  // I expect a compilation error but it works 
  @fallback({fallback: (props: {x:number,z:number})=>{ return 0} })
  static method1(pros:{x:number, z?: number}):number {
    return 1
  }
}

Answer №1

Wow, that definitely presented a challenge. Read the full discussion here.

Check out my initial solution. Unfortunately, it didn't work as expected (refer to the link for the playground)

At first, I suspected a typescript bug.

Turns out it's just method parameter bivariance.

Here's a workaround solution to tackle parameter bivariance.:

function fallback2<MethodArgs extends unknown[],MethodReturn,FallbackFn extends (...args: MethodArgs) => MethodReturn>(props: { fallbackFn: FallbackFn }) {
  return function(target: any,
    propertyKey: string,
    descriptor: TypedPropertyDescriptor<(...args: MethodArgs) => MethodReturn>
  ) {
    // implement fallback logic...
    return descriptor
  };
}

class MyClass1 {
  // I expect a compilation error because FallbackFn does not extend Method1Fn
  @fallback2({ fallbackFn: (props: { x: number,y:number }):number => { return 0 } }) // works! why??
  static method1Class1(pros: {x: number }): number {
    return 1
  }

  @fallback2({ fallbackFn: ():number => { return 0 } }) // works! why??
  static method1Class2(x:number): number {
    return 1
  }

      // I expect a compilation error because FallbackFn does not extend Method1Fn
  @fallback2({ fallbackFn: (y:number,z:number):number => { return 0 } }) // works! why??
  static method1Class3(x:number): number {
    return 1
  }

  @fallback2({ fallbackFn: (y:number,z?:number):number => { return 0 } }) // works! why??
  static method1Class4(x:number): number {
    return 1
  }
}

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

Tips on joining property name in typescript

Attempting to pass values between components using inheritance but encountering difficulties. Is it possible to achieve this through a service? If so, how can I overcome this issue? Any assistance in finding the solution would be greatly appreciated. bus. ...

Is it possible to set the initial value of useState() as null and later assign it an object value?

https://i.sstatic.net/TjAbz.png Looking at the image, I am attempting to set up a React state hook for the alert system on my website. Initially, I want no alerts to be displayed. However, when a user clicks a button, I want to show a success alert with a ...

What mistakes am I making with Typescript and jquery-ui?

Having some difficulty integrating jquery, jquery-ui, and typescript in my project. I used npm to install both jquery and jquery-ui with the following commands: npm install --save jquery npm install --save jquery-ui On my typescript file, I included them ...

Issue detected in loading ./styles.css in Angular 6

I'm a beginner with Angular 6 and encountered this error in my project: ERROR in multi ./node_modules/bootstrap/dist/css/bootstrap.min.css ./styles.css Module not found: Error: Can't resolve 'C:\Users\User\e-CommerceWebsite& ...

What could be causing the OnInit lifecycle hook to fail to execute properly?

I'm having trouble with this code. Every time I run it, the console throws a type error saying it can't read property sort. Does anyone have any ideas on how to fix this? import { Component, OnInit, Input } from '@angular/core'; impor ...

What is the importance of always catching errors in a Promise?

In my project, I have implemented the @typescript-eslint/no-floating-promises rule. This rule highlights code like this - functionReturningPromise() .then(retVal => doSomething(retVal)); The rule suggests adding a catch block for the Promise. While ...

Tips for navigating through a nested JSON object with loops

Is it possible to access the value of the Address object within an interface in Angular using *ngFor? export interface User { id: number; name: string; username: string; email: string; address: Address; } export interface Address { st ...

Clicking on the <Link to=URL> in a React application built with Typescript and Redux triggers the disappearance of the component

Issue Background The application was created using npx create-react-app rrts --typescript, which sets up React, Redux, and Typescript. Problem Visualization (Content is the component with sentences) View Problem Image Here Problem Description Clicking o ...

Defining types for functions that retrieve values with a specified default

My method aims to fetch a value asynchronously and return it, providing a default value if the value does not exist. async get(key: string, def_value?: any): Promise<any> { const v = await redisInstance.get(key); return v ? v : def_value; } W ...

The anticipated data originates from the 'style' attribute, which is formally noted within the 'IntrinsicAttributes & TextInputProps & RefAttributes<TextInput>' type

I have been working on developing a text form using typescript within the React Native framework. To accomplish this, I created a TextInput component specifically designed for email and password inputs. Below is the code I have been working with: TextInpu ...

Troubleshooting issue: Angular Typescript object array filter functionality malfunctioning

I am currently attempting to filter an array of objects based on a specific value. Interestingly, out of the console.log outputs provided below, only the first one is yielding the expected result: console.log('log1: ', sf); console.log('log ...

Angular failing to retrieve URL parameters correctly

As I was trying to retrieve URL queries like www.website.com?a:b, I decided to follow the guidance provided in a particular Angular tutorial. This official tutorial (accessible via this link) instructed me to implement the following simple code snippet wit ...

Importing a JSON or JSONC file into a vite/typescript project can be easily done

I am looking for a way to seamlessly share my routes between my actix-web backend and Vue with Vue-Router frontend without needing separate route files. I want to define the routes on the frontend without having to make any changes on the server side. If t ...

When I utilize the redux connect function, the class information in my IDE (PhpStorm/WebStorm) seems to disappear

When I use the connect function from redux, it seems to hinder my IDE (PhpStorm) from "Find Usages" on my classes. This is likely because connect returns any, causing the type information from the imported SomeClass file to be lost. export default connect ...

Tips for excluding test files in next.js when building

I am currently developing a next.js application with tests integrated within the page directory structure. In order to achieve this, I have made necessary configurations in the next.config.js file. const { i18n } = require('./next-i18next.config' ...

Creating a data type restricted to utilizing property names exclusively from a specified string union:

I have a specific Enum: enum MyEnum { optionOne = 0, optionTwo = 1, optionThree = 2, optionFour = 3, } and a related Type: export type EnumNamesList = keyof typeof MyEnum; I am looking to create a type similar to this: export type EnumDataTypes = ...

Listening for value changes on a reactive form seems to be a challenge for me

While attempting to listen for value changes on a reactive form, I ran into the following error: This expression is not callable. Type 'Observable<string | null>' has no call signatures. searchWord = this.fb.group({ word: ['' ...

What is the syntax for declaring a list of JSON objects in TypeScript?

I've been attempting to implement something similar to the following: interface IUser { addresses: JSON = []; } Unfortunately, it doesn't seem to be working! I'm looking to store a list of nested JSON objects inside the addresses field, ...

Monorepo with Yarn workspaces using Typescript and Node.JS project encounters "module not found" error while running nodemon

After creating a monorepo with yarn workspaces for a TypeScript Node.js project, I encountered an issue with local development. Despite successfully building the project, I faced errors when running yarn dev without first manually running yarn build. The e ...

The function does not yield any result

import { Injectable } from '@angular/core'; export class Test { public id: number; public name: string; public fid: number }; export const TESTS2: Test[] = [ {id: 1, name: 'Lion', fid: 1}, {id: 2, name: 'Tiger', fid: 1 ...