Skip to content

Function return type inferrence expecting () => undefined may refine impl to () => void which breaks #49400

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
paul-marechal opened this issue Jun 6, 2022 · 4 comments
Labels
Duplicate An existing issue was already created

Comments

@paul-marechal
Copy link

Bug Report

When defining interfaces with methods returning undefined, it would help if TypeScript could properly infer that the implementation does return undefined and not just void.

Maybe related: TS2355 A function whose declared type is neither 'void' nor 'any' must return a value. should include return types including undefined in its exception set for functions that don't require an explicit return statement.

🔎 Search Terms

undefined function void

🕗 Version & Regression Information

⏯ Playground Link

Playground link with relevant code

💻 Code

interface Test {
    method1(): Promise<string | undefined>
    method2(): string | undefined
}

const impl: Test = {
    method1: async () => {
        console.log('why bug 1')
    },
    method2: () => {
        console.log('why bug 2')
    }
}

class Impl implements Test {
    async method1(): Promise<undefined> {
        console.log('why bug 3')
    }
    method2(): undefined {
        console.log('why bug 4')
    }
}

🙁 Actual behavior

The impl assignment fails because it evaluates impl.method1 as () => Promise<void> and impl.method2 as () => void.

For the snippet to work we have to write unnecessary boilerplate:

const impl: Test = {
    method1: async (): Promise<undefined> => {
        console.log('why bug 1')
        return
    },
    method2: (): undefined => {
        console.log('why bug 2')
        return
    }
}

🙂 Expected behavior

I would expect TypeScript to type impl.method1 as () => Promise<undefined> and impl.method2 as () => undefined based on the expected type of impl being defined and the fact that the implementations do in fact return undefined written as is.

Moreover, we get error 2355 in the class Impl saying A function whose declared type is neither 'void' nor 'any' must return a value.

I would argue that TS could expand the explicit return value exception to return types including undefined.

@RyanCavanaugh
Copy link
Member

Duplicate #36288

@RyanCavanaugh RyanCavanaugh added the Duplicate An existing issue was already created label Jun 6, 2022
@fatcerberus
Copy link

fatcerberus commented Jun 6, 2022

() => undefined can't be treated as synonymous with () => void because the latter allows a function with any return type to be substituted for it. For example if you ask for () => void then I can give you a () => number since void acts as a promise that you're going to ignore the return value. On the other hand if you ask for a () => undefined, then I can only give you something that explicitly returns undefined.

@paul-marechal
Copy link
Author

@fatcerberus consider the following playground: In this issue I try to describe how TS should better infer method definitions to match the expected type, as well as allowing implicit return statements when dealing with return types including undefined.

@paul-marechal
Copy link
Author

After reading #36288 in more detail it looks like what I was after, sorry for the duplicate.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Duplicate An existing issue was already created
Projects
None yet
Development

No branches or pull requests

3 participants