如何使用Typescript,React和Webpack导入CSS模块

时间:2016-12-26 22:22:58

标签: reactjs typescript webpack typescript-typings css-modules

如何使用Webpack在Typescript中导入CSS模块?

  1. 为CSS生成(或自动生成).d.ts个文件?并使用经典的Typescript import语句?使用./styles.css.d.ts

    import * as styles from './styles.css'
    
  2. 使用require Webpack功能导入?

    let styles = require("./styles.css");
    
  3. 但是对于最后一种方法,我必须定义require函数。

    什么是最佳方法或最佳选择,还可以处理CSS文件定义和类的IntelliSense?

7 个答案:

答案 0 :(得分:25)

A)正如您所说,有一个最简单(不是最好)的选项可以使用 require

const css = require('./component.css')
  • 我们需要为require打字,因为它不是打字稿中的标准功能。
  • 此特定要求的最简单输入可能是:

    declare function require(name: string): string;
    
  • Webpack将编译typescript并正确使用模块 - 但没有任何IDE帮助和类名检查构建

B)使用标准导入

有更好的解决方案
import * as css from './component.css'
  • 启用完整的类名称IntelliSense
  • 需要每个css文件的类型定义,否则tsc编译器将失败

为了正确的IntelliSense,Webpack需要为每个css文件生成类型定义:

  1. 使用webpack typings-for-css-modules-loader

    webpackConfig.module.loaders: [
      { test: /\.css$/, loader: 'typings-for-css-modules?modules' }
      { test: /\.scss$/, loader: 'typings-for-css-modules?modules&sass' }
    ];
    
  2. Loader将为您的代码库中的每个css文件生成*.css.d.ts个文件

  3. Typescript编译器将理解css import将是具有string类型的属性(类名)的模块。
  4. 提到typings-for-css-loader包含a bug,由于类型文件生成延迟,如果我们的*.css文件尚未生成,最好声明全局*.css.d.ts类型。

    little bug场景:

    1. 创建css文件component.css
    2. 将其包含在组件import * as css from './component.css'
    3. 运行webpack
    4. Typescript编译器将尝试编译代码(ERROR)
    5. Loader将生成Css模块文件夹(component.css.d.ts),但是打字稿编译器找到新的文件列表文件
    6. 再次运行webpack将修复构建错误。
    7. 简单的解决方法是创建全局定义(例如,源根目录中名为typings.d.ts的文件)以导入CSS模块:

      declare module '*.css' {
        interface IClassNames {
          [className: string]: string
        }
        const classNames: IClassNames;
        export = classNames;
      }
      

      如果没有生成css文件(例如,您添加了新的css文件),将使用此定义。否则将使用生成的特定(需要在同一文件夹中并命名为与源文件+ .d.ts扩展名相同),例如。 component.css.d.ts定义和IntelliSense将完美运行。

      component.css.d.ts的示例:

      export const wrapper: string;
      export const button: string;
      export const link: string;
      

      如果您不想看到生成的css类型,您可以在IDE中设置过滤器以隐藏源中扩展名为.css.d.ts的所有文件。

答案 1 :(得分:13)

现在是 2021 年,您需要做的就是使用以下几行将 src/Globals.d.ts 添加到您的项目中:

declare module "*.module.css";
declare module "*.module.scss";
// and so on for whatever flavor of css you're using

然后安装并添加

{
  "compilerOptions": {
    "plugins": [{ "name": "typescript-plugin-css-modules" }]
  }
}

到您的 tsconfig。

进行简单更改后在 VS 代码中正确运行的示例(root 是在我的样式表中定义的类):

enter image description here

Webpack 和 tsc 也可以在命令行上正确编译。

答案 2 :(得分:4)

我已经在我的Global.d.ts文件夹中添加了一个名为typings.d.ts./src的文件,其中包含一些类型定义:

declare module "*.module.css";

Webpack CSS配置:

{
  test: /\.css$/,
  use: [
    isProductionBuild ? MiniCssExtractPlugin.loader : "style-loader",
    {
      loader: "css-loader",
      options: {
        modules: true,
        importLoaders: 1,
        localIdentName: "[name]_[local]_[hash:base64]",
        sourceMap: true,
        minimize: true
      }
    }
  ]
},

然后,我只需导入以下模块:import styles from "./App.module.css";

答案 3 :(得分:1)

这个案例与Typescript有关。您可以使用以下内容在项目中添加 typings.d.ts

declare module "*.module.css";
declare module "*.module.scss";

如果要启用 CSS 模块,最好使用 *.module.* 格式的文件名。

css-loader 将自动为名称满足此 RegEx 的文件启用 CSS 模块:/\.module\.\w+$/i。此功能可通过将 options.modules 属性设置为对象来自定义。

例如:

import style from './App.module.css'; // CSS Module enabled
import './index.css'; // Plain CSS loaded

对于最近的配置,您可以将此规则添加到webpack.config.js

{
  test: /\.css$/,
  use: [
    'style-loader',
    {
      loader: "css-loader",
      options: {
        modules: {
          localIdentName: "[hash:base64]", // default
          auto: true // default
        },
        sourceMap: true
      }
    },
  ]
},

自定义配置示例:

{
  loader: "css-loader",
  options: {
    modules: {
      localIdentName: "[name]_[local]_[hash:base64]", // custom class name format
      auto: /\.cmod\.\w+$/i, // custom auto enable CSS Module for "*.cmod.css" format
    },
  }
},

完整的文档是 HERE

答案 4 :(得分:0)

  

或使用require webpack函数导入

这就是我使用做的事情,并且在我的一些项目中仍然有这些代码。

现在:我写了typestyle:http://typestyle.github.io/#/,但你不必使用它。如果它让你开心,只需坚持使用const styles = require('./styles.css')。如果你想要http://typestyle.github.io/#/raw

,你还可以使用带有typestyle的原始css

答案 5 :(得分:0)

我认为现在打字稿可以通过简单地导入css文件 导入'fileTobeImportedPath.css'

答案 6 :(得分:-5)

let styles = require("./styles.css");是最好的approch,因为它是javascript的es5版本,它与react的每个功能都兼容。import * as styles from './styles.css'是javascript的es6版本。