Uh oh!
There was an error while loading. Please reload this page.
extract rest params - #17898
Conversation
kiara (KiaraGrouwstra)
commented
Aug 24, 2017
Update: managed to make it error both if passing too many as well as if passing too few arguments now. That only leaves the hard part now... |
Jacob Eggers (eggers)
commented
Aug 24, 2017
@tycho01 Here's another use case to check: |
kiara (KiaraGrouwstra)
commented
Aug 24, 2017
Jacob Eggers (@eggers): out of curiosity, what's up with the |
Jacob Eggers (eggers)
commented
Aug 24, 2017
@tycho01 I was looking for a way to ensure that T is an array to activate that signature. There's probably a better way. |
kiara (KiaraGrouwstra)
commented
Aug 25, 2017
Jacob Eggers (@eggers): Makes sense then. This wasn't a standard library function though is it? |
Jacob Eggers (eggers)
commented
Aug 25, 2017
@tycho01 It's not in the native promise library, but it's in most polyfills. There are different ways of declaring spread now: // Qspread<U>(onFulfill: (...args: any[])=>IWhenable<U>,onReject?: (reason: any)=>IWhenable<U>): Promise<U>;// bluebirdspread<U,W>(fulfilledHandler: (...values: W[])=>U|PromiseLike<U>): Bluebird<U>;spread<U>(fulfilledHandler: Function): Bluebird<U>;// Whenspread<T>(onFulfilled: _.Fn0<Promise<T>|T>): Promise<T>;spread<A1,T>(onFulfilled: _.Fn1<A1,Promise<T>|T>): Promise<T>;spread<A1,A2,T>(onFulfilled: _.Fn2<A1,A2,Promise<T>|T>): Promise<T>;spread<A1,A2,A3,T>(onFulfilled: _.Fn3<A1,A2,A3,Promise<T>|T>): Promise<T>;spread<A1,A2,A3,A4,T>(onFulfilled: _.Fn4<A1,A2,A3,A4,Promise<T>|T>): Promise<T>;spread<A1,A2,A3,A4,A5,T>(onFulfilled: _.Fn5<A1,A2,A3,A4,A5,Promise<T>|T>): Promise<T>;None of which will give an error if the fulfilled handler arguments are incompatible with the promise type. e.g.: declarevarpromise: Promise<number>;promise.spread((x: string)=>x);// No error |
Jacob Eggers (@eggers): Thanks for the background, at least I know where to check for run-time behavior now. Your case here is actually interesting as you don't even require capturing the info into a generic for this -- with that, it appears to already work with my current progress :), just added a test for it. |
Jacob Eggers (eggers)
commented
Aug 25, 2017
Awesome. I made some explicit use cases below. The second overload was to cover how I thought bluebird treated promises that aren't arrays (see case 1), but I retested, and it actually throws an error ( declarevarpromiseNumber: Promise<number>;promiseNumber.spread((x: string)=>x);// Case 0: ErrorpromiseNumber.spread((x: number)=>x);// Case 1: No ErrordeclarevarpromiseNumberArray: Promise<number[]>;promiseNumberArray.spread((x: string)=>x);// Case 2: ErrorpromiseNumberArray.spread((x: number)=>x);// Case 3: No ErrordeclarevarpromiseTuple: Promise<[number,string]>;promiseTuple.spread((x: string,y: string)=>x);// Case 4: ErrorpromiseTuple.spread((x: number,y: string)=>x);// Case 5: No ErrorpromiseTuple.spread((x: number)=>x);// Case 6: Probably Error, though not criticalpromiseTuple.spread((x: number, ...rest: any[])=>x);// Case 7: No ErrorpromiseTuple.spread((...start: any[],x: string)=>x);// Case 8: No Error |
9b6de0c to
6d38c6bComparekiara (KiaraGrouwstra)
commented
Aug 28, 2017
I got this working now, would be happy to get feedback. |
kiara (KiaraGrouwstra)
commented
Aug 31, 2017
Update: I fixed the test Travis complained about. Apparently the |
Eyas (Eyas)
commented
Sep 17, 2017
I ran into this recently with code like: So looking forward to seeing this merged. |
Mikkel Snitker (MikkelSnitker)
commented
Oct 16, 2017
Hi. Would this change allow me pass a callback function where i change the callback function's return type but keeping the parameters names and types? e.g. something like this: would the signature of myPatchedFunction then be: /Mikkel |
Mikkel Snitker (@MikkelSnitker): this PR does half of that. That The second part, the An alternative possible today would be to type |
Mikkel Snitker (MikkelSnitker)
commented
Oct 16, 2017
@tycho01 Thanks for the clarification :) I don't see how I could overload the patchFunction, and keep the parameter names (it's meant to take an arbitrary function as input). In my use case the patchFunction would take a pure function and wrap it into a redux action, but still keep the parameter names/types of the original function. Are there any timeline for when we could expect this (and #18004 ) to be included in typescript? /Mikkel |
kiara (KiaraGrouwstra)
commented
Oct 16, 2017
Yeah, state management libs like Redux are definitely one of the main use cases of type programming :), that was what drove me to wanting to see more progress on this front as well.
I haven't received feedback from the team on either here yet, seems they're quite busy.
I would love this as well. My current PRs don't cover param names though -- I don't know what would be the nicest API for this. I'd be pretty interested in ideas on that front. |
Mikkel Snitker (MikkelSnitker)
commented
Oct 17, 2017
I'm not a language designer, but a could a simple solution be to make a generic function type? like |
kiara (KiaraGrouwstra)
commented
Oct 17, 2017
Note that for testing types in TS you can write The idea of a generic function type was discussed at gcanti/typelevel-ts#8, with an attempt at implementation on my part here. Note that using that in an attempt to capture the function is a bit problematic though -- I don't think you can currently use the type params in In fact, afaik we currently don't have a way to extract parameter types from function types at all, other than using overload matching (kills generics, verbose, doesn't scale well performance-wise once you get multiple variables that explode the number of combinations). I'd made a PoC to work around this for |
Xenya0815
commented
Feb 19, 2018
What's the status of that cool feature? |
TypeScript Bot (typescript-bot)
commented
Jun 19, 2018
Thanks for your contribution. This PR has not been updated in a while and cannot be automatically merged at the time being. For housekeeping purposes we are closing stale PRs. If you'd still like to continue working on this PR, please leave a message and one of the maintainers can reopen it. |
This stub to extracting rest params into tuple types is the second part of my attempt to tackle #5453.
It allows specifying array-like types including tuple types and array-bound generics as rest constraints:
<T extends number[]>(...args: T)/(...args: [number, string]). The former of these examples aims to extract the types of passed parameters on function application, while the latter is primarily useful to dynamically generate functions, e.g. to typebindorcurry.One may extract the types passed into generics from rest parameters as follows:
Fixes a third of #5453, alongside other issues that ran into
A rest parameter must be of an array type, like #1024, #2328, #5331, and #16931.