question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

[typescript] Incompatible types between React.forwardRef and OverridableComponent

See original GitHub issue

Duplicates

  • I have searched the existing issues

Latest version

  • I have tested the latest version

Current behavior 😯

When I try to define a wrapper for a component that uses the OverridableComponent type helper and uses React.forwardRef, I get a typescript error:

import React from "react";
import MUITypography, { TypographyTypeMap, TypographyProps } from "@mui/material/Typography";
import { OverridableComponent } from "@mui/material/OverridableComponent";


export const Typography: OverridableComponent<TypographyTypeMap> = React.forwardRef(function Typography<
  D extends React.ElementType
>(props: TypographyProps<D>, ref: React.Ref<HTMLSpanElement> | null) {
  return <MUITypography ref={ref} variantMapping={defaultVariantMapping} {...props} />;
});
Type 'ForwardRefExoticComponent<Pick<SystemProps<Theme> & { align?: "inherit" | "left" | "right" | "center" | "justify" | undefined; children?: ReactNode; classes?: Partial<TypographyClasses> | undefined; ... 5 more ...; variantMapping?: Partial<...> | undefined; } & CommonProps & Omit<...>, string | ... 1 more ... | symb...' is not assignable to type 'OverridableComponent<TypographyTypeMap<{}, "span">>'.
  Type 'ReactElement<any, string | JSXElementConstructor<any>> | null' is not assignable to type 'Element'.
    Type 'null' is not assignable to type 'ReactElement<any, any>'.ts(2322)

Expected behavior 🤔

I would expect types to be compatible

Steps to reproduce 🕹

In a typescript project define this in a file:

import React from "react";
import MUITypography, { TypographyTypeMap, TypographyProps } from "@mui/material/Typography";
import { OverridableComponent } from "@mui/material/OverridableComponent";


export const Typography: OverridableComponent<TypographyTypeMap> = React.forwardRef(function Typography<
  D extends React.ElementType
>(props: TypographyProps<D>, ref: React.Ref<HTMLSpanElement> | null) {
  return <MUITypography ref={ref} variantMapping={defaultVariantMapping} {...props} />;
});

Context 🔦

I have an internal package to isolate Mui and either re-export components directly, or wrap them.

If I only export my component without doing an explicit typing with OverridableComponent, I don’t have a proper autocompletion working, which is why I’d like to use that in the first place.

If I update the OverridableComponent to the following (returning JSX.Element | null instead of just JSX.Element)

export interface OverridableComponent<M extends OverridableTypeMap> {
  <C extends React.ElementType>(
    props: {
      /**
       * The component used for the root node.
       * Either a string to use a HTML element or a component.
       */
      component: C;
    } & OverrideProps<M, C>,
  ): JSX.Element | null;
  (props: DefaultComponentProps<M>): JSX.Element | null;
}

Then the type issue disappears.

Your environment 🌎

`npx @mui/envinfo`
  System:
    OS: macOS 12.3.1
  Binaries:
    Node: 14.19.1 - ~/.nvm/versions/node/v14.19.1/bin/node
    Yarn: 1.22.15 - ~/.yarn/bin/yarn
    npm: 6.14.16 - ~/.nvm/versions/node/v14.19.1/bin/npm
  Browsers:
    Chrome: 100.0.4896.127
    Edge: Not Found
    Firefox: 97.0.1
    Safari: 15.4
  npmPackages:
    @mui/system: 5.5.0 => 5.5.0

This is not browser related.

Typescript version: 4.5.4 @types/react-dom: 17.0.14 @types/react: 17.0.43

Issue Analytics

  • State:closed
  • Created a year ago
  • Reactions:3
  • Comments:7 (5 by maintainers)

github_iconTop GitHub Comments

1reaction
michaldudakcommented, Jul 11, 2022

Hi @HHK1, sorry for the delayed response. I took a closer look at OverridableComponent and I don’t see a reason for not including null as the return type. Would you like to create a PR? Please not that we have two versions of OverridableComponent - one in @mui/material and the other in @mui/types.

0reactions
michaldudakcommented, Dec 20, 2022

@rotemee Please open a new issue and provide a codesandbox with reproduction steps if you still encounter issues in this area.

Read more comments on GitHub >

github_iconTop Results From Across the Web

React + Typescript error for material ui icons - Stack Overflow
Type 'MutableRefObject<unknown>' is not assignable to type 'RefObject<SVGSVGElement>'. Types of property 'current' are incompatible. Type ' ...
Read more >
Useful Patterns by Use Case - React TypeScript Cheatsheets
Type '"foo"' is not assignable to type '"button" | "submit" | "reset" | undefined'.(2322) ... In future, the need to forwardRef may go...
Read more >
Making your components extensible with TypeScript
It's a generic type that receives two arguments: the name of the element ('button' on our case), and an object with our custom...
Read more >
typescript-cheatsheet - GitHub Pages
Setting up Event Handlers; TypeScript and React Hooks ... Since at least 1 of the members between the types string and number clash,...
Read more >
Deciphering TypeScript's React errors | by Fiona Hopkins |
This is exactly how you'd write it in an HTML page, but TypeScript shows an error: Types of property 'size' are incompatible. Type...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found