I'm trying to generate template literals based on the keys from a generic type. I am using this to extract only the keys of properties that are objects, which works but only with any strings as such:
type KeysWithValsOfType<T, V> = keyof { [P in keyof T as T[P] extends V ? P : never]: P };
type Person = {
firstName: string;
lastName: string;
};
type Customer = {
title: string;
email: string;
};
type Booking = {
id: string;
person: Person;
customer: Customer;
};
type TemplateLiteral<T> = `${string & KeysWithValsOfType<T>}($select=${string})`;
type BookingTemplate = TemplateLiteral<Booking>;
/**
* BookingTemplate type can be either of these:
*
* person($select=${string})
* customer($select=${string})
*/
Is it possible to achieve the commented template literals where typescript generates based on the keys of the nested objects?
type TemplateLiteral<T> = `${string & KeysWithValsOfType<T>}($select=${???})`;
type BookingTemplate = TemplateLiteral<Booking>;
/**
* BookingTemplate can be either of these:
*
* person($select=firstName)
* person($select=lastName)
* person($select=firstName,lastName)
* customer($select=title)
* customer($select=email)
* customer($select=title,email)
*/