Skip to content
This repository has been archived by the owner on Sep 1, 2024. It is now read-only.

React Portals can't be validated with prop-types #167

Open
betalb opened this issue Mar 1, 2018 · 4 comments
Open

React Portals can't be validated with prop-types #167

betalb opened this issue Mar 1, 2018 · 4 comments

Comments

@betalb
Copy link

betalb commented Mar 1, 2018

PropTypes.node is not accepting element, created by React.createPortal as valid

Is it possible to treat element created by React.createPortal as iterator over it's children or treat portal itself as valid node?

@hnipps
Copy link

hnipps commented Aug 11, 2020

Any update on this?

I'm experiencing the same issue.

The React type definitions state that ReactPortal is a valid ReactNode, but it seems prop-types disagrees at runtime.

React version: 16.3.1

Steps To Reproduce

  1. Create new React app with CRA
  2. Implement simple routing setup using BrowserRouter from react-router-dom
  3. Call ReactDOM.createPortal(React.createElement(Link, { to: "/other-page" }, "OTHER PAGE"), mountPoint) as a direct child of BrowserRouter (see code sample below)
  4. Run app, see console for warning
Code sample:
import React, { useState, useRef, useEffect } from "react";
import ReactDOM from "react-dom";
import { BrowserRouter as Router, Switch, Route, Link } from "react-router-dom";
import logo from "./logo.svg";
import "./App.css";

function App() {
  const [mountPoint, setMountPoint] = useState();

  const mountRef = useRef(null);

  useEffect(() => {
    if (mountRef.current) {
      setMountPoint(mountRef.current);
    }
  }, [setMountPoint, mountRef]);

  return (
    <>
      <div ref={mountRef} id="test-id"></div>
      <Router>
        {mountPoint
          ? ReactDOM.createPortal(
              React.createElement(Link, { to: "/other-page" }, "OTHER PAGE"),
              mountPoint
            )
          : null}
        <Switch>
          <Route path="/" exact>
            <div className="App">
              <header className="App-header">
                <img src={logo} className="App-logo" alt="logo" />
                <p>
                  Edit <code>src/App.js</code> and save to reload.
                </p>
                <a
                  className="App-link"
                  href="https://reactjs.org"
                  target="_blank"
                  rel="noopener noreferrer"
                >
                  Learn React
                </a>
              </header>
            </div>
          </Route>
          <Route path="/other-page">
            <Link to="/">HOME</Link>
            <h1>Other page</h1>
          </Route>
        </Switch>
      </Router>
    </>
  );
}

export default App;

Link to code example:

Edit hnipps/portal-prop-type

The current behavior

The app renders and behaves as expected but this console error is thrown:

Warning: Failed prop type: Invalid prop `children` supplied to `BrowserRouter`, expected a ReactNode.

The expected behavior

No error thrown because ReactPortal is a valid ReactNode.

@ljharb ljharb added bug help wanted and removed new validator request Requests for a new kind of validator. labels Aug 11, 2020
@Eliav2
Copy link

Eliav2 commented May 29, 2022

any workaround to suppress this warning? this is quite annoying as this warning is false positive

@Ysandor
Copy link

Ysandor commented Jul 20, 2022

Any news on this one please ?

@donalffons
Copy link

In my case it helped to simply wrap createPortal in a fragment, i.e. instead of

<div>
  <div>bla</div>
  {createPortal(<div>Hello, World!</div>, targetEl)}
</div>

do

<div>
  <div>bla</div>
  <>
    {createPortal(<div>Hello, World!</div>, targetEl)}
  </>
</div>

Console error is gone, now.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

6 participants