Утверждение типа объекта TypeScript не работает

#typescript

Вопрос:

 type ConfigItem<T> = {
  label: string;
  name: keyof T;
};

type P1 = {
  E1: {
    A: "xl",
    B: "xl",
    C: "xl",
    D: "xl",
  },
  E2: {
    AA: "xxl",
    BB: "xxl",
    CC: "xxl",
    DD: "xxl",
  },
};

export const Configs = {
  X1: [
    { label: "ax", name: "A2" }, // ⬅️ Why is it not restricted?
    { label: "bx", name: "B" },
    { label: "cx", name: "C" },
    { label: "dx", name: "D2" }, // If the last one is not in E1, an error is reported.
  ] as ConfigItem<P1["E1"]>[],
  X2: [
    // ...
  ]
};
 

Об ошибке сообщается только в том случае, если последний элемент в массиве имеет неправильный тип значения.

Если последний элемент указан правильно, предыдущий элемент неверен, сообщение об ошибке не будет.

 "typescript": "^4.4.4"
 

[ОБНОВЛЕНИЕ]: Это единственный способ сделать это?

 const X1: ConfigItem<P1["E1"]> = [
  { label: "ax", name: "A2" },
  { label: "bx", name: "B" },
  { label: "cx", name: "C" },
  { label: "dx", name: "D" },
];

export const Configs = {
  X1,
  X2: []
};
 

Комментарии:

1. Какого поведения вы ожидаете ? Пожалуйста, предоставьте более подробную информацию о возникшей у вас проблеме

2. Вы вообще не должны использовать утверждение типа; вы хотите, чтобы компилятор проверял типы, а не просто доверял вам: tsplay.dev/we0veW

Ответ №1:

Когда вы используете as [[typename]] нотацию, проверка типа не будет выполняться, так как вы вручную сообщаете компилятору, что уверены в правильности этого.

Что вы хотите сделать, чтобы включить проверку типов, так это:

 type ConfigItem<T> = {
  label: string;
  name: keyof T;
};

type P1 = {
  E1: {
    A: "xl",
    B: "xl",
    C: "xl",
    D: "xl",
  },
  E2: {
    AA: "xxl",
    BB: "xxl",
    CC: "xxl",
    DD: "xxl",
  },
};

export const Configs: {X1: ConfigItem<P1["E1"]>[], X2: any /*define next here*/} = {
  X1: [
    { label: "ax", name: "A2" },
    { label: "bx", name: "B" },
    { label: "cx", name: "C" },
    { label: "dx", name: "D2" },
  ],
  X2: [
    // ...
  ]
};