繁体   English   中英

TypeScript object 中键值的类型

[英]TypeScript type for value of key in object

我正在尝试使用 TypeScript 为导航库定义自定义类型,但我还没有全神贯注地创建一个navigate function,它将屏幕的名称作为第一个参数,并将屏幕的属性作为第二个参数,同时仍然是类型安全的。

我试着:

  1. 安全地输入屏幕名称 ( keyof Stack ) 作为第一个参数
  2. 安全地封装我的两个导航堆栈( navigate<LoginStack>('HomeScreen')应该永远不会工作,只有来自LoginStack的屏幕应该是可能的)
  3. 使用正确的 arguments 作为相应屏幕名称 ( keyof Stack ) 作为第二个参数

我目前的做法:

ScreenDefinitions.ts

export interface LoginStackScreens {
    LoginScreen: BaseProps & { isHeadless?: boolean };
    ForgotPasswordScreen: BaseProps & { email: string };
}
export interface HomeStackScreens {
    HomeScreen: BaseProps & { isHeadless?: boolean };
    SavedScreen: BaseProps;
    ChatsListScreen: BaseProps;
    MyProfileScreen: BaseProps;
    PostDetailsScreen: BaseProps & {
        post: Post;
    };
    // ... some more
}

Navigation.ts

type ValueOf<T> = T[keyof T];
function navigate<Stack extends HomeStackScreens | LoginStackScreens>(screenName: keyof Stack, props: ValueOf<Stack>): void {
    // Navigation logic
}

navigate<HomeStackScreens>('HomeScreen', {});

虽然我达到了第1点和第2点,但第二个参数(arguments)的类型并不安全,因为它们包含HomeStackScreens堆栈中的所有值

显示所有类型参数的 VSCode 屏幕截图

而在这种情况下我只想拥有BaseProps & { isHeadless?: boolean } (参见HomeStackScreens定义)

试试这个!

function navigate<Stack extends {}>(
  screenName: keyof Stack,
  props: Stack[typeof screenName]
) {
  // Implementation
}

例子,

type SomeStack = {
  someScreen: {
    test: string
  }
}

navigate<SomeStack>('someScreen', {
  test: 5 // Fails - should be a string!
})

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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