Невозможно передать реквизиты, такие как className или style, в реквизиты пользовательских компонентов

Я работаю над созданием пакета NPM, дружественного к TypeScript, но у меня возникают проблемы с передачей общих атрибутов HTML в качестве реквизитов, таких как className и style, в мой компонент. Я надеялся, что мне не придется вручную добавлять каждый атрибут в список реквизитов, расширив интерфейс всеми нужными реквизитами. Мой упрощенный компонент выглядит так:

import React, { Key, ReactElement } from "react";

interface MyComponentProps extends React.HTMLAttributes<HTMLDivElement> {
    customText: string;
    uniqueKey?: Key;
}

export function MyComponent({uniqueKey, customText, ...props}: MyComponentProps): ReactElement {
    return (
        <div key = {uniqueKey} {...props}>{customText}</div>
    );
}

Я создал реквизит uniqueKey, так как его нельзя назвать просто key (то же самое с ref). Я попытался расширить параметр props, чтобы передать произвольные реквизиты моему компоненту, но, похоже, это не имеет значения. Я импортирую этот компонент в свой проект и пытаюсь вызвать его так:

<MyComponent customText = "Hello World" uniqueKey = {123} className = "myClass" />

Я получаю сообщение об ошибке: Property 'className' does not exist on type 'MyComponentProps'.

Я надеялся, что это сработает, так как MyComponentProps расширяет HTMLAttributes, у которого есть реквизиты, которые я хочу, такие как className и style.

Мой файл index.d.ts выглядит так:

import React, { Key, ReactElement } from "react";
interface MyComponentProps extends React.HTMLAttributes<HTMLDivElement> {
    customText: string;
    uniqueKey?: Key;
}
export declare function MyComponent({ uniqueKey, customText, ...props }: MyComponentProps): ReactElement;
export {};
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Навигация по приложениям React: Исчерпывающее руководство по React Router
Навигация по приложениям React: Исчерпывающее руководство по React Router
React Router стала незаменимой библиотекой для создания одностраничных приложений с навигацией в React. В этой статье блога мы подробно рассмотрим...
Массив зависимостей в React
Массив зависимостей в React
Все о массиве Dependency и его связи с useEffect.
3
0
754
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Самый простой способ получить доступные реквизиты для определенного элемента HTML — использовать JSX.IntrinsicElements.

type MyComponentProps = JSX.IntrinsicElements['div'] & {
    customText: string;
    uniqueKey?: Key;
}

Под капотом JSX.IntrinsicElements['div'] находится следующий тип.

React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>

Спасибо. Кажется, это помогает! Не могли бы вы помочь мне понять, почему расширение React.HTMLAttributes<HTMLAnchorElement> также не сработало для меня? С вашим решением также появляется, что я могу исключить свою опору uniqueKey и просто использовать key при создании экземпляра MyComponent.

roundtheworld 26.12.2020 18:35
HTMLAnchorElement неверно, так как вы передаете реквизит элементу div. Если вы замените его на HTMLDivElement, он должен работать, хотя реквизит key будет отсутствовать.
Mark Skelton 26.12.2020 18:44

Ой, извините, в моем исходном примере была опечатка. В моем реальном коде я использую элемент привязки, но в моем примере выше это div. Я исправил опечатку в своем первоначальном вопросе. С учетом сказанного... почему расширение React.HTMLAttributes<HTMLDivElement> не работает в моем примере? Хотя это звучит так, как будто вы предложили, чтобы это сработало - к сожалению, это не сработало. Это пакет NPM, при тестировании моего пакета я мог использовать такие атрибуты, как className, но не в проектах, в которых мой пакет NPM был зависимым.

roundtheworld 26.12.2020 18:56

Установлен ли @types/react в проекте, где вы используете свой пакет?

Mark Skelton 26.12.2020 18:57

Да, версия 17.0.0

roundtheworld 26.12.2020 18:58

Как выглядит ваш файл .d.ts для вашего пакета npm? Отсюда будут извлечены определения типов для вашего компонента, так что это поможет мне разобраться.

Mark Skelton 26.12.2020 19:07

Я обновил исходный вопрос, указав, как выглядит файл index.d.ts до предложенного вами изменения.

roundtheworld 26.12.2020 19:17

Давайте продолжим обсуждение в чате.

Mark Skelton 26.12.2020 19:21

Другие вопросы по теме