Skip to content

Design Meeting Notes, 5/29/2020 #38905

Closed
Closed
@DanielRosenwasser

Description

@DanielRosenwasser

Variadic Types and Variadic Tuples

#5453

  • 2nd-highest most-upvoted.
  • A lot of slicing and dicing (and splicing) on tuples
  • Proposal: Variadic Kinds -- Give specific types to variadic functions #5453 is a broad issue, but we've been thinking about what it would take to power up a lot of the scenarios.
  • Today, a tuple type is comprised of some combination of [FixedTypes, OptionalTypes?, ...OneRestType[]]
  • What if we loosened the restrictions?
    • Allow you to put spreads earlier: [number, ...string[], boolean
    • Allow you to spread in other tuples: [number, ...[string, boolean], number]
    • And of course, the magic question: what about generics? Does it work with generics?
      • Yes!

        type T4<T extends any[]> = [number, ...T];
        type T5 = T4<[string, string]>;
      • And if you feed in a union, it distributes

        // [number] | [number, string] | [number, number, number]
        type T6 = T4<[] | [string] | [number, number]>;
    • Okay, what about the more magical question: does inference "work" (i.e. does it work well) with this?
      • Example: what do you infer to [...T, ...U]?

      • If you can do it "right", you can type Function.prototype.bind more simply.

      • Also, could enable lots of super nice helper functions

        type First<T> = T extends [infer U, ...any[]] ? U : never;
        type DropFirst<T> = T extends [any, ...infer U] ? U : never;
        type Last<T> = T extends [...any[], infer U] ? U : never;
      • What about things in the "middle"?

        • Could beef up inference a bit
    • Do labels slice and dice correctly?
      • The intent is that they should, some technicalities that make it not work right.
  • One of the use-cases was curry - take a function of a parameter list of some length, return a function that takes the first and returns a function that takes the rest.
    • People would be sad if it doesn't quite work out.
  • Ideally, could write Zip
    type Zip<T, U> = {
      [K in (keyof T) & (keyof U)]: [T[K], U[K]]
    };
    
    // Doesn't work.
    type Yadda = Zip<[1,2,3], [4,5,6]>;
    • @weswigham shows me it's possible

       type Cast<T, U> = T extends U ? T : never;
      type Zip<T, U, Hah = T | U> = { [K in keyof Hah]: [T  [Cast<K, keyof T>], U[Cast<K, keyof U>]] };
      type Yadda = Zip<[1, 2, 3], [4, 5, 6]>;

Node Factory

#35282
#38604

  • This does add quite a bit of indirection.
  • What about compatibilty for NodeFactorys between different versions?
    • Big old deprecations
  • Need this for certain applications post-parse
    • Top-level await can't be done with ambiguous parsing contexts (i.e. script .js vs module .mjs).
  • Make sure it's fast.

Pedantic Modes

https://gist.github.com/RyanCavanaugh/f80f9ddc50d45c4d76e7c4101efada28

  • Not a feature - more like a philosophy and/or shift in mindset of us saying we're okay adding a flag for stricter but largely not-palatable modes.
  • Examples
    • undefined in indexed access types (currently too annoying)
    • override keyword in classes (useless without noImplicitOverride or something)
  • If we do this, should we have --pedantic?
    • Convinced himself it's not a good idea.
    • Also, someone can publish an extendable tsconfig called my-super-kewl-typscript-pedantic?
  • Do these get named pedanticYaddaYadda?
    • If you don't, you can "graduate" to strict
    • But it is hard to remember which is strict and which is not.
  • What is the story for DefinitelyTyped?
    • Do they need to be pedantic-compatible?
    • Unclear.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Design NotesNotes from our design meetings

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions