How can I map all object values of the first obj while preserving the generic type for the Wrapped object?
I attempted this using a mapped type, but encountered two issues:
- I'm struggling to represent a nested Object in the MapToWrappedType
- I can't seem to find a way to specify the type so that the mapped type is not
, but ratherWrapper<ValueObject<...>>
Wrapper<...>
Transforming from:
{
a: ValueObject<number>,
b: ValueObject<number>,
c: {
d: ValueObject<string>,
e: ValueObject<number>
}
}
To:
{
a: Wrapper<number>,
b: Wrapper<number>,
c: {
d: Wrapper<string>,
e: Wrapper<number>
}
}
class ValueObject<T> {
public value: T;
constructor(value: T) {
this.value = value;
}
}
class Wrapper<T> {
public value: T;
constructor(vo: ValueObject<T>) {
this.value = vo.value;
}
}
const obj = {
a: new ValueObject<number>(1),
b: new ValueObject<number>(2),
c: {
d: new ValueObject<string>("3"),
e: new ValueObject<number>(4)
}
} as const;
// 2 Problems:
// - how to express a nested object?
// - how to change the type to Wrapper<...> instead of Wrapper<Valueobject<...>>?
type MapToWrapped<T> = {
[K in keyof T]: Wrapper<T[K]>
}
function toWrappedObj<T>(obj: T): MapToWrapped<T> {
const result: any = {};
for (const key in obj) {
const item = obj[key];
if (item instanceof ValueObject) {
result[key] = new Wrapper<any>(item.value);
} else {
result[key] = toWrappedObj(item);
}
}
return result;
}
const wrappedValuesObj = toWrappedObj(obj);
const x = wrappedValuesObj.a // should be Wrapper<number>