I'm trying to create a generic function that returns a configuration, given an enum.
In my packages I'd like to create a getConfiguration
method that would return me all the env variables that I need.
So for example :
enum PackageAEnvs {
API_KEY = "API_KEY"
}
enum PackageBEnvs {
ADMIN_URL = "ADMIN_URL"
}
Ideally, I would like to do something like this :
const getConfiguration = <T extends string[]> (conf: T): Record<T, string>{
return conf.reduce( (acc, val) => {
const env = process.env[val];
if(! env) throw new Error()
return { ...acc, [val]: env}
}, {})
}
I would then like to have typescript raising errors if the key does not exist :
const { randomKey} = getConfiguration<PackageAEnvs>() <-- typescript should throw error
I found a way using a type :
type Conf = "K1" | "K2"
type Config = {[Property in Conf]: string}
const getConfig = (): Config => {
return {
K1: "2",
K2: "2"
}
}
const { someKey } = getConf() // <-- error
However how can I make this getConfig function generic so it could accept any type ? Is it possible ?
CodePudding user response:
You would want to change your function to this:
const getConfiguration = <T extends object>(conf: T): Record<keyof T, string> => {
return Object.keys(conf).reduce( (acc, val) => {
const env = process.env[val];
if(! env) throw new Error()
return { ...acc, [val]: env}
}, {}) as any
}
The function now takes the enum
directly as an argument and constructs a Record
where the keys are the enum keys. We also use Object.keys(conf)
to get those keys at runtime.
const { API_KEY } = getConfiguration(PackageAEnvs)
const { ADMIN_URL } = getConfiguration(PackageBEnvs)