Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(react): update @types/react to v19+ #30085

Open
wants to merge 5 commits into
base: main
Choose a base branch
from

Conversation

ptmkenny
Copy link

@ptmkenny ptmkenny commented Dec 15, 2024

Issue number: resolves #29991


What is the current behavior?

React types are currently being tested against React 17, but React 19 is the current version.

What is the new behavior?

Does this introduce a breaking change?

  • Yes
  • No

I don't think this introduces a breaking change but this needs confirmation because of the type changes.

Also, the dev dependency is react 17, which makes it tricky to test with 19.

Other information

I don't know if this is ready to go yet; I made this PR to run the tests.

@ptmkenny ptmkenny requested a review from a team as a code owner December 15, 2024 00:53
Copy link

vercel bot commented Dec 15, 2024

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Comments Updated (UTC)
ionic-framework ✅ Ready (Inspect) Visit Preview 💬 Add feedback Jan 3, 2025 8:06am

@github-actions github-actions bot added the package: react @ionic/react package label Dec 15, 2024
@ptmkenny ptmkenny changed the title Update @types/react to v19+ fix(react): update @types/react to v19+ Dec 15, 2024
@ptmkenny
Copy link
Author

The issue that needs to be fixed:

New function components will no longer need forwardRef, and we will be publishing a codemod to automatically update your components to use the new ref prop. In future versions we will deprecate and remove forwardRef.

@jadejr
Copy link

jadejr commented Jan 2, 2025

This PR seems to be missing adjustments in at least IonRouter, IonTab, and IonIcon. I tried it myself, but simply adding children and adjusting some refs wasn't enough.

@ptmkenny
Copy link
Author

ptmkenny commented Jan 2, 2025

This PR seems to be missing adjustments in at least IonRouter, IonTab, and IonIcon. I tried it myself, but simply adding children and adjusting some refs wasn't enough.

It would be helpful if you could post the specific errors you encountered. Also, hopefully we can get approval from someone at Ionic soon so that the workflows can be run, which should surface some more errors.

@jadejr
Copy link

jadejr commented Jan 3, 2025

I was able to successfully build @ionic/core with this PR, but not @ionic/react which seems necessary: Here are the errors with just this PR applied. Some of them can be fixed byadding missing children, using as Props or setting proper default values for createRef but not all. Fixing thesee will surface other errors. Some trivial, some not (to me anyways).

Errors and warnings ```sh npm run build

@ionic/[email protected] build
npm run clean && npm run copy && npm run compile

@ionic/[email protected] clean
rimraf dist && rimraf routing

@ionic/[email protected] copy
node scripts/copy.js

@ionic/[email protected] compile
rollup -c

src/index.ts → dist/...
(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type '{ children: ReactNode; style?: { [key: string]: any; } | undefined; className: string; routeInfo: RouteInfo | undefined; forwardedRef: ForwardedRef | undefined; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes & Readonly'.
Property 'children' does not exist on type 'IntrinsicAttributes & IntrinsicClassAttributes & Readonly'.
src/components/IonPage.tsx: (27:8)

27 <PageManager
~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'PropsWithoutRef & { forwardedRef: ForwardedRef; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes & Readonly'.
Type 'PropsWithoutRef & { forwardedRef: ForwardedRef; }' is not assignable to type 'Readonly'.
src/components/createControllerComponent.tsx: (125:13)

125 return <Overlay {...props} forwardedRef={ref} />;
~~~~~~~

src/components/react-component-lib/createOverlayComponent.tsx: (140:13)

140 return <Overlay {...props} forwardedRef={ref} />;
~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLIonOverlayElement | null>' is not assignable to type 'RefObject'.
Type 'HTMLIonOverlayElement | null' is not assignable to type 'HTMLIonOverlayElement'.
Type 'null' is not assignable to type 'HTMLIonOverlayElement'.
src/components/createInlineOverlayComponent.tsx: (47:7)

47 this.ref = React.createRef();
~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLElement | null>' is not assignable to type 'RefObject'.
src/components/createInlineOverlayComponent.tsx: (53:7)

53 this.wrapperRef = React.createRef();
~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLElement | null>' is not assignable to type 'RefObject'.
Type 'HTMLElement | null' is not assignable to type 'HTMLElement'.
Type 'null' is not assignable to type 'HTMLElement'.
src/components/createRoutingComponent.tsx: (42:7)

42 this.ref = React.createRef();
~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'IonNavProps'.
src/components/navigation/IonNav.tsx: (21:50)

21 const IonNavInternal: React.FC = ({ children, forwardedRef, ...restOfProps }) => {
~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS18046: 'child.props' is of type 'unknown'.
src/components/navigation/IonTabs.tsx: (95:45)

95 (child.type === Fragment && child.props.children[0].type === IonRouterOutlet);
~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type '{ className?: string | undefined; children: ReactNode | ChildFunction; onIonTabsDidChange?: ((event: IonTabsCustomEvent<{ tab: string; }>) => void) | undefined; onIonTabsWillChange?: ((event: IonTabsCustomEvent<...>) => void) | undefined; }' is not assignable to type 'Omit<HTMLAttributes, "style">'.
Types of property 'children' are incompatible.
Type 'ReactNode | ChildFunction' is not assignable to type 'ReactNode'.
Type 'ChildFunction' is not assignable to type 'ReactNode'.
src/components/navigation/IonTabs.tsx: (177:17)

177 return <IonTabsInner {...this.props}>;
~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type '{ children: Element; className: string; routeInfo: RouteInfo | undefined; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes & Readonly'.
Property 'children' does not exist on type 'IntrinsicAttributes & IntrinsicClassAttributes & Readonly'.
src/components/navigation/IonTabs.tsx: (195:14)

195 <PageManager className={className ? ${className} : ''} routeInfo={this.context.routeInfo} {...props}>
~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2345: Argument of type '{ (props: StencilReactExternalProps<PropType, ElementType>, ref: StencilReactForwardedRef): React.JSX.Element; displayName: string; }' is not assignable to parameter of type 'ForwardRefRenderFunction<ElementType, PropsWithoutRef<StencilReactExternalProps<PropType, ElementType>>>'.
Types of parameters 'props' and 'props' are incompatible.
Type 'PropsWithoutRef<StencilReactExternalProps<PropType, ElementType>>' is not assignable to type 'StencilReactExternalProps<PropType, ElementType>'.
Type 'Omit<HTMLAttributes, "style"> & StyleReactProps' is not assignable to type 'StencilReactExternalProps<PropType, ElementType>'.
Type 'Omit<HTMLAttributes, "style"> & StyleReactProps' is not assignable to type 'PropType'.
'PropType' could be instantiated with an arbitrary type which could be unrelated to 'Omit<HTMLAttributes, "style"> & StyleReactProps'.
src/components/react-component-lib/utils/index.tsx: (40:27)

40 return React.forwardRef(forwardRef);
~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2345: Argument of type '{ (props: IonicReactExternalProps<PropType, ElementType>, ref: React.ForwardedRef): React.JSX.Element; displayName: string; }' is not assignable to parameter of type 'ForwardRefRenderFunction<ElementType, PropsWithoutRef<IonicReactExternalProps<PropType, ElementType>>>'.
Types of parameters 'props' and 'props' are incompatible.
Type 'PropsWithoutRef<IonicReactExternalProps<PropType, ElementType>>' is not assignable to type 'IonicReactExternalProps<PropType, ElementType>'.
Type 'Omit<HTMLAttributes, "style" | "placeholder"> & IonicReactProps' is not assignable to type 'IonicReactExternalProps<PropType, ElementType>'.
Type 'Omit<HTMLAttributes, "style" | "placeholder"> & IonicReactProps' is not assignable to type 'PropType'.
'PropType' could be instantiated with an arbitrary type which could be unrelated to 'Omit<HTMLAttributes, "style" | "placeholder"> & IonicReactProps'.
src/components/utils/index.tsx: (28:27)

28 return React.forwardRef(forwardRef);
~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2554: Expected 1 arguments, but got 0.
src/hooks/useController.ts: (18:22)

18 const overlayRef = useRef();
~~~~~~

node_modules/@types/react/index.d.ts:1722:24
1722 function useRef(initialValue: T): RefObject;
~~~~~~~~~~~~~~~
An argument for 'initialValue' was not provided.

src/hooks/useOverlay.ts: (25:22)

25 const overlayRef = useRef();
~~~~~~

node_modules/@types/react/index.d.ts:1722:24
1722 function useRef(initialValue: T): RefObject;
~~~~~~~~~~~~~~~
An argument for 'initialValue' was not provided.

src/hooks/useOverlay.ts: (26:26)

26 const containerElRef = useRef();
~~~~~~

node_modules/@types/react/index.d.ts:1722:24
1722 function useRef(initialValue: T): RefObject;
~~~~~~~~~~~~~~~
An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (8:14)

8 const id = useRef<number | undefined>();
~~~~~~

node_modules/@types/react/index.d.ts:1722:24
1722 function useRef(initialValue: T): RefObject;
~~~~~~~~~~~~~~~
An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (21:14)

21 const id = useRef<number | undefined>();
~~~~~~

node_modules/@types/react/index.d.ts:1722:24
1722 function useRef(initialValue: T): RefObject;
~~~~~~~~~~~~~~~
An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (34:14)

34 const id = useRef<number | undefined>();
~~~~~~

node_modules/@types/react/index.d.ts:1722:24
1722 function useRef(initialValue: T): RefObject;
~~~~~~~~~~~~~~~
An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (47:14)

47 const id = useRef<number | undefined>();
~~~~~~

node_modules/@types/react/index.d.ts:1722:24
1722 function useRef(initialValue: T): RefObject;
~~~~~~~~~~~~~~~
An argument for 'initialValue' was not provided.

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'undefined' is not assignable to type 'OverlayType'.
'OverlayType' could be instantiated with an arbitrary type which could be unrelated to 'undefined'.
src/hooks/useController.ts: (38:9)

38 overlayRef.current = undefined;
~~~~~~~~~~~~~~~~~~

src/hooks/useController.ts: (59:5)

59 overlayRef.current = undefined;
~~~~~~~~~~~~~~~~~~

src/hooks/useOverlay.ts: (79:7)

79 overlayRef.current = undefined;
~~~~~~~~~~~~~~~~~~

src/hooks/useOverlay.ts: (88:5)

88 overlayRef.current = undefined;
~~~~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'undefined' is not assignable to type 'HTMLDivElement'.
src/hooks/useOverlay.ts: (80:7)

80 containerElRef.current = undefined;
~~~~~~~~~~~~~~~~~~~~~~

src/hooks/useOverlay.ts: (89:5)

89 containerElRef.current = undefined;
~~~~~~~~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly'.
src/routing/NavManager.tsx: (134:23)

134 {this.props.children}
~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLDivElement | null>' is not assignable to type 'RefObject'.
Type 'HTMLDivElement | null' is not assignable to type 'HTMLDivElement'.
Type 'null' is not assignable to type 'HTMLDivElement'.
src/routing/PageManager.tsx: (23:5)

23 this.ionPageElementRef = React.createRef();
~~~~~~~~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly'.
src/routing/PageManager.tsx: (85:24)

85 const { className, children, routeInfo, forwardedRef, ...props } = this.props;
~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly'.
src/routing/ViewLifeCycleManager.tsx: (51:29)

51 {show && this.props.children}
~~~~~~~~

created dist/ in 3.1s

</details>

@ptmkenny
Copy link
Author

ptmkenny commented Jan 3, 2025

@jadejr Thanks, that's helpful. A challenge is that on HEAD, there are a lot of warnings even before the MR:

npm run build

> @ionic/[email protected] build
> npm run clean && npm run copy && npm run compile


> @ionic/[email protected] clean
> rimraf dist && rimraf routing


> @ionic/[email protected] copy
> node scripts/copy.js


> @ionic/[email protected] compile
> rollup -c


src/index.ts → dist/...
(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'PropsWithoutRef<Props> & { forwardedRef: ForwardedRef<OverlayType>; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<Overlay> & Readonly<Props>'.
  Type 'PropsWithoutRef<Props> & { forwardedRef: ForwardedRef<OverlayType>; }' is not assignable to type 'Readonly<Props>'.
src/components/createControllerComponent.tsx: (125:13)

125     return <Overlay {...props} forwardedRef={ref} />;
                ~~~~~~~

src/components/createOverlayComponent.tsx: (142:13)

142     return <Overlay {...props} forwardedRef={ref} />;
                ~~~~~~~

src/components/react-component-lib/createOverlayComponent.tsx: (140:13)

140     return <Overlay {...props} forwardedRef={ref} />;
                ~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLIonOverlayElement | null>' is not assignable to type 'RefObject<HTMLIonOverlayElement>'.
  Type 'HTMLIonOverlayElement | null' is not assignable to type 'HTMLIonOverlayElement'.
    Type 'null' is not assignable to type 'HTMLIonOverlayElement'.
src/components/createInlineOverlayComponent.tsx: (47:7)

47       this.ref = React.createRef();
         ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLElement | null>' is not assignable to type 'RefObject<HTMLElement>'.
src/components/createInlineOverlayComponent.tsx: (53:7)

53       this.wrapperRef = React.createRef();
         ~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLElement | null>' is not assignable to type 'RefObject<HTMLElement>'.
  Type 'HTMLElement | null' is not assignable to type 'HTMLElement'.
    Type 'null' is not assignable to type 'HTMLElement'.
src/components/createRoutingComponent.tsx: (42:7)

42       this.ref = React.createRef();
         ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly<Props>'.
src/components/IonApp.tsx: (45:52)

45           <IonAppInner {...this.props}>{this.props.children}</IonAppInner>
                                                      ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly<InternalProps>'.
src/components/IonIcon.tsx: (56:21)

56         {this.props.children}
                       ~~~~~~~~

src/components/IonRouterOutlet.tsx: (33:13)

33     const { children, forwardedRef, ...props } = this.props;
               ~~~~~~~~

src/components/IonRouterOutlet.tsx: (49:21)

49         {this.props.children}
                       ~~~~~~~~

src/components/navigation/IonTabBar.tsx: (257:40)

257         {React.Children.map(this.props.children as any, this.renderTabButton(activeTab))}
                                           ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly<IonPageInternalProps>'.
src/components/IonPage.tsx: (24:24)

24     const { className, children, forwardedRef, ...props } = this.props;
                          ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type '{ children: any; style?: { [key: string]: any; } | undefined; className: string; routeInfo: RouteInfo<any> | undefined; forwardedRef: ForwardedRef<HTMLDivElement> | undefined; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<PageManager> & Readonly<PageManagerProps>'.
  Property 'children' does not exist on type 'IntrinsicAttributes & IntrinsicClassAttributes<PageManager> & Readonly<PageManagerProps>'.
src/components/IonPage.tsx: (27:8)

27       <PageManager
          ~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2694: Namespace 'global.JSX' has no exported member 'Element'.
src/components/IonRoute.tsx: (9:32)

9   render: (props?: any) => JSX.Element; // TODO(FW-2959): type
                                 ~~~~~~~

src/framework-delegate.tsx: (8:44)

8 type ReactComponent = (props?: any) => JSX.Element;
                                             ~~~~~~~

src/models/ReactComponentOrElement.ts: (3:92)

3 export type ReactComponentOrElement = React.ComponentClass<any, any> | React.FC<any> | JSX.Element;
                                                                                             ~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type '{ children: any; animated?: boolean | undefined; animation?: AnimationBuilder | undefined; mode?: "ios" | "md" | undefined; basePath?: string | undefined; ref?: Ref<...> | undefined; ionPage?: boolean | undefined; StackManager: any; routeInfo: RouteInfo<...> | undefined; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<OutletPageManager> & Readonly<OutletPageManagerProps>'.
  Property 'children' does not exist on type 'IntrinsicAttributes & IntrinsicClassAttributes<OutletPageManager> & Readonly<OutletPageManagerProps>'.
src/components/IonRouterOutlet.tsx: (37:10)

37         <OutletPageManager StackManager={StackManager} routeInfo={this.context.routeInfo} {...props}>
            ~~~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'IonNavProps'.
src/components/navigation/IonNav.tsx: (21:50)

21 const IonNavInternal: React.FC<IonNavProps> = ({ children, forwardedRef, ...restOfProps }) => {
                                                    ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type '{ onSetCurrentTab: (tab: string, routeInfo: RouteInfo<any>) => void; routeInfo: RouteInfo<any>; tabsContext?: IonTabsContextState | undefined; ... 8 more ...; slot?: "bottom" | ... 1 more ... | undefined; }'.
src/components/navigation/IonTabBar.tsx: (293:14)

293       {props.children}
                 ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS18046: 'child.props' is of type 'unknown'.
src/components/navigation/IonTabs.tsx: (95:45)

95                 (child.type === Fragment && child.props.children[0].type === IonRouterOutlet);
                                               ~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type '{ className?: string | undefined; children: ReactNode | ChildFunction; onIonTabsDidChange?: ((event: IonTabsCustomEvent<{ tab: string; }>) => void) | undefined; onIonTabsWillChange?: ((event: IonTabsCustomEvent<...>) => void) | undefined; }' is not assignable to type 'Omit<HTMLAttributes<HTMLIonTabsElement>, "style">'.
  Types of property 'children' are incompatible.
    Type 'ReactNode | ChildFunction' is not assignable to type 'ReactNode'.
      Type 'ChildFunction' is not assignable to type 'ReactNode'.
src/components/navigation/IonTabs.tsx: (177:17)

177         return <IonTabsInner {...this.props}></IonTabsInner>;
                    ~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type '{ children: Element; className: string; routeInfo: RouteInfo<any> | undefined; }' is not assignable to type 'IntrinsicAttributes & IntrinsicClassAttributes<PageManager> & Readonly<PageManagerProps>'.
  Property 'children' does not exist on type 'IntrinsicAttributes & IntrinsicClassAttributes<PageManager> & Readonly<PageManagerProps>'.
src/components/navigation/IonTabs.tsx: (195:14)

195             <PageManager className={className ? `${className}` : ''} routeInfo={this.context.routeInfo} {...props}>
                 ~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2345: Argument of type '{ (props: StencilReactExternalProps<PropType, ElementType>, ref: StencilReactForwardedRef<ElementType>): React.JSX.Element; displayName: string; }' is not assignable to parameter of type 'ForwardRefRenderFunction<ElementType, PropsWithoutRef<StencilReactExternalProps<PropType, ElementType>>>'.
  Types of parameters 'props' and 'props' are incompatible.
    Type 'PropsWithoutRef<StencilReactExternalProps<PropType, ElementType>>' is not assignable to type 'StencilReactExternalProps<PropType, ElementType>'.
      Type 'Omit<HTMLAttributes<ElementType>, "style"> & StyleReactProps' is not assignable to type 'StencilReactExternalProps<PropType, ElementType>'.
        Type 'Omit<HTMLAttributes<ElementType>, "style"> & StyleReactProps' is not assignable to type 'PropType'.
          'PropType' could be instantiated with an arbitrary type which could be unrelated to 'Omit<HTMLAttributes<ElementType>, "style"> & StyleReactProps'.
src/components/react-component-lib/utils/index.tsx: (40:27)

40   return React.forwardRef(forwardRef);
                             ~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2345: Argument of type '{ (props: IonicReactExternalProps<PropType, ElementType>, ref: React.ForwardedRef<ElementType>): React.JSX.Element; displayName: string; }' is not assignable to parameter of type 'ForwardRefRenderFunction<ElementType, PropsWithoutRef<IonicReactExternalProps<PropType, ElementType>>>'.
  Types of parameters 'props' and 'props' are incompatible.
    Type 'PropsWithoutRef<IonicReactExternalProps<PropType, ElementType>>' is not assignable to type 'IonicReactExternalProps<PropType, ElementType>'.
      Type 'Omit<HTMLAttributes<ElementType>, "style" | "placeholder"> & IonicReactProps' is not assignable to type 'IonicReactExternalProps<PropType, ElementType>'.
        Type 'Omit<HTMLAttributes<ElementType>, "style" | "placeholder"> & IonicReactProps' is not assignable to type 'PropType'.
          'PropType' could be instantiated with an arbitrary type which could be unrelated to 'Omit<HTMLAttributes<ElementType>, "style" | "placeholder"> & IonicReactProps'.
src/components/utils/index.tsx: (28:27)

28   return React.forwardRef(forwardRef);
                             ~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2554: Expected 1 arguments, but got 0.
src/hooks/useController.ts: (18:22)

18   const overlayRef = useRef<OverlayType>();
                        ~~~~~~

  node_modules/@types/react/index.d.ts:1722:24
    1722     function useRef<T>(initialValue: T): RefObject<T>;
                                ~~~~~~~~~~~~~~~
    An argument for 'initialValue' was not provided.

src/hooks/useOverlay.ts: (25:22)

25   const overlayRef = useRef<OverlayType>();
                        ~~~~~~

  node_modules/@types/react/index.d.ts:1722:24
    1722     function useRef<T>(initialValue: T): RefObject<T>;
                                ~~~~~~~~~~~~~~~
    An argument for 'initialValue' was not provided.

src/hooks/useOverlay.ts: (26:26)

26   const containerElRef = useRef<HTMLDivElement>();
                            ~~~~~~

  node_modules/@types/react/index.d.ts:1722:24
    1722     function useRef<T>(initialValue: T): RefObject<T>;
                                ~~~~~~~~~~~~~~~
    An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (8:14)

8   const id = useRef<number | undefined>();
               ~~~~~~

  node_modules/@types/react/index.d.ts:1722:24
    1722     function useRef<T>(initialValue: T): RefObject<T>;
                                ~~~~~~~~~~~~~~~
    An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (21:14)

21   const id = useRef<number | undefined>();
                ~~~~~~

  node_modules/@types/react/index.d.ts:1722:24
    1722     function useRef<T>(initialValue: T): RefObject<T>;
                                ~~~~~~~~~~~~~~~
    An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (34:14)

34   const id = useRef<number | undefined>();
                ~~~~~~

  node_modules/@types/react/index.d.ts:1722:24
    1722     function useRef<T>(initialValue: T): RefObject<T>;
                                ~~~~~~~~~~~~~~~
    An argument for 'initialValue' was not provided.

src/lifecycle/hooks.ts: (47:14)

47   const id = useRef<number | undefined>();
                ~~~~~~

  node_modules/@types/react/index.d.ts:1722:24
    1722     function useRef<T>(initialValue: T): RefObject<T>;
                                ~~~~~~~~~~~~~~~
    An argument for 'initialValue' was not provided.

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'undefined' is not assignable to type 'OverlayType'.
  'OverlayType' could be instantiated with an arbitrary type which could be unrelated to 'undefined'.
src/hooks/useController.ts: (38:9)

38         overlayRef.current = undefined;
           ~~~~~~~~~~~~~~~~~~

src/hooks/useController.ts: (59:5)

59     overlayRef.current = undefined;
       ~~~~~~~~~~~~~~~~~~

src/hooks/useOverlay.ts: (79:7)

79       overlayRef.current = undefined;
         ~~~~~~~~~~~~~~~~~~

src/hooks/useOverlay.ts: (88:5)

88     overlayRef.current = undefined;
       ~~~~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'undefined' is not assignable to type 'HTMLDivElement'.
src/hooks/useOverlay.ts: (80:7)

80       containerElRef.current = undefined;
         ~~~~~~~~~~~~~~~~~~~~~~

src/hooks/useOverlay.ts: (89:5)

89     containerElRef.current = undefined;
       ~~~~~~~~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly<NavManagerProps>'.
src/routing/NavManager.tsx: (134:23)

134           {this.props.children}
                          ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly<OutletPageManagerProps>'.
src/routing/OutletPageManager.tsx: (86:27)

86     const { StackManager, children, routeInfo, ...props } = this.props;
                             ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2322: Type 'RefObject<HTMLDivElement | null>' is not assignable to type 'RefObject<HTMLDivElement>'.
  Type 'HTMLDivElement | null' is not assignable to type 'HTMLDivElement'.
    Type 'null' is not assignable to type 'HTMLDivElement'.
src/routing/PageManager.tsx: (23:5)

23     this.ionPageElementRef = React.createRef();
       ~~~~~~~~~~~~~~~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly<PageManagerProps>'.
src/routing/PageManager.tsx: (85:24)

85     const { className, children, routeInfo, forwardedRef, ...props } = this.props;
                          ~~~~~~~~

(!) Plugin typescript: @rollup/plugin-typescript TS2339: Property 'children' does not exist on type 'Readonly<ViewTransitionManagerProps>'.
src/routing/ViewLifeCycleManager.tsx: (51:29)

51         {show && this.props.children}
                               ~~~~~~~~

created dist/ in 1.5s

@ptmkenny
Copy link
Author

ptmkenny commented Jan 3, 2025

I pushed a few more fixes for missing children props, including some that were already broken on HEAD. I think this is ready for review despite all the warnings, because the warnings are already there in HEAD (as far as I can tell; the list is quite long so it was hard to compare).

Long-term, I think the best fix would be to get rid of these wrappers as I proposed in #30107

@jadejr
Copy link

jadejr commented Jan 3, 2025

@ptmkenny : Using the custom elements directly would be for the best, but how soon can ionic actually do that? Seems like it would require a semver major bump since the packages are versioned collectively and I doubt they'd wanna do that just for react.

@jadejr
Copy link

jadejr commented Jan 3, 2025

It was on me for not realizing those warnings weren't actually a problem, but here is an actual issue in my code that uses @ionic/react

Same error regarding args for the types of 'shouldComponentUpdate' are incompatible between these types. for IonTabButton and IonApp so far.

'IonTabs' cannot be used as a JSX component.
  Its type '{ new (props: Props): { context: NavContextState; routerOutletRef: Ref<HTMLIonRouterOutletElement>; selectTabHandler?: ((tag: string) => boolean) | undefined; tabBarRef: RefObject<any>; ionTabContextState: IonTabsContextState; componentDidMount(): void; renderTabsInner(children: ReactNode, outlet: ReactElement<{}, string | JSXElementConstructor<any>> | undefined): Element; render(): Element; setState<K extends never>(state: {} | ((prevState: Readonly<{}>, props: Readonly<Props>) => {} | Pick<{}, K> | null) | Pick<{}, K> | null, callback?: (() => void) | undefined): void; forceUpdate(callback?: (() => void) | undefined): void; readonly props: Readonly<Props> & Readonly<{ children?: ReactNode; }>; state: Readonly<{}>; refs: { [key: string]: ReactInstance; }; shouldComponentUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): boolean; componentWillUnmount?(): void; componentDidCatch?(error: Error, errorInfo: ErrorInfo): void; getSnapshotBeforeUpdate?(prevProps: Readonly<Props>, prevState: Readonly<{}>): any; componentDidUpdate?(prevProps: Readonly<Props>, prevState: Readonly<{}>, snapshot?: any): void; componentWillMount?(): void; UNSAFE_componentWillMount?(): void; componentWillReceiveProps?(nextProps: Readonly<Props>, nextContext: any): void; UNSAFE_componentWillReceiveProps?(nextProps: Readonly<Props>, nextContext: any): void; componentWillUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): void; UNSAFE_componentWillUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): void; }; readonly contextType: Context<NavContextState>; }' is not a valid JSX element type.
    Type '{ new (props: Props): { context: NavContextState; routerOutletRef: Ref<HTMLIonRouterOutletElement>; selectTabHandler?: ((tag: string) => boolean) | undefined; tabBarRef: RefObject<any>; ionTabContextState: IonTabsContextState; componentDidMount(): void; renderTabsInner(children: ReactNode, outlet: ReactElement<{}, string | JSXElementConstructor<any>> | undefined): Element; render(): Element; setState<K extends never>(state: {} | ((prevState: Readonly<{}>, props: Readonly<Props>) => {} | Pick<{}, K> | null) | Pick<{}, K> | null, callback?: (() => void) | undefined): void; forceUpdate(callback?: (() => void) | undefined): void; readonly props: Readonly<Props> & Readonly<{ children?: ReactNode; }>; state: Readonly<{}>; refs: { [key: string]: ReactInstance; }; shouldComponentUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): boolean; componentWillUnmount?(): void; componentDidCatch?(error: Error, errorInfo: ErrorInfo): void; getSnapshotBeforeUpdate?(prevProps: Readonly<Props>, prevState: Readonly<{}>): any; componentDidUpdate?(prevProps: Readonly<Props>, prevState: Readonly<{}>, snapshot?: any): void; componentWillMount?(): void; UNSAFE_componentWillMount?(): void; componentWillReceiveProps?(nextProps: Readonly<Props>, nextContext: any): void; UNSAFE_componentWillReceiveProps?(nextProps: Readonly<Props>, nextContext: any): void; componentWillUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): void; UNSAFE_componentWillUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): void; }; readonly contextType: Context<NavContextState>; }' is not assignable to type 'new (props: any) => Component<any, any, any>'.
      Construct signature return types '{ context: NavContextState; routerOutletRef: Ref<HTMLIonRouterOutletElement>; selectTabHandler?: ((tag: string) => boolean) | undefined; tabBarRef: RefObject<any>; ionTabContextState: IonTabsContextState; componentDidMount(): void; renderTabsInner(children: ReactNode, outlet: ReactElement<{}, string | JSXElementConstructor<any>> | undefined): Element; render(): Element; setState<K extends never>(state: {} | ((prevState: Readonly<{}>, props: Readonly<Props>) => {} | Pick<{}, K> | null) | Pick<{}, K> | null, callback?: (() => void) | undefined): void; forceUpdate(callback?: (() => void) | undefined): void; readonly props: Readonly<Props> & Readonly<{ children?: ReactNode; }>; state: Readonly<{}>; refs: { [key: string]: ReactInstance; }; shouldComponentUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): boolean; componentWillUnmount?(): void; componentDidCatch?(error: Error, errorInfo: ErrorInfo): void; getSnapshotBeforeUpdate?(prevProps: Readonly<Props>, prevState: Readonly<{}>): any; componentDidUpdate?(prevProps: Readonly<Props>, prevState: Readonly<{}>, snapshot?: any): void; componentWillMount?(): void; UNSAFE_componentWillMount?(): void; componentWillReceiveProps?(nextProps: Readonly<Props>, nextContext: any): void; UNSAFE_componentWillReceiveProps?(nextProps: Readonly<Props>, nextContext: any): void; componentWillUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): void; UNSAFE_componentWillUpdate?(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any): void; }' and 'Component<any, any, any>' are incompatible.
        The types of 'shouldComponentUpdate' are incompatible between these types.
          Type '((nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any) => boolean) | undefined' is not assignable to type '((nextProps: Readonly<any>, nextState: Readonly<any>) => boolean) | undefined'.
            Type '(nextProps: Readonly<Props>, nextState: Readonly<{}>, nextContext: any) => boolean' is not assignable to type '(nextProps: Readonly<any>, nextState: Readonly<any>) => boolean'.
              Target signature provides too few arguments. Expected 3 or more, but got 2.

@ptmkenny
Copy link
Author

ptmkenny commented Jan 4, 2025

@ptmkenny : Using the custom elements directly would be for the best, but how soon can ionic actually do that? Seems like it would require a semver major bump since the packages are versioned collectively and I doubt they'd wanna do that just for react.

My understanding of web components is limited, but I think that support can be added without replacing the React components. In other words, the React components would be kept available (for use with versions of React before 19, which will likely be supported for years anyway), but the web components would also be made available for direct use with React 19. If you have more comments on this, please add them to the other issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
package: react @ionic/react package
Projects
None yet
Development

Successfully merging this pull request may close these issues.

bug: Issues with React 19 types
2 participants