babel-plugin-flow-react-proptypes icon indicating copy to clipboard operation
babel-plugin-flow-react-proptypes copied to clipboard

babelPluginFlowReactPropTypes_proptype_Element is not defined

Open rosskevin opened this issue 7 years ago • 5 comments

Source (mimicing result of findDOMNode()):

/**
 * return type of ReactDOM.findDOMNode()
 *
 * NOTE: `Element` is NOT the same as `type { Element } from 'react'` a.k.a React$Element
 *
 * To use it as a typical node, check with `if (node instanceof HTMLElement) { ... }`
 */
export type DOMNode = Element | Text | null;

Usage is causing:

types.js:15 Uncaught ReferenceError: babelPluginFlowReactPropTypes_proptype_Element is not defined
    at Object.defineProperty.value (types.js:15)
    at __webpack_require__ (bootstrap 67889448ccd6ec73efec:49)
    at Object.<anonymous> (Transition.js:67)
    at __webpack_require__ (bootstrap 67889448ccd6ec73efec:49)
    at Object.defineProperty.value (Fade.js:45)
    at __webpack_require__ (bootstrap 67889448ccd6ec73efec:49)
    at Object.defineProperty.value (Modal.js:90)
    at __webpack_require__ (bootstrap 67889448ccd6ec73efec:49)
    at Object.defineProperty.value (Dialog.js:36)
    at __webpack_require__ (bootstrap 67889448ccd6ec73efec:49)

/see https://github.com/callemall/material-ui/issues/7400

Does use of the DOM Element require an explicit import type for compatibility with this plugin?

rosskevin avatar Jul 10 '17 15:07 rosskevin

It seems like we are missing a declaration or require for

Here is the entire build file for that:

"use strict";

/**
 * return type of ReactDOM.findDOMNode()
 *
 * NOTE: `Element` is NOT the same as `type { Element } from 'react'` a.k.a React$Element
 *
 * To use it as a typical node, check with `if (node instanceof HTMLElement) { ... }`
 */
if (typeof exports !== "undefined") Object.defineProperty(exports, "babelPluginFlowReactPropTypes_proptype_DOMNode", {
  value:
    require("prop-types").oneOfType(
      [
        typeof babelPluginFlowReactPropTypes_proptype_Element === "function" ? babelPluginFlowReactPropTypes_proptype_Element : require("prop-types").shape(babelPluginFlowReactPropTypes_proptype_Element),
        typeof Text === "function" ? require("prop-types").instanceOf(Text) : require("prop-types").any
      ]
    ),
  configurable: true
});

Nowhere in this file is babelPluginFlowReactPropTypes_proptype_Element declared or required.

rosskevin avatar Jul 10 '17 15:07 rosskevin

Compared to when we encounter import type { Element } from 'react', which generates:

var babelPluginFlowReactPropTypes_proptype_Element = require('react').babelPluginFlowReactPropTypes_proptype_Element || require('prop-types').any;

It seems like this plugin isn't recognizing global types from the dom. Am I on the right track?

rosskevin avatar Jul 10 '17 15:07 rosskevin

Yeah, we don't have a list of global types.

So, currently the solution is:

const Element = window.Element;

type FooProps = {
  element: Element,
}

class Foo extends React.Component {
  props: FooProps;

  render() { return null; }
}

This does an instanceOf check.

element: typeof Element === \\"function\\" 
  ? require(\\"prop-types\\").instanceOf(Element).isRequired 
  : require(\\"prop-types\\").any.isRequired

Are you thinking to have a list of global types flow supports, and do instanceOf checks on them if no type with that name is imported or defined?

brigand avatar Jul 10 '17 16:07 brigand

Thanks for the workaround. I was wondering what to do, it seems a bit overzealous to interpret as a global if not defined, but I guess that's how it works in the browser anyway.

So, I think implementing a whitelisted set of globals could be the correct solution here.

rosskevin avatar Jul 10 '17 16:07 rosskevin

It seems the workaround didn't work.

Source:

const Element = window.Element;
const Text = window.Text;
export type DOMNode = Element | Text | null;

build:

var Element = window.Element;
var Text = window.Text;
if (typeof exports !== "undefined") Object.defineProperty(exports, "babelPluginFlowReactPropTypes_proptype_DOMNode", {
  value:
    require("prop-types").oneOfType([
      typeof babelPluginFlowReactPropTypes_proptype_Element === "function" ? babelPluginFlowReactPropTypes_proptype_Element : require("prop-types").shape(babelPluginFlowReactPropTypes_proptype_Element),
      typeof Text === "function" ? require("prop-types").instanceOf(Text) : require("prop-types").any
    ]),
  configurable: true
});

rosskevin avatar Jul 10 '17 16:07 rosskevin