镜像站点 · 本页由第三方 GitHub 只读镜像提供,非 GitHub 官方站点,不接受任何登录或凭据输入。前往 github.com
Skip to content

TS 3.9 - No overload matches this call #38241

Description

TypeScript Version: 3.9.1-rc

Search Terms:
No overload matches this call

Code

export interface SyncNgccOptions {
    basePath: string;
    targetEntryPointPath?: string;
    async?: false;
}

export type AsyncNgccOptions = Omit<SyncNgccOptions, 'async'> & { async: true };

export function process(options: AsyncNgccOptions): Promise<void>;
export function process(options: SyncNgccOptions): void;
export function process(options: AsyncNgccOptions | SyncNgccOptions): void | Promise<void> {
    return mainNgcc(options);
}


export function mainNgcc(options: AsyncNgccOptions): Promise<void>;
export function mainNgcc(options: SyncNgccOptions): void;
export function mainNgcc(options: AsyncNgccOptions | SyncNgccOptions): void | Promise<void> {
}

Expected behavior:
No error as per TS 3.8

Actual behavior:
Error

No overload matches this call. Overload 1 of 2, '(options: AsyncNgccOptions): Promise', gave the following error. Argument of type 'SyncNgccOptions | AsyncNgccOptions' is not assignable to parameter of type 'AsyncNgccOptions'. Type 'SyncNgccOptions' is not assignable to type 'AsyncNgccOptions'. Type 'SyncNgccOptions' is not assignable to type '{ async: true; }'. Types of property 'async' are incompatible. Type 'false | undefined' is not assignable to type 'true'. Type 'undefined' is not assignable to type 'true'. Overload 2 of 2, '(options: SyncNgccOptions): void', gave the following error. Argument of type 'SyncNgccOptions | AsyncNgccOptions' is not assignable to parameter of type 'SyncNgccOptions'. Type 'AsyncNgccOptions' is not assignable to type 'SyncNgccOptions'. Types of property 'async' are incompatible. Type 'true' is not assignable to type 'false | undefined'.

Playground Link: https://www.typescriptlang.org/v2/en/play?ts=3.9.0-beta#code/KYDwDg9gTgLgBASwHY2FAZgQwMbDgZQE8lsA5Ac22wHkwYEIkBnOAbwCg4u4AjTJ4AAVMMABYAuOExhRk5ANyduMTFHLAYAURRRCgiMhjCxAfknTZSBUq79i2M3CwAbAYoC+7dqEiw4MQjA8AEEmewoqWnpGFgBeOGoAWwQYAB4iEgiaOgZmABo4AHI7EkKAPjgAMjY4EuxJGQBXPHdFb3BoeHRGkmikODAoCFwmJgAKCByYyVDwymy+pgBKSUEh5IFUgDcDABMyxR9Opx7sPoGhkfHJxckMsnmo3OXJHYRdw46-bt7ci+HgKMJlNmDMwplHiCWAAfAhzSJQlZwN67OCwtYQDbAbZ7CocbhwKAaRpQfqJTDILLAxZLDxedq+Lqnc7kynzanPMHwhbPJEYrE494HBnHH5nP6spBUm6cuEQhE0157T6Mk6-RhwSXSqFc+U8mJouUPBW8pXvQ38hCbFF49ieIA

Related Issues:

Activity

  1. kitsonk commented on Apr 29, 2020

    @kitsonk
    Contributor

    It is a breaking changed covered in #37195. async? being optional is causing your problem. It was unsound code before that is now being caught.

  2. petebacondarwin commented on Apr 29, 2020

    @petebacondarwin
    Contributor

    This convoluted typing was created because we could not work out a better way to support a function that if invoked with async: true would return a Promise or void otherwise.

    Kitson Kelly (@kitsonk) - do you have a suggestion for how we can support this scenario?

  3. DanielRosenwasser commented on Apr 29, 2020

    @DanielRosenwasser
    Member

    I'm tempted to mark Working as Intended but I'm not totally clear exactly why Omit<..., "async"> & { async: true } causes issues. Anders Hejlsberg (@ahejlsberg) care to weigh in?

  4. kitsonk commented on Apr 29, 2020

    @kitsonk
    Contributor

    Daniel Rosenwasser (@DanielRosenwasser) not to step on Ander's toes, but I believe it is very intentional, because #37195 was specifically to fix unsafe situations with Omit and intersection types brought up in #36604.

  5. DanielRosenwasser commented on Apr 29, 2020

    @DanielRosenwasser
    Member

    Oh, I see - I wasn't looking at where the error was being issued. This makes sense.

    George Kalpakas (@gkalpak) technically you could condense the whole thing down to

    // Overload
    export function process<T extends AsyncNgccOptions | SyncNgccOptions>(options: T):
      T extends AsyncNgccOptions ? Promise<void> : void;
    
    // Implementation
    export function process(options: AsyncNgccOptions | SyncNgccOptions): void | Promise<void> {
        return mainNgcc(options);
    }
  6. alan-agius4 commented on Apr 30, 2020

    @alan-agius4
    ContributorAuthor

    Thanks guys for your input.

  7. gkalpak commented on Apr 30, 2020

    @gkalpak

    Thx, Daniel Rosenwasser (@DanielRosenwasser)!

    FWIW, I still find overloads more readable (and wish TypeScript would recognize the 3rd overload signature from the implementation):

    function process(options: SyncNgccOptions): void;
    function process(options: AsyncNgccOptions): Promise<void>;
    function process(options: SyncNgccOptions | AsyncNgccOptions): void | Promise<void> {
        // ...
    }
  8. locked as resolved and limited conversation to collaborators on Oct 21, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Working as IntendedThe behavior described is the intended behavior; this is not a bug

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions