Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it possible to declare dynamic string type in Typescript [duplicate]

Tags:

typescript

Suppose:

export enum EEnv { devint, qa1 };
export type TEnv = keyof typeof EEnv;
export const env:Record<TEnv, {something:number}> = {
  devint: {
    something: 1,
  },
  qa1: {
    something: 1,
  },
}

Then I want to create dynamic object based on env object, like this:

export const SAVE_TOKEN: Record<TEnv, string> = {
  devint: "SAVE_TOKEN/devint", // based on "env" key
  qa1: "SAVE_TOKEN/qa1", // based on "env" key
}

Is there any way to create type of string to be "SAVE_TOKEN/"+TEnv rather that just string.

like image 579
Exit Ekkasit Pinyoanuntapong Avatar asked Jan 30 '26 06:01

Exit Ekkasit Pinyoanuntapong


1 Answers

Update for those who still find their way here: this will be added in 4.1, see TypeScript#40336.

export type SaveTokenNamespace<K extends string> = { [T in K]: `SAVE_TOKEN/${T}` };

export function makeNamespace<K extends TEnv>(env: Record<K, unknown>): SaveTokenNamespace<K> {
  return Object.keys(env).reduce((ns, k) => ({ ...ns, [k]: `SAVE_TOKEN/${k}` }), {} as SaveTokenNamespace<K>);
}

console.log(makeNamespace(env));
const envNamespace = makeNamespace(env);
const test1: 'SAVE_TOKEN/qa1' = envNamespace.qa1; // Ok!
const test2: 'SAVE_TOKEN/notqa1' = envNamespace.qa1; // Error: Type '"SAVE_TOKEN/qa1"' is not assignable to type '"SAVE_TOKEN/notqa1"'.

Try it in the TypeScript playground


There are some popular open proposals/requests including Regex-validated string type: TypeScript#6579 and TypeScript#12754 with a comment about this exact use case, but as of 3.5.1 the answer is no.

like image 68
SpencerPark Avatar answered Feb 01 '26 19:02

SpencerPark