简体   繁体   中英

How to create an optional object key string in typescript?

declare interface timezoneSyntax {
  region: string;
  en: {
    x: string;
    offset: {
      EST?: number;
      EDT?: number;
      [key: string]: number;
    };
  };
  it: {
   x: string;
  }
}

How to make the following object optional and also en generic?

en: {
    x: string;
    offset: {
      EST?: number;
      EDT?: number;
      [key: string]: number;
    };
  };

I have tried to convert en to [key: string]? But it is showing error. Please advice.

Indexes of the form [key: string]: T can be considered as being always optional, so no need to specify it with the ? notation.

However, specifying an index signature like that forces all interface properties to have the same T type as the key. For example, region would result in

Property 'region' of type 'string' is not assignable to string index type '{ x: string; offset: { ... }; }'

This is because an index signature [key: string]: T simply dictates how all interface properties should be like. An alternative would be to use [key: string]: any but you would loosen up your type safety.

From my understanding, this is not a side effect that you want so you should reconsider the use of index keys in this interface and find a different approach.

Proposal

Instead of using a language-specific property name ( en , it , es , etc), use the generic language as a name. If you also need to know what language you are dealing with, then that should be added to the language model as name .

You would end up with something like this:

declare interface timezoneSyntax {
  region: string;
  language: {
    name: string; // `en`, `it`, `es`, etc
    x: string;
    offset: {
      EST?: number;
      EDT?: number;
      [key: string]: number;
    };
  };
}

Further Reading

Indexable Types - Official TypeScript Documentation

Index Signatures - TypeScript Deep Dive

BTW, It already becomes optional. But, if you still want to explicitly do that then you can do something like this.

declare interface timezoneSyntax {
  region: string;
  en: {
    x: string;
    offset:
      | {
          EST?: number;
          EDT?: number;
          [key: string]: number;
        }
      | {
          EST?: number;
          EDT?: number;
        };
  };
  it: {
    x: string;
  };
}

Indexes of the form [key: string]: T can be optional. You can try to use Partial


   interface timezoneSyntax {
       page: Partial<{ [key: string]: number }>;
   }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM