@@ -19,8 +19,7 @@ export const fetchUserWithFullName = async (
19
19
...args : Parameters < typeof fetchUser >
20
20
) : Promise < Awaited < ReturnType < typeof fetchUser > > & { fullName : string } > => {
21
21
/**
22
- * 💡 Ouch, that's a lot of generics in a row. Discuss among
23
- * your group what you think this big mess of generics means.
22
+ * 💡 Ouch, that's a lot of generics in a row.
24
23
*/
25
24
const user = await fetchUser ( ...args ) ;
26
25
return {
@@ -47,26 +46,28 @@ export const fetchUserWithFullName = async (
47
46
* 💡 This is our first intro to generic code - and a lot of it
48
47
* can look like this: Something<SomethingElse<Wow<Deeper<Ok>>>>.
49
48
*
50
- * 🧑💻 There's a reason we went for this approach. Take a look at
51
- * the type definitions for external-lib.
49
+ * 🧑💻 There's a reason we went for this approach. There's something
50
+ * annoying about the type definitions for external-lib.
52
51
*
53
52
* 🔮 Do a go-to-definition on fetchUser:
54
53
*
55
54
* import { fetchUser } from "external-lib";
56
55
* ^ 🔮
57
56
*
58
- * You'll see that the only type definition here is a single function.
59
- * There isn't any code like this:
57
+ * You'll see that the only type definition here is a single
58
+ * function. There aren't any type defs for the return types
59
+ * or parameters of the functions. I.e:
60
60
*
61
- * interface User {
61
+ * interface FetchUserReturnType {
62
62
* id: string;
63
63
* firstName: string;
64
64
* lastName: string;
65
65
* age: number;
66
66
* }
67
67
*
68
68
* This is an issue, because we need that information if we're going
69
- * to extend it with `& { fullName: string }`.
69
+ * to extend it with `& { fullName: string }` for our wrapper
70
+ * function.
70
71
*/
71
72
72
73
/**
@@ -85,6 +86,8 @@ export const fetchUserWithFullName = async (
85
86
/**
86
87
* 🛠 We can extract the value of the promise with Awaited:
87
88
*
89
+ * https://www.typescriptlang.org/docs/handbook/release-notes/typescript-4-5.html#the-awaited-type-and-promise-improvements
90
+ *
88
91
* type FetchUserReturnType = Awaited<ReturnType<typeof fetchUser>>;
89
92
* ^ 🚁
90
93
*
@@ -128,6 +131,7 @@ export const fetchUserWithFullName = async (
128
131
* 🧑💻 There's one more thing to think about, too. We're currently only
129
132
* using one function from 'external-lib', fetchUser. But that's because
130
133
* we're at the start of the project.
134
+ *
131
135
* We'll likely end up using 10-12 functions from that lib, so this code
132
136
* might be duplicated many times if we want to add extra parameters to
133
137
* the output.
@@ -384,3 +388,47 @@ export const fetchUserWithFullName = async (
384
388
* We've also seen how some clever inference can get you out of
385
389
* tight spots when library typings aren't terribly helpful.
386
390
*/
391
+
392
+ /**
393
+ * 🕵️♂️ Stretch goal 1: Create a fetchPostWithMeta function which:
394
+ *
395
+ * Calls fetchPost and adds
396
+ *
397
+ * { meta: { title: title, description: body } }
398
+ *
399
+ * to the output.
400
+ *
401
+ * Use the existing WrapFunction to give it a type definition.
402
+ *
403
+ * Solution #1
404
+ */
405
+
406
+ const fetchPost = ( id : string ) => {
407
+ return Promise . resolve ( {
408
+ id,
409
+ title : "Title" ,
410
+ body : "Great post" ,
411
+ } ) ;
412
+ } ;
413
+
414
+ /**
415
+ * 🕵️♂️ Stretch goal 2: Given the function below, get a union
416
+ * type of all of its parameters.
417
+ *
418
+ * Solution #2
419
+ */
420
+
421
+ const funcWithManyParameters = (
422
+ a : string ,
423
+ b : string ,
424
+ c : number ,
425
+ d : boolean ,
426
+ ) => {
427
+ return [ a , b , c , d ] . join ( " " ) ;
428
+ } ;
429
+
430
+ type FuncParamsAsUnion = any ;
431
+ /** ^ 🚁
432
+ *
433
+ * 🚁 This should be string | number | boolean
434
+ */
0 commit comments