reactjs - Webpack css-loader misslyckas: "Du kan behöva en lämplig loader för att hantera denna filtyp."


Jag bygger en React-app som använder TypeScript och Webpack 4. Jag försöker importera en CSS-fil från react-select, och jag får det generiska felet:

ERROR in ./node_modules/react-select/dist/react-select.css
Module parse failed: Unexpected token (8:0)
You may need an appropriate loader to handle this file type.
|  * MIT License: https://github.com/JedWatson/react-select
| */
| .Select {
|   position: relative;
| }
 @ ./src/App.react.tsx 28:0-45
 @ ./src/Root.react.tsx
 @ ./src/index.tsx
 @ multi (webpack)-dev-server/client?http://localhost:3000 webpack/hot/dev-server ./src/index.tsx

Jag hade ett liknande problem när jag försökte lägga till en loader för .graphql-filer innan jag gav upp... Jag föreställer mig att problemen är relaterade; något med min konfiguration måste vara fel som gör att dessa extra loaders inte används.

Jag tog det barebones css-loader-upplägget direkt från https://github.com/webpack-contrib/css-loader.

Den file-loader jag har fungerar helt perfekt.

Här är vad jag tror är de relevanta kodsnuttarna:

Från webpack.common.ts:

const config: webpack.Configuration = {
  module: {
    rules: [
      ...
      {
        test: /\.css$/,
        use: ['style-loader', 'css-loader']
      },
    ],
  },
  resolve: {
    extensions: ['.ts', '.tsx', '.js', '.css'],
  },
  ...
};

Från App.react.tsx:

import 'react-select/dist/react-select.css';
...

Men jag gissar att det finns något utanför det sammanhanget som orsakar problemet. Mer kontext...

webpack.common.ts

import * as HTMLPlugin from 'html-webpack-plugin';
import * as CleanWebpackPlugin from 'clean-webpack-plugin';
import * as webpack from 'webpack';

const config: webpack.Configuration = {
  // Root TS file for bundling
  entry: './src/index.tsx',
  module: {
    rules: [
      // Bundle files (e.g. images)
      {
        test: /\.(png|jpg|gif)$/,
        use: ['file-loader'],
      },
      // Transpile & type check with babel/typescript loader
      {
        test: /\.tsx?$/,
        use: [
          {
            // Need babel for React HMR support (otherwise could drop babel and use just typescript)
            loader: 'babel-loader',
            options: {
              babelrc: true,
              plugins: ['react-hot-loader/babel'],
            },
          },
          'ts-loader',
        ],
      },
      // Handle .css files
      {
        test: /\.css$/,
        use: ['style-loader', 'css-loader']
      },
    ],
  },
  // Enable served source maps
  devtool: 'inline-source-map',
  resolve: {
    // Include all these extensions in processing (note we need .js because not all node_modules are .ts)
    extensions: ['.ts', '.tsx', '.js', '.css'],
  },
  // Webpack Dev Server for running locally
  devServer: {
    // Play nicely with react-router
    historyApiFallback: true,
    port: 3000,
    // Enable hot module reloading (HMR)
    hot: true,
  },
  plugins: [
    // Cleans the build folder per-build/reload
    new CleanWebpackPlugin(['dist']),
    // Builds the .html file for entering into bundle
    new HTMLPlugin({
      template: 'INDEX_TEMPLATE.html',
    }),
    // HMR plugins
    new webpack.NamedModulesPlugin(),
    new webpack.HotModuleReplacementPlugin(),
    // Prevents webpack watch from going into infinite loop (& stopping on retry) due to TS compilation
    new webpack.WatchIgnorePlugin([
      /\.js$/,
      /\.d\.ts$/,
    ]),
  ],
};

export default config;

tsconfig.json

{
  "compilerOptions": {
    // Required option for react-hot-loader
    "target": "es6",
    // Required option for react-hot-loader
    "module": "commonjs",
    "strict": true,
    "jsx": "react",
    // Absolute imports start from here
    "baseUrl": ".",
    "sourceMap": true
  }
}

Vänligen meddela mig om det finns något annat värt att notera som kan vara en del av problemet... Tack!

Svar #1

OP här. Det verkar ha varit ett dumt problem: Jag klickade på "Compile All" i WebStorm TypeScript-kompilatorn och css-loader började fungera som det skulle. Så jag antar att webpack använde en icke-uppdaterad webpack.common.js-fil istället för webpack.common.ts-filen i min fråga.

Försöker förstå varför det refererade till den kompilerade .js-filen även om mitt kommando var:

webpack-dev-server --mode development --open --config config/webpack.development.ts

Troligtvis något att göra med det faktum att jag använde webpack-merge och därmed importerade webpack.common: import common from './webpack.common';. Utan filändelse i importen måste den av någon anledning som standard anta .js.

Om någon annan stöter på detta problem, användbart tips från denna fråga Konfigurera WebStorm för att ta bort *.ts *.js *.js.map tillsammans: lägg ut de genererade filerna (.js och .js.map) i en annan mapp med hjälp av outDir-alternativet i tsconfig.json. Byggmappen kan sedan enkelt rengöras

Jag kommer att rapportera tillbaka om jag får reda på något mer.