David Armendariz
David Armendariz

Reputation: 1749

Type '{}' is not assignable to type 'IntrinsicAttributes'

I am new to TypeScript and I would like to use it with React. I have a functional component that needs to be exported like this:

import React from 'react';
import HOC from './HOC';

interface PropsType {
  someProp: boolean;
}

const MyFunctionalComponent: React.FC<PropsType> = ({ someProp }) => {
  return(
    ...
  )
};

export default HOC(MyFunctionalComponent);

and HOC.tsx is something like this:

import React, { Suspense } from 'react';
import Loader from './Loader';

export default function HOC(HocComponent: React.FC) {
  return function () {
    return (
      <Suspense fallback={<Loader />}>
        <HocComponent />
      </Suspense>
    );
  };
}

The problem is that I get the following error and I have googled but haven't found a definite solution:

Type '{ someProp: true; }' is not assignable to type 'IntrinsicAttributes'.
  Property 'someProp' does not exist on type 'IntrinsicAttributes'.  TS2322

Obviously, if I don't wrap MyFunctionalComponent with HOC then it works fine. What is the correct approach to solve this problem? Thanks in advance.

Upvotes: 1

Views: 1985

Answers (2)

KFunk
KFunk

Reputation: 3152

I had to go a step further from R.Karlus, and use props as P & {}

import React, { Suspense } from 'react';
import Loader from './Loader';

const withLoading<P extends object> (Component: React.ComponentType<P>) => 
    class WithLoading extends React.Component<P> {
        render() {
            return (
                <Suspense fallback={<Loader />}>
                    <HocComponent {...this.props as P & {}} />
                </Suspense>
            );
        }
    }
}

export default HOC;

Upvotes: 1

R. Karlus
R. Karlus

Reputation: 2256

The problem is that you must cast the properties to the an abstract parameter like object.

This should work:

import React, { Suspense } from 'react';
import Loader from './Loader';

const withLoading<P extends object> (Component: React.ComponentType<P>) => 
    class WithLoading extends React.Component<P> {
        render() {
            return (
                <Suspense fallback={<Loader />}>
                    <HocComponent {...this.props as P} />
                </Suspense>
            );
        }
    }
}

export default HOC;

And then you can simply:

import React from 'react';
import withLoading from './HOC';

interface PropsType {
    someProp: boolean;
}

const MyFunctionalComponent: React.FC<PropsType> = ({ someProp }) => {
    return(
        ...
    );
};

export default withLoading(MyFunctionalComponent);

Here's the source: https://medium.com/@jrwebdev/react-higher-order-component-patterns-in-typescript-42278f7590fb

Upvotes: 3

Related Questions