I am trying to create a type from a readonly object, i.e.
const Actions = {
'user.crud': ['user.create', 'user.read', 'user.update', 'user.delete'],
} as const
type ActionsType = keyof typeof Actions | typeof Actions[keyof typeof Actions][number]
The above works nicely and sets up the type ActionsType to the string literals ('user.crud', 'user.create', etc..).
However, the Actions object above is very simplistic, instead, I really need to generate the Actions via functions. When I port the above over to being generated by a function, i.e.
// set up a function to generate all actions for the passed role
function getActions (role: string): Record<string, string[]> {
return {
[`${role}.crud`]: [`${role}.create`, `${role}.read`, `${role}.update`, `${role}.delete`],
}
}
// generate the Actions from a function
const ActionsFromFunction = {
...getActions('user'),
} as const
// set up the Actions from a readonly object with values generated by getActions()
type ActionsFromFunctionType = keyof typeof ActionsFromFunction | typeof ActionsFromFunction[keyof typeof ActionsFromFunction][number]
the type ActionsFromFunctionType is no longer set to the string literals. Instead it is set to: string | number and in turn type tests fail as any string is accepted.
I've put together a demo of the above:
Is there a way of generating the Actions object via a function, whilst still maintaining the string literals within the type?