In Typescript, we have mapped types that can map properties from one type to another.
A common example is the Partial type, which makes all properties on the generic type 'optional'.
I would like to achieve the opposite, something like Required, where all properties are made 'required', regardless of their optionality up front.
Is such a thing possible?
(Since learned my question is superficial, please see update!)
Update:
Some context...
I'm learning about mapped types, and was inspired by the documentation here
type Proxy<T> = {
get(): T;
set(value: T): void;
}
type Proxify<T> = {
[P in keyof T]: Proxy<T[P]>;
}
function proxify<T>(o: T): Proxify<T> {
// ... wrap proxies ...
}
let proxyProps = proxify(props);
I thought to myself, hmm, "I wonder what mischief we can get up to with this?"
So I wrote something like:
type ProxyObservable<T> = Observable<T> & {
[P in keyof T]: ProxyObservable<T[P]>;
};
Which is cool, because you can give it a type like this:
interface Foo {
myNum: number;
myString: string;
myObject: {
someValue: number;
anotherValue: Date;
};
}
And you get a ProxyObservable<Foo>
type where every property is Observable of the same type, but also has matching navigation properties for child properties (which are also Observable).
const foo: ProxyObservable<Foo> = Proxify<Foo>(...)
foo.myNum.subscribe(...)
foo.myObject.subscribe(...)
foo.myObject.someValue.subscribe(...)
Unholy, I know. But cool.
The interesting problem comes in when you make a property (such as myObject) optional. Then Typescript will break on:
foo.myObject.someValue.subscribe(...)
Because it can't discern whether the type to union with Observable is 'undefined' or the object we defined. This is where my question came in.
BUT... I now also see that this isn't a problem with 'optional' properties, so much a problem with Discriminated Union types in general.
I realised that given the right context, Typescript may be able to infer the type of the foo.myObject
property. I tried a few variations:
foo.myObject!.someValue //<- Nope
foo.myObject ? foo.myObject.someValue : ... //<- Nope
if(foo.myObject) foo.myObject.someValue //<- Nope
In my mind the Typescript compiler should be able to infer this!
Can anyone tell me why not?