警告:道具 `className` 不匹配。当使用带有语义-ui-react 的样式化组件时

Posted

技术标签:

【中文标题】警告:道具 `className` 不匹配。当使用带有语义-ui-react 的样式化组件时【英文标题】:Warning: Prop `className` did not match. when using styled components with semantic-ui-react 【发布时间】:2019-01-18 08:15:39 【问题描述】:

我使用此代码将我的 Button 从顶部设置为边缘:

const makeTopMargin = (elem) => 
    return styled(elem)`
        && 
            margin-top: 1em !important;
        
    `;


const MarginButton = makeTopMargin(Button);

每当我使用MarginButton 节点时,我都会收到此错误:Warning: PropclassNamedid not match. Server: "ui icon left labeled button sc-bwzfXH MjXOI" Client: "ui icon left labeled button sc-bdVaJa fKCkqX"

你可以看到这个产生的here。

我该怎么办?

【问题讨论】:

您共享的链接是指向 IP 地址上的端口 :3000。除非您将该 IP 地址提供给公共流量,并且那里有一个当前正在运行的 Web 服务器,否则没有人将能够访问您正在运行的内容。尝试使用类似代码沙盒的工具创建一个最小的问题示例。 codesandbox.io 对不起,这个 ip 实际上是一个 vps,但由于某种原因它现在没有运行。我现在会尝试重现它。 @brianespinosa 请参阅codesandbox.io/s/xvmq9jjzzq 我正在查看您的控制台,但没有针对 className 的 proptype 警告。 我认为它只发生在开发环境中。我无法在线复制它。 【参考方案1】:

通过在项目主文件夹中添加一个 .babelrc 文件为我修复了此警告,其内容如下:


  "presets": ["next/babel"],
  "plugins": [["styled-components",  "s-s-r": true ]]

请参阅以下链接以获取示例: https://github.com/nblthree/nextjs-with-material-ui-and-styled-components/blob/master/.babelrc

【讨论】:

这在我 npm i babel-preset-next 之后对我有用 所以这对我有用,但对此有何解释?【参考方案2】:

你应该为 styled-components 安装 babel 插件并在你的 .babelrc 中启用该插件

npm install --save-dev babel-plugin-styled-components

.babelrc


  "plugins": [
    [
      "babel-plugin-styled-components"
    ]
  ]

【讨论】:

【参考方案3】:

//1.  I got an error when using material-ui with Next.js 


/********************************************* */

//2.  The code I imported was like this  : 


const useStyles = makeStyles(
    root:      //  root must change 
        width: 100 ,
    
);

const Footer = () => 
    const classes = useStyles();

    return (
        <div className=classes.root >  /*  root must change */
            <p> footer copyright @2021 </p>
        </div>
    )


export default Footer;


/********************************************* */

//3. I changed the code like this :


const useStyles = makeStyles(
    footer:    //  changed here to footer
        width: "100%",
        backgroundColor: "blue !important"
    
);

const Footer = () => 
    const classes = useStyles();

    return (
        <div className=classes.footer >  /*  changed here to footer */
            <p> footer copyright @2021 </p>
        </div>
    )


export default Footer;



// I hope it works

【讨论】:

【参考方案4】:

如果你已经添加了 babel 插件,请删除 .next 构建文件夹并重新启动服务器

信用:Parth909 https://github.com/vercel/next.js/issues/7322#issuecomment-912415294

【讨论】:

【参考方案5】:

Styled components server side rendering

服务器端渲染 styled-components 支持并发服务器 侧面渲染,带有样式表补液。基本思想是 每次在服务器上渲染应用程序时,您都可以创建一个 ServerStyleSheet 并将提供程序添加到您的 React 树,它接受 通过上下文 API 实现样式。

这不会影响全局样式,例如关键帧或 createGlobalStyle 并允许您将样式化组件与 React 一起使用 DOM 的各种 s-s-r API。


import  renderToString  from 'react-dom/server'
import  ServerStyleSheet  from 'styled-components'

const sheet = new ServerStyleSheet()
try 
  const html = renderToString(sheet.collectStyles(<YourApp />))
  const styleTags = sheet.getStyleTags() // or sheet.getStyleElement();
 catch (error) 
  // handle error
  console.error(error)
 finally 
  sheet.seal()



import  renderToString  from 'react-dom/server'
import  ServerStyleSheet, StyleSheetManager  from 'styled-components'

const sheet = new ServerStyleSheet()
try 
  const html = renderToString(
    <StyleSheetManager sheet=sheet.instance>
      <YourApp />
    </StyleSheetManager>
  )
  const styleTags = sheet.getStyleTags() // or sheet.getStyleElement();
 catch (error) 
  // handle error
  console.error(error)
 finally 
  sheet.seal()


在我使用 nextjs 的情况下

import Document,  Head, Main, NextScript  from "next/document";
import  ServerStyleSheet  from "styled-components";

export default class MyDocument extends Document 
  static getInitialProps( renderPage ) 
    const sheet = new ServerStyleSheet();
    const page = renderPage(App => props =>
      sheet.collectStyles(<App ...props />)
    );
    const styleTags = sheet.getStyleElement();
    return  ...page, styleTags ;
  

  render() 
    return (
      <html>
        <Head>this.props.styleTags</Head>
        <body>
          <Main />
          <NextScript />
        </body>
      </html>
    );
  


【讨论】:

我尝试将 styled-components 添加到我的 Next.js 项目中。它仍然不起作用。我的问题是,当我重新加载 npm run dev 部署的页面时,它会抛出服务器与客户端样式不匹配的错误。我什至使用过 babel-plugin-styled-component 插件。似乎没有任何工作。你能提出一些建议吗?谢谢!【参考方案6】:

我遇到了完全相同的问题,通过以下方式解决了:

npm i babel-preset-next
npm install --save -D babel-plugin-styled-components

并将其添加到 .babelrc 文件中:


    "presets": ["next/babel"],
    "plugins": [["styled-components",  "s-s-r": true ]]

【讨论】:

【参考方案7】:

PropType 错误是运行时错误,它会让您知道传递给 prop 的预期数据不是预期的。当组件在服务器上呈现和在客户端的 DOM 中呈现时,在组件上设置的 className 属性看起来不一样。

由于您使用的是服务器端渲染,因此您需要确保您的类名是确定性的。该错误向您显示由服务器上的 styled-components 库创建的类以及它与 DOM 的不同之处。对于通常没有确定性类名的库,您需要查看高级配置。 Take a look at the styled-components documentation regarding specificity as it pertains to s-s-r.

【讨论】:

【参考方案8】:

我已经按照这些步骤解决了这个问题。

    在根目录下创建一个名为.babelrc的文件,并配置.babelrc文件。 删除 .next 构建文件夹(它存储一些缓存)。 重启服务器。 热重载浏览器。

.babelrc配置文件


    "presets": [
        "next/babel"
    ],
    "plugins": [
        [
            "styled-components",
            
                "s-s-r": true,
                "displayName": true,
                "preprocess": false
            
        ]
    ]

【讨论】:

【参考方案9】:

或者您可以将其添加到您的next.config.js。这也使得 next-swc (speedy web compiler) 可以减少构建时间。见more here。

// next.config.js
module.exports = 
  experimental: 
    // Enables the styled-components SWC transform
    styledComponents: true
  

【讨论】:

【参考方案10】:

如果你使用 create-react-app,你可以使用这个解决方案。

名为 styled.ts 的文件

import styled from 'styled-components/macro';
import  css  from 'styled-components';

export const ListRow = styled.div`
  ...
  ...
`

根据文件名,前缀如下。

`$file_name__styled_component_name $unique_id`

实现时的含义它将具有以下类名

虽然指定第一个前缀的来源会很好,这意味着我们使用文件夹名称而不是文件名。我目前不知道它的解决方案。

【讨论】:

以上是关于警告:道具 `className` 不匹配。当使用带有语义-ui-react 的样式化组件时的主要内容,如果未能解决你的问题,请参考以下文章

Next.Js 带有样式组件的 React 应用程序。警告:道具 `className` 不匹配。服务器:“x” 客户端:“y”

react-dom.development.js?61bb:530 警告:道具类名不匹配

react-select:如何解决“警告:道具`id`不匹配”

material-ui 客户端警告:道具“样式”不匹配

在一个组件中使用 formik-material-ui TextField 和 material-ui TextField 时出现“警告:Prop `className` 不匹配...”

[Vue 警告]:缺少必需的道具