重复的字符串索引签名.ts(2374)

RSF*_*RSF 3 typescript reactjs

以下是我想在 TypeScript 中使用索引签名创建的类型。

export interface LoginState {
    account: {
              [userName: string]: string;
              [password: string]: string;
           };
}
Run Code Online (Sandbox Code Playgroud)

但是,我收到了这个问题标题中所述的错误。

该工具会提示/突出显示密码字段。

在此处输入图片说明

我找到了以下答案: Reactjs with Typescript 'Duplicate string index signature' 的错误 但这对我的问题没有帮助。

谁能指出我在这里犯的错误?

请随时询问是否需要进一步说明。

干杯,RSF

PS添加完整的组件实现:

import * as React from "react";
import { User } from "./../interfaces/User";
import { SecurityService } from "./../services/SecurityService";

export interface LoginProps {
  onLogged: (user: User) => void;
}

export interface LoginState {
  currentUser: User | null;
  account: {
         [userName: string]: string;
         [password: string]: string;
  };
}

export class Login extends React.Component<LoginProps, LoginState> {

   constructor(props: LoginProps) {
          super(props);

          this.state = {
          currentUser: null,
               account: {
               userName: "",
               password: ""
           }
        };
   }

  handleSubmit = async (e: React.FormEvent<HTMLFormElement>) => {
     e.preventDefault();
  };

  handleChange = (e: React.ChangeEvent<HTMLInputElement>) => {
      let account = { ...this.state.account };
      account[e.currentTarget.name] = e.currentTarget.value;
 };

 render() {
  return (
  <div>
    <h1>Login</h1>
    <form onSubmit={this.handleSubmit}>
      <div className="form-group">
        <label htmlFor="userName">Username</label>
        <input
          autoFocus
          onChange={this.handleChange}
          name="userName"
          id="userName"
          type="text"
          className="form-control"
        />
      </div>
      <div className="form-group">
        <label htmlFor="password">Password</label>
        <input
          onChange={this.handleChange}
          name="password"
          id="password"
          type="text"
          className="form-control"
        />
      </div>
      <button className="btn btn-primary">Login</button>
    </form>
  </div>
   );
  }
 }
Run Code Online (Sandbox Code Playgroud)

Pra*_*anD 5

来自打字稿手册

类似于我们如何使用接口来描述函数类型,我们也可以描述我们可以“索引到”的类型,如 a[10] 或 ageMap["daniel"]。可索引类型有一个索引签名,它描述了我们可以用来索引对象的类型,以及索引时相应的返回类型

当您使用时,index types您只是告诉打字稿在索引自定义类型时获得什么返回类型。

所以你只需要告诉 Typescript 当你account用字符串类型索引时,将返回一个字符串类型。就这样。

export interface LoginState {
  currentUser: User | null;
  account: {
      // Tells Typescript that a string index on account would return a string
      [k: string]: string;

      username: string;
      password: string;
      address: string;
      anotherField: string;
  };
}
Run Code Online (Sandbox Code Playgroud)

通过像这样定义它:

[userName: string]: string;
[password: string]: string;    // This is a duplicate string index
Run Code Online (Sandbox Code Playgroud)

你这样做:

[k1: string]: string;
[k2: string]: string;    // This is a duplicate string index
Run Code Online (Sandbox Code Playgroud)

这是错误的,因为您将同一件事告诉 Typescript 两次:如果您使用字符串索引帐户,您将得到一个字符串。如果您用字符串索引帐户,您将得到一个字符串。

稍后,如果您想引入 number称为idageto 的类型字段account,您的定义将如下所示:

export interface LoginState {
  currentUser: User | null;
  account: {
      // Tells Typescript that a string index on account would return a string OR a number
      [k: string]: string | number;

      username: string;
      password: string;
      address: string;
      anotherField: string;
      id: number;
      age: number;
  };
}
Run Code Online (Sandbox Code Playgroud)