Skip to content
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

Some code written in strict mode is invalid in non-strict mode #17774

Closed
kujon opened this issue Aug 14, 2017 · 4 comments
Closed

Some code written in strict mode is invalid in non-strict mode #17774

kujon opened this issue Aug 14, 2017 · 4 comments
Labels
Working as Intended The behavior described is the intended behavior; this is not a bug

Comments

@kujon
Copy link
Contributor

kujon commented Aug 14, 2017

TypeScript Version: 2.4.0

Code

Consider the following snippet:

const EMPTY_ARRAY = [];

Typescript infers EMPTY_ARRAY to be any[] and doesn't complain even with noImplicitAny turned on. Things get weirder, when we start using this variable:

const EMPTY_ARRAY = []; // Variable 'EMPTY_ARRAY' implicitly has type 'any[]' in some locations where its type cannot be determined.

const foo = () => EMPTY_ARRAY; // Variable 'EMPTY_ARRAY' implicitly has an 'any[]' type.

We get no implicit any error in 2 places. A questionable attempt at fixing this might be to type EMPTY_ARRAY as never[] or ReadonlyArray<never> which results in no errors:

const EMPTY_ARRAY: ReadonlyArray<never> = [];

const foo = () => EMPTY_ARRAY;

Questionability of this 'fix' aside, one would expect that turning off strictNullChecks would result in the code continuing to compile, but it's not the case:

// --strictNullChecks false
const EMPTY_ARRAY: ReadonlyArray<never> = [];
/** Type 'undefined[]' is not assignable to type 'ReadonlyArray<never>'.
  Types of property 'concat' are incompatible.
    Type '{ (...items: undefined[][]): undefined[]; (...items: undefined[][]): undefined[]; }' is not assignable to type '{ <U extends ReadonlyArray<never>>(...items: U[]): never[]; (...items: never[][]): never[]; (...i...'.
      Type 'undefined[]' is not assignable to type 'never[]'.
        Type 'undefined' is not assignable to type 'never'. */

const foo = () => EMPTY_ARRAY;

Expected behavior:
Not sure how this should be fixed tbh. To me it seems like never[] is not a type that should be allowed in either mode, since mutating the array will certainly break this. ReadonlyArray<never> looks like a valid option. On top of this, I'd expect that making the compiler less strict will keep the strict code compiling.

Actual behavior:
Described above.

@DanielRosenwasser DanielRosenwasser added Bug A bug in TypeScript Needs Proposal This issue needs a plan that clarifies the finer details of how it could be implemented. labels Aug 16, 2017
@DanielRosenwasser
Copy link
Member

DanielRosenwasser commented Aug 16, 2017

Seems like the ergonomics of using [] in certain combinations are somewhat problematic. #16651 is related.

@DanielRosenwasser DanielRosenwasser added this to the TypeScript 2.6 milestone Aug 16, 2017
@RyanCavanaugh
Copy link
Member

@DanielRosenwasser what's the concrete change that's supposed to happen?

@ahejlsberg
Copy link
Member

This is working as intended. See #11432 and #13779 for context. In particular, note that in --noImplicitAny mode we perform control flow analysis to determine the type of variables initialized with [].

I'm perfectly happy to consider alternate proposals, but the currently behavior is a careful balance of performing better analysis when we can in --noImplicitAny mode while not breaking code when not in that mode.

@ahejlsberg ahejlsberg removed the Bug A bug in TypeScript label Aug 16, 2017
@mhegazy mhegazy added Working as Intended The behavior described is the intended behavior; this is not a bug and removed Needs Proposal This issue needs a plan that clarifies the finer details of how it could be implemented. labels Aug 31, 2017
@mhegazy mhegazy removed this from the TypeScript 2.6 milestone Aug 31, 2017
@mhegazy
Copy link
Contributor

mhegazy commented Sep 18, 2017

Automatically closing this issue for housekeeping purposes. The issue labels indicate that it is unactionable at the moment or has already been addressed.

@mhegazy mhegazy closed this as completed Sep 18, 2017
@microsoft microsoft locked and limited conversation to collaborators Jun 14, 2018
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Working as Intended The behavior described is the intended behavior; this is not a bug
Projects
None yet
Development

No branches or pull requests

5 participants