Incorporating a custom type called ExtendWithAlias
, I have designed it to accept two generic arguments: the base type (
T extends Record<PropertyKey, any>
) and an object (
A extends { [aliasName: PropertyKey]: keyof T }
) that will enhance the
base type by utilizing an
Intersection Type.
By leveraging a
Mapped Type with
Key Mapping and a
Conditional Type, we can "look up" an existing
keyof T
(=
keyof Data
) and include it in our newly computed type with a specified alias. It should be noted that TypeScript will automatically infer
TTitle
as string.
One thing to keep in mind is that I have only tested this implementation with your specific input and some basic variations. There may be potential flaws or limitations when dealing with more intricate, nested types.
type TTitle = string;
type Data = {
id: string;
title: TTitle;
};
type ExtendWithAlias<
T extends Record<PropertyKey, any>,
A extends { [aliasName: PropertyKey]: keyof T },
> = T & {
[K in keyof A as A[K] extends keyof T ? K : never]: T[A[K]]
};
type ExtendedData = ExtendWithAlias<Data, { cardTitle: "title" }>;
// type ExtendedData = Data & {
// cardTitle: string;
// }
Further testing:
type Invalid1 = ExtendWithAlias<Data, { cardTitle: "no title" }>;
// ~~~~~~~~~~~~~~~~~~~~~~~~~
// Type '{ cardTitle: "no title"; }' does not satisfy the constraint ...
type Invalid2 = ExtendWithAlias<Data, { cardTitle: {} }>;
// ~~~~~~~~~~~~~~~~~
// Type '{ cardTitle: {}; }' does not satisfy the constraint ...
type ValidMultiple = ExtendWithAlias<Data, { cardTitle: "title", idAlias: "id" }>;
// type ExtendedData4 = Data & {
// cardTitle: string;
// idAlias: string;
// }
TypeScript Playground