Challenges 5 exercises
solution

Add Objects to the Global Scope Dynamically

The solution will still have declare global and interface Window:

declare global { interface Window {} } 

Because Window is an interface, we can use the extends keyword to add additional types to it.

For example, if we declare a Whatever type inside of the global and

Loading solution

Transcript

0:00 The way we start this is with a declare global. What we need to do inside here is we need to say, "interface Window." We somehow need to stick all of the stuff inside there. The thing that's useful about this is that Window is an interface, which means that we can use the extends keyword.

0:21 We can't change Window into a type. We can't say, "type Window = window & typeof addAllOfThisToWindow," but we can use interface Window Extends. Now we can start actually adding stuff inside here.

0:36 This is interesting. An interface can only extend an identifier/qualified-name with optional type arguments. Huh? An identifier/qualified-name is actually a type. We need to express type, let's say, Whatever equals this. Now interface Window can extend not Window, but Whatever. This works.

0:58 Now we can add a, for instance, typeof addAllOfThisToWindow. I've changed these to addSolution instead of thingy, blah, blah, blah, blah, blah. This shouldn't be add a. This should be addSolution. Now this one starts passing.

1:19 You can see where we're heading here. Now that we can extend this, we can actually, instead of mapping these individually onto addSolution, subtractSolution, multiplySolution, we can actually do this. We can say, "type StuffToAdd," let's say, "= typeof addAllOfThisToWindow." Then we can say, "interface Window extends StuffToAdd." Wow.

1:46 Now we've just done a big old merge, putting all of the stuff that's inside here into the Window. This means we can just say...I just want to say, "wow" is "1," for instance. We can then say, "window.wow." It's right there. Of course, this works at runtime because we're doing an Object.assign here which merges them both together. Super-nice.

2:06 This is really useful when you want to assign like process environment variables to a certain default value, let's say, and you have a type that you want to pull from, and you want to stick it in the global scope. Really, really nice.