如何解决“警告:React在DOM元素上未识别X属性”的问题?

77

我正在使用一个叫做 react-firebase-js 的东西来处理Firebase授权,但是我的React和提供者-消费者思想的理解有限。

起初,我在顶层构建了一个非常大的JSX组件,它能正常工作而没有警告。但是当我尝试将其拆分成组件时,我得到了标题中显示的警告和其他几个警告。

这样做没有警告...

// in App.js component

  render() {
    return (
        <header className="App-header">
            <img src={logo} className="App-logo" alt="logo" />
            <FirebaseAuthConsumer>
                {({ isSignedIn, user, providerId }) => {
                    if (isSignedIn) {
                        return (
                           // ui for signed in user
                        );  
                    } else {
                        if (this.state.confirmationResult) {
                            return (
                                // ui to get a phone number sign in
                            );
                        } else {                  
                            return (
                                // ui to verify sms code that was sent
                            );
                        }
                    }
                }}
            </FirebaseAuthConsumer>
        </header>
    );
  }

但是,我认为这种更好的设计会产生错误/警告...

// in App.js component
render() {
    return (
      <MuiThemeProvider>
      <FirebaseAuthProvider {...config} firebase={firebase}>
        <div className="App">
          <IfFirebaseAuthed>
            <p>You're authed buddy</p>
            <RaisedButton label="Sign Out" onClick={this.signOutClick} />
          </IfFirebaseAuthed>
          <IfFirebaseUnAuthed>
              <Authenticater />  // <-- this is the new component
        </IfFirebaseUnAuthed>
        </div>
      </FirebaseAuthProvider>
      </MuiThemeProvider>
    );
  }

// in my brand new Authenticator component...

  render() {
    return (
        <header className="App-header">
            <img src={logo} className="App-logo" alt="logo" />
            <FirebaseAuthConsumer>
                {({ isSignedIn, user, providerId }) => {
                    if (isSignedIn) {
                        return (
                        <div>
                            <pre style={{ height: 300, overflow: "auto" }}>
                            {JSON.stringify({ isSignedIn, user, providerId }, null, 2)}
                            </pre>
                        </div>
                        );  
                    } else {
                        if (this.state.confirmationResult) {
                            return (
                                // ui to get a phone number sign in
                            );
                        } else {                  
                            return (
                                // ui to verify an sms code that was sent
                            );
                        }
                    }
                }}
            </FirebaseAuthConsumer>
        </header>
    );
  }

错误/警告的样子如下...

[错误] 警告: React未能识别DOM元素上的isSignedIn属性。如果您有意将其显示为自定义属性,请将其拼写为小写的issignedin。如果您意外地从父组件传递了它,请从DOM元素中删除它。

[错误] 警告: React未能识别DOM元素上的providerId属性。如果您有意将其显示为自定义属性,请将其拼写为小写的providerid。如果您意外地从父组件传递了它,请从DOM元素中删除它。

[错误] 错误: 无法加载外部重CAPTCHA依赖项!(匿名函数) (0.chunk.js:1216) [错误] 错误: 您提供的错误不包含堆栈跟踪。

我是否误解了如何使用提供程序和消费者,还是react-firebase代码中存在错误,或者我做错了其他事情?谢谢。


删除 {JSON.stringify({ isSignedIn, user, providerId }, null, 2)} 并检查错误是否仍在显示 - evgeni fotia
@evgenifotia - 谢谢。我尝试了,但是还是出现了相同的错误。 - user1272965
1
FirebaseAuthProvider 是如何实现的? - SomoKRoceS
请添加FirebaseAuthProvider代码。 - Shubham Khatri
5
你遇到错误是因为将 isSignedInproviderId 放在一个 DOM 元素上,像这样: <h3 isSignedIn={...}>stuff</h3>。在 React 中,这是无效的。请搜索代码,查找所有使用 isSignedInproviderId 的情况,并确保它们不直接放在 HTML 元素上,而需要是一个 React 组件。你可以在这里查看实际操作 https://codesandbox.io/s/o4kn2vqj4q。 - Sam Uherek
5个回答

96

想必,这一行肯定是罪魁祸首:

<FirebaseAuthProvider {...config} firebase={firebase}>

您的config对象当前包含字段isSignedInproviderId,您必须将它们发送到子组件,并最终发送到DOM元素。尝试在将它们发送到下游之前从对象中删除这些字段:

const { providerId, isSignedIn, ...authProviderConfig } = config
那样,您的对象authProviderConfig将不包含providerIdisSignedIn属性。
更好的是,您可以显式地重建配置对象,以避免任何进一步的混淆:
const authProviderConfig = { /* The fields from config FirebaseAuthProvider actually needs */ }

您还应检查 FirebaseAuthProvider 组件,查看它如何使用那些属性,并避免将它们传播到 DOM 元素。

相关文档:https://reactjs.org/warnings/unknown-prop.html


15
在我的情况下,在属性名称前添加$使问题得到了解决。
.tsx文件:
<Wrapper $offset={isOffset}>

在.style.tsx文件中:
height: ${({ $offset }) => ($offset ? 'calc(100% + 20px)' : '100%')};

我也一样。以防万一,这是相关文档链接:https://styled-components.com/docs/api#transient-props - N.K.
2
更新到 styled-components 6+ 版本时,这是一个重大变更。 - Sauce

11

您在组件上传递了一个无效的prop

例如,以下代码将触发警告:

<Component someUnknownProp='random-text' />

为了消除警告,您应该找出警告来自哪里。

堆栈跟踪应该给您提示。


7

检查您的自定义属性

在我的情况下,我创建了一个可重复使用的隐藏组件。(最初,它将安装一个带有掩码文本(******)的按钮,点击此按钮将显示API密钥,这是一个CopyToClipboard组件)

const [hide, setHide] = useState(true);

如果 hidetrue,我将渲染一个按钮(展开所有的 props)。
<Button onClick={() => setHide(false)} {...props}>
     ******
</Button>

当点击此按钮时,hide为false,我正在呈现一个CopyToClipboard组件。
<CopyToClipboard
   {...props}
>
  {value}
</CopyToClipboard>

问题

  1. 在上述情况中,我将{...props}传递给了Button和CopyToClipboard组件。
  2. 但是,CopyToClipboard的某些props与Button的不兼容。

修复方法

  1. 所以,在组件的顶部解构那些特定于某个组件的props(如CopyToClipboard)。
  2. 现在可以安全地将剩余的props分别传递给两个组件,并单独传递新的prop(给CopyToClipboard组件)。

const {onCopy, ...restProps} = props

<Button onClick={() => setHide(false)} {...restProps}>
     ******
</Button>

<CopyToClipboard
   onCopy={onCopy}
   {...restProps}
>
  {value}
</CopyToClipboard>

4

在我的情况下,我在使用 react-firebase 的 IfFirebaseAuthed 组件时遇到了这个错误。

你必须确保在这个组件内返回一个函数。

我做了以下更改:

<IfFirebaseAuthed>
  ... My authenticated code here ...
</IfFirebaseAuthed>

翻译成:

<IfFirebaseAuthed>
 {() => (
    ... My authenticated code here ...
 )}
</IfFirebaseAuthed>

这个问题已经解决了。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接