تایپاسکریپت - ویژگیهای اختیاری بسته به ویژگی دیگر


فرض کنیم که ما interface تایپاسکریپت زیر را داریم:

interface Sample {
    key1: boolean;
    key2?: string;
    key3?: number;
};

در این حالت، key1 همیشه مورد نیاز است، key2 همیشه اختیاری است، در حالی که key3 باید وجود داشته باشد اگر key1 true باشد و نباید وجود داشته باشد اگر key1 false باشد. به عبارت دیگر، وجود یک کلید به مقدار کلید دیگری بستگی دارد. چگونه میتوانیم این را در تایپاسکریپت پیادهسازی کنیم؟

پاسخ شماره ۱

سادهترین راه برای نمایش این موضوع استفاده از یک نام مستعار نوع به جای یک رابط است:

type Sample = {
  key1: true,
  key2?: string,
  key3: number
} | {
  key1: false,
  key2?: string,
  key3?: never
}

در این حالت، نوع مستعار، اتحاد دو نوعی است که شما توصیف میکنید. بنابراین یک Sample باید یا اولین جزء باشد (جایی که key1 درست است و key3 اجباری است) یا دومین جزء باشد (جایی که key1 نادرست است و key3 وجود ندارد).

نامهای مستعار نوع شبیه رابطها هستند اما کاملاً قابل جایگزینی نیستند. اگر استفاده از یک نام مستعار نوع منجر به نوعی خطا شود، لطفاً جزئیات بیشتری درباره مورد استفاده خود در سوال اضافه کنید.

امیدوارم کمک کند. موفق باشی!

پاسخ شماره ۲

من همچنین واقعاً دوست دارم روشی که بن ایلگبودو (https://www.benmvp.com/blog/conditional-react-props-typescript/) انجام میدهد را:

این سه حالت مختلف را در JSX بدهید:

<Text>not truncated</Text>
<Text truncate>truncated</Text>
<Text truncate showExpand>truncated w/ expand option</Text>

... در اینجا تعریف TypeScript مربوطه آمده است تا ویژگی showExpanded هنگام وجود پروپ truncate الزامی شود:

interface CommonProps {
  children: React.ReactNode

  // ...other props that always exist
}

type TruncateProps =
  | { truncate?: false; showExpanded?: never }
  | { truncate: true; showExpanded?: boolean }

type Props = CommonProps & TruncateProps

const Text = ({ children, showExpanded, truncate }: Props) => {
  // Both truncate & showExpanded will be of
  // the type `boolean | undefined`
}```