S
S
Sergey Kondrashevsky2020-05-14 18:03:05
JavaScript
Sergey Kondrashevsky, 2020-05-14 18:03:05

Why does Webpack duplicate css and js files?

Good evening!
The problem I have is that Webpack creates two files app.css , main.css and app.js , main.js , not sourcemap files . The code is the same in both files. How to solve the problem of making one file?

webpack.config.js

const path = require('path')
const HTMLWebpackPlugin = require('html-webpack-plugin')
const { CleanWebpackPlugin } = require('clean-webpack-plugin')
const CopyWebpackPlugin = require('copy-webpack-plugin')
const MiniCssExtractPlugin = require('mini-css-extract-plugin')
const OptimizeCssAssetsWebpackPlugin = require('optimize-css-assets-webpack-plugin')
const TerserWebpackPlugin = require('terser-webpack-plugin')
const { BundleAnalyzerPlugin } = require('webpack-bundle-analyzer')

const PATHS = {
  src: path.join(__dirname, '/src'),
  dist: path.join(__dirname, '/public'),
  assets: 'assets/'
}

const isDev = process.env.NODE_ENV === 'development'
const isProd = !isDev

const optimization = () => {
  const config = {
    splitChunks: {
      cacheGroups: {
        vendor: {
          name: 'vendors',
          test: /node_modules/,
          chunks: 'all',
          enforce: true
        }
      }
    }
  }

  if (isProd) {
    config.minimizer = [
      new OptimizeCssAssetsWebpackPlugin(),
      new TerserWebpackPlugin()
    ]
  }

  return config
}

const filenameJS = ext => isDev ? `${PATHS.assets}js/[name].${ext}` : `${PATHS.assets}js/[name].[hash].${ext}`
const filenameCSS = ext => isDev ? `${PATHS.assets}css/[name].${ext}` : `${PATHS.assets}css/[name].[hash].${ext}`

const cssLoaders = extra => {
  const loaders = [
    {
      loader: MiniCssExtractPlugin.loader,
      options: {
        hmr: isDev,
        reloadAll: true
      }
    },
    'css-loader'
  ]

  if (extra) {
    loaders.push(extra)
  }

  return loaders
}

const babelObject = preset => {
  const opts = {
    presets: [
      '@babel/preset-env',
    ],
    plugins: [
      '@babel/plugin-proposal-class-properties'
    ]
  }

  if (preset) {
    opts.presets.push(preset)
  }

  return opts
}

const jsLoaders = () => {
  const loaders = [{
    loader: 'babel-loader',
    options: babelObject()
  }]

  if (isDev) {
    loaders.push('eslint-loader')
  }

  return loaders
}

const plugins = () => {
  const base = [
    new HTMLWebpackPlugin({
      template: `${PATHS.src}/index.html`,
      minify: {
        collapseWhitespace: isProd
      }
    }),
    new CleanWebpackPlugin(),
    new CopyWebpackPlugin([
      { from: `${PATHS.src}/${PATHS.assets}img`, to: `${PATHS.assets}img` },
      { from: `${PATHS.src}/${PATHS.assets}fonts`, to: `${PATHS.assets}fonts` },
      { from: `${PATHS.src}/static`, to: `` }
      // {
      // 	from: path.resolve(__dirname, 'src/favicon.ico'),
      // 	to: path.resolve(__dirname, 'dist')
      // }
    ]),
    new MiniCssExtractPlugin({
      filename: filenameCSS('css')
    })
  ]

  if (isProd) {
    base.push(new BundleAnalyzerPlugin())
  }

  return base
}

module.exports = {
  mode: 'development',
  entry: {
    app: PATHS.src,
    // main: ['@babel/polyfill', 'src/index.js'],
    main: `${PATHS.src}/index.js`,
  },
  externals: {
    paths: PATHS
  },
  output: {
    filename: filenameJS('js'),
    path: PATHS.dist,
    publicPath: '/'
  },
  resolve: {
    extensions: ['.js', '.json', '.xml', '.csv', '.png', '.sass', '.scss'],
    alias: {
      '~': path.resolve(__dirname, 'src')
    }
  },
  optimization: optimization(),
  devServer: {
    port: 8081,
    hot: isDev
  },
  devtool: isDev ? 'source-map' : '',
  plugins: plugins(),
  module: {
    rules: [
      {
        test: /\.css$/,
        use: cssLoaders()
      }, {
        test: /\.s[ac]ss$/,
        use: cssLoaders('sass-loader')
      }, {
        test: /\.(png|jpg|gif|svg)$/,
        loader: 'file-loader',
        options: {
          name: '[name].[ext]',
          quality: 75
        }
      }, {
        test: /\.(woff(2)?|ttf|eot|svg)(\?v=\d+\.\d+\.\d+)?$/,
        loader: 'file-loader',
        options: {
          name: '[name].[ext]'
        }
      }, {
        test: /\.xml$/,
        use: ['xml-loader']
      }, {
        test: /\.csv$/,
        use: ['csv-loader']
      }, {
        test: /\.js$/,
        exclude: /node_modules/,
        use: jsLoaders()
      },
    ]
  }
}



files from src folder
5ebd5cbbca36c656136550.jpeg

files from the public folder
5ebd5d1ec90b2813608269.jpeg


Help me figure it out

Answer the question

In order to leave comments, you need to log in

2 answer(s)
S
smilingcheater, 2020-05-15
@Seryoga96

Because you have 2 entry points,

entry: {
    app: PATHS.src,
    // main: ['@babel/polyfill', 'src/index.js'],
    main: `${PATHS.src}/index.js`,
  },

M
McBernar, 2020-05-14
@McBernar

These are maps for debugging code in the browser. Sourcemaps.

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question