React.FC より props の型を取得する
React.FC<Props>
を定義して後から Props
を export
しないと・・・という場合に
Conditional Types - Advanced Types - TypeScript を利用して対象関数の引数の型を取得します。
いらなかった・・・
こちらの記事より以下の記事の React.ComponentProps
について確認したほうがよいです。
Parameters - Utility Types - TypeScript
Parameters
type T1 = Parameters<(s: string) => void>; // [string]
実例
ComponentProps-type
import React from 'react'
type ComponentProps<T> = T extends (props: infer P) => ReturnType<React.FC> ? P : never
React.FC に限定したくない実例
でも any
は・・・というときに unknown
使用
ComponentProps-unknown-type
type ComponentProps<T> = T extends (props: infer P) => unknown ? P : never
説明
Type inference in conditional types - TypeScript 2.8 の Conditional Types について - Qiita より
・・・
type FirstArgs<T> = T extends (a1: infer A1, ...rest: any[]) => any ? A1 : never;
・・・
こちらを参考に
- 取得対象となる
Props
をA1
からP
へリネーム - 戻り値を
React.FC
の戻り値となるようにReturnType<React.FC>
に変更
サンプル
user.tsx
import React from 'react'
type Props = {
user: {
/** ユーザー ID */
id: number
/** ユーザー名 */
name: string
}
}
const Component: React.FC<Props> = props => (
<div>
{props.user.id} {props.user.name}
</div>
)
export default Component
user.story.tsx
import React from 'react'
import { storiesOf } from '@storybook/react'
import User from './user'
type ComponentProps<T> = T extends (props: infer P) => ReturnType<React.FC> ? P : never
storiesOf('organisms/User', module).add('main', () => {
const user: ComponentProps<typeof User>['user'] = {
id: 1,
name: 'taro',
}
return (
<>
<User user={user} />
</>
)
})