Reacting
Reacting

Reputation: 6123

How to use multiple types with required props on the same declaration?

I am attempting to use this type:

type DataTypes =
  | Link
  | Event
  | People
  | Article
  | Department
  | PageSearch
  | OfficeSearch
  | CatalogSearch
  | DocumentSearch
  | KnowledgeSearch;

If I do it like this, it works properly:

const showOnTypeInQuery = (
    onType: string,
    cardType: (dataType: any[]) => ReactElement,
    dataType: DataTypes[]
  ): ReactElement | null => {
    if (typeInQuery === 'all' || typeInQuery === onType) {
      return cardType(dataType as DataTypes[]);
    }

    return null;
};


const getPeopleCards = (people: People[]): ReactElement => {
    return (
      <ComponentToShow
        data={people}
        heading="People"
      >
        {people.map((p: People) => (
            <PeopleCard
              people={p}
              isFetching={isFetchingData}
            />
        ))}
      </ComponentToShow>
    );
};

return showOnTypeInQuery('people', getPeopleCards, people);

On the function showOnTypeInQuery I have this param:

cardType: (dataType: any[]) => ReactElement

If I change to this cardType: (dataType: DataTypes[]) => ReactElement, it stops working and throws the following error:

ERROR in [at-loader] ./src/components/searchResult/searchResults.tsx:491:38
    TS2345: Argument of type '(people: People[]) => React.ReactElement<any, string | ((props: any) => React.ReactElement<any, string | ... | (new (props: any) => React.Component<any, any, any>)> | null) | (new (props: any) => React.Component<...>)>' is not assignable to parameter of type '(dataType: DataTypes[]) => ReactElement<any, string | ((props: any) => ReactElement<any, string | ... | (new (props: any) => Component<any, any, any>)> | null) | (new (props: any) => Component<...>)>'.
  Types of parameters 'people' and 'dataType' are incompatible.
    Type 'DataTypes[]' is not assignable to type 'PeopleModel[]'.
      Type 'DataTypes' is not assignable to type 'PeopleModel'.
        Property 'loginId' is missing in type 'Article' but required in type 'PeopleModel'.

In the DataTypes type I have all of those types in the same declaration because I need them in the function showOnTypeInQuery as parameters that will be used at some point. Those types in the DataTypes type contain required props but I thought that separating the types with pipelines, will make the trick.

So what am I doing wrong?

Upvotes: 0

Views: 90

Answers (1)

ssdh233
ssdh233

Reputation: 154

You cannot put a function whose type is People[] => ReactElement to a position which expects DataTypes[] => ReactElement, because your function might receive, for example, a Link type parameter and it doesn't know how to handle it, since it can only handle the People type.


I'm not very sure what you want to achieve here, but if you want to reuse showOnTypeInQuery for multiple types like Link, Event, People in your example, one solution is using generic like

const showOnTypeInQuery = <T extends DataTypes>(
    onType: string,
    cardType: (dataType: T[]) => ReactElement,
    dataType: T[]
  ): ReactElement | null => {
    if (typeInQuery === 'all' || typeInQuery === onType) {
      return cardType(dataType);
    }

    return null;
};

showOnTypeInQuery('people', getPeopleCards, people);

Upvotes: 1

Related Questions