React:使用 Webpack 在 JSX 中内联 CSS 模块

Posted

技术标签:

【中文标题】React:使用 Webpack 在 JSX 中内联 CSS 模块【英文标题】:React: Inline CSS modules in JSX with Webpack 【发布时间】:2016-04-22 06:11:52 【问题描述】:

我有一个最小的 React 组件,它由两个文件组成:button.jsxbutton.less。样式被导入,并且类名被附加一个散列,以使所有样式对组件都是本地的。

这很好,但我希望将所有组件代码放在一个文件中。是否可以在不丢失 css 模块化的情况下内联 jsx 文件中的样式?

当前代码

button.jsx

import React from 'react';
import styles from './button.less'

export default class Button extends React.Component 
    render() 
        return <button className=styles.primary>this.props.text</button>;
    

button.less

@import '~semantic-ui/src/definitions/elements/button.less';

.common 
    composes: ui button;


.primary 
    composes: common primary;

webpack.config.js(相关位)

module: 
    loaders: [
        
            test: /\.jsx$/,
            loader: 'babel'
        ,

        
            test: /\.less$/,
            loader: "style!css?modules&importLoaders=1!less"
        
    ]
,

我想写什么

button.jsx

<style lang="less" modules>
    @import '~semantic-ui/src/definitions/elements/button.less';

    .common 
        composes: ui button;
    

    .primary 
        composes: common primary;
    
</style>

import React from 'react';

export default class Button extends React.Component 
    render() 
        return <button className=styles.primary>this.props.text</button>;
    

受 vue.js 和 vue-loader 启发。

我相信这是这个未回答问题的重复: Using css-loader inline with Webpack + React

【问题讨论】:

React Styleable 会为你工作github.com/pluralsight/react-styleable? 【参考方案1】:

我为此编写了一个 Webpack 加载器:

https://github.com/chrisdavies/stylextract-loader

它允许你为每个 JSX 文件编写一个样式标签,如果你愿意,它也支持 webpack CSS 模块。

在构建时,它会从您的样式标签中提取规则并将它们移出到外部 CSS 文件中。

我应该注意,因为它只是将您的规则提取到外部 CSS 文件中,所以它与 SASS、自动前缀等很好地配合

【讨论】:

【参考方案2】:

您可以为此使用callback-loader。这实际上是一种解决方法,但它可以解决问题。只需实现一个回调,它将提取您的 css 代码并将其替换为适当的导入。例如:

webpack.config.js

var fs = require('fs');
var cssIndex = 0;
// Do not forget to create and clean temporary folder "cssTemp" before
var webpackConfig = 
    ...
    resolve: 
        alias: 
            cssTemp: path.resolve('./cssTemp')
        
    ,
    module: 
        loaders: [
             test: /\.jsx$/, loader: "callback!babel" 
        ]
    ,
    callbackLoader: 
        cssCallback: function(code) 
            var filename = cssIndex + '.less';
            cssIndex++;
            // Save the css code from the callback argument
            fs.writeFileSync('./cssTemp/' + filename, code);
            // Return the import statement which will replace the callback statement
            return 'import styles from "cssTemp/' + filename + '";';
        
    
    ...
;

button.jsx

import React from 'react';
cssCallback(`
    @import '~semantic-ui/src/definitions/elements/button.less';

    .common 
        composes: ui button;
    

    .primary 
        composes: common primary;
    
`);

export default class Button extends React.Component 
    render() 
        return <button className=styles.primary>this.props.text</button>;
    

【讨论】:

好主意! webpack 配置虽然有点冗长。

以上是关于React:使用 Webpack 在 JSX 中内联 CSS 模块的主要内容,如果未能解决你的问题,请参考以下文章

React + Webpack (jsx +less)

我无法使用 webpack 导入 React 组件

React,Babel,Webpack 不解析 jsx,意外令牌错误 [重复]

React,babel,webpack 不解析 jsx 代码

webpack4 react jsx无法渲染img

React jsx babel es6 webpack 如何在渲染中评论(返回(//||/**/))?