• Ville Immonen's avatar
    Create a shareable ESLint configuration package (#689) · a2d0469c
    Ville Immonen authored
    * Move ESLint configuration to a separate package
    
    * Remove the ESLint configuration, moved to eslint-config-react-app
    
    * Update ESLint instructions
    
    * Pin the package versions in eslint-config-react-app
    
    * Add a README for eslint-config-react-app
    
    * Update README.md
    
    * Update README.md
    
    * Update README.md
    
    * Update README.md
    
    * Update package.json
    
    * Update package.json
    
    * Update production eslint-loader config
    
    * Add the ESLint config to devDependencies of the repo
    a2d0469c
webpack.config.prod.js 9.50 KiB
// @remove-on-eject-begin
/**
 * Copyright (c) 2015-present, Facebook, Inc.
 * All rights reserved.
 * This source code is licensed under the BSD-style license found in the
 * LICENSE file in the root directory of this source tree. An additional grant
 * of patent rights can be found in the PATENTS file in the same directory.
 */
// @remove-on-eject-end
var path = require('path');
var autoprefixer = require('autoprefixer');
var webpack = require('webpack');
var HtmlWebpackPlugin = require('html-webpack-plugin');
var ExtractTextPlugin = require('extract-text-webpack-plugin');
var url = require('url');
var paths = require('./paths');
var env = require('./env');
// Assert this just to be safe.
// Development builds of React are slow and not intended for production.
if (env['process.env.NODE_ENV'] !== '"production"') {
  throw new Error('Production builds must have NODE_ENV=production.');
// We use "homepage" field to infer "public path" at which the app is served.
// Webpack needs to know it to put the right <script> hrefs into HTML even in
// single-page apps that may serve index.html for nested URLs like /todos/42.
// We can't use a relative path in HTML because we don't want to load something
// like /todos/42/static/js/bundle.7289d.js. We have to know the root.
var homepagePath = require(paths.appPackageJson).homepage;
var publicPath = homepagePath ? url.parse(homepagePath).pathname : '/';
if (!publicPath.endsWith('/')) {
  // If we don't do this, file assets will get incorrect paths.
  publicPath += '/';
// This is the production configuration.
// It compiles slowly and is focused on producing a fast and minimal bundle.
// The development configuration is different and lives in a separate file.
module.exports = {
  // Don't attempt to continue if there are any errors.
  bail: true,
  // We generate sourcemaps in production. This is slow but gives good results.
  // You can exclude the *.map files from the build during deployment.
  devtool: 'source-map',
  // In production, we only want to load the polyfills and the app code.
  entry: [
    require.resolve('./polyfills'),
    paths.appIndexJs
  output: {
    // The build folder.
    path: paths.appBuild,
    // Generated JS file names (with nested folders).
    // There will be one main bundle, and one file per asynchronous chunk.
    // We don't currently advertise code splitting but Webpack supports it.
    filename: 'static/js/[name].[chunkhash:8].js',
    chunkFilename: 'static/js/[name].[chunkhash:8].chunk.js',
    // We inferred the "public path" (such as / or /my-project) from homepage.
    publicPath: publicPath
  resolve: {
    // This allows you to set a fallback for where Webpack should look for modules.
    // We read `NODE_PATH` environment variable in `paths.js` and pass paths here.
    // We use `fallback` instead of `root` because we want `node_modules` to "win"
    // if there any conflicts. This matches Node resolution mechanism.
    // https://github.com/facebookincubator/create-react-app/issues/253
    fallback: paths.nodePaths,
7172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
// These are the reasonable defaults supported by the Node ecosystem. // We also include JSX as a common component filename extension to support // some tools, although we do not recommend using it, see: // https://github.com/facebookincubator/create-react-app/issues/290 extensions: ['.js', '.json', '.jsx', ''], alias: { // Support React Native Web // https://www.smashingmagazine.com/2016/08/a-glimpse-into-the-future-with-react-native-for-web/ 'react-native': 'react-native-web' } }, // Resolve loaders (webpack plugins for CSS, images, transpilation) from the // directory of `react-scripts` itself rather than the project directory. // You can remove this after ejecting. resolveLoader: { root: paths.ownNodeModules, moduleTemplates: ['*-loader'] }, module: { // First, run the linter. // It's important to do this before Babel processes the JS. preLoaders: [ { test: /\.(js|jsx)$/, loader: 'eslint', include: paths.appSrc } ], loaders: [ // Process JS with Babel. { test: /\.(js|jsx)$/, include: paths.appSrc, loader: 'babel', query: require('./babel.prod') }, // The notation here is somewhat confusing. // "postcss" loader applies autoprefixer to our CSS. // "css" loader resolves paths in CSS and adds assets as dependencies. // "style" loader normally turns CSS into JS modules injecting <style>, // but unlike in development configuration, we do something different. // `ExtractTextPlugin` first applies the "postcss" and "css" loaders // (second argument), then grabs the result CSS and puts it into a // separate file in our build process. This way we actually ship // a single CSS file in production instead of JS code injecting <style> // tags. If you use code splitting, however, any async bundles will still // use the "style" loader inside the async code so CSS from them won't be // in the main CSS file. { test: /\.css$/, // "?-autoprefixer" disables autoprefixer in css-loader itself: // https://github.com/webpack/css-loader/issues/281 // We already have it thanks to postcss. We only pass this flag in // production because "css" loader only enables autoprefixer-powered // removal of unnecessary prefixes when Uglify plugin is enabled. // Webpack 1.x uses Uglify plugin as a signal to minify *all* the assets // including CSS. This is confusing and will be removed in Webpack 2: // https://github.com/webpack/webpack/issues/283 loader: ExtractTextPlugin.extract('style', 'css?-autoprefixer!postcss') // Note: this won't work without `new ExtractTextPlugin()` in `plugins`. }, // JSON is not enabled by default in Webpack but both Node and Browserify // allow it implicitly so we also enable it. { test: /\.json$/, loader: 'json' }, // "file" loader makes sure those assets end up in the `build` folder. // When you `import` an asset, you get its filename. {
141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210
test: /\.(ico|jpg|jpeg|png|gif|eot|otf|webp|svg|ttf|woff|woff2)(\?.*)?$/, exclude: /\/favicon.ico$/, loader: 'file', query: { name: 'static/media/[name].[hash:8].[ext]' } }, // A special case for favicon.ico to place it into build root directory. { test: /\/favicon.ico$/, include: [paths.appSrc], loader: 'file', query: { name: 'favicon.ico?[hash:8]' } }, // "url" loader works just like "file" loader but it also embeds // assets smaller than specified size as data URLs to avoid requests. { test: /\.(mp4|webm|wav|mp3|m4a|aac|oga)(\?.*)?$/, loader: 'url', query: { limit: 10000, name: 'static/media/[name].[hash:8].[ext]' } }, // "html" loader is used to process template page (index.html) to resolve // resources linked with <link href="./relative/path"> HTML tags. { test: /\.html$/, loader: 'html', query: { attrs: ['link:href'], } } ] }, // @remove-on-eject-begin // Point ESLint to our predefined config. eslint: { // TODO: consider separate config for production, // e.g. to enable no-console and no-debugger only in production. configFile: path.join(__dirname, '../.eslintrc'), useEslintrc: false }, // @remove-on-eject-end // We use PostCSS for autoprefixing only. postcss: function() { return [ autoprefixer({ browsers: [ '>1%', 'last 4 versions', 'Firefox ESR', 'not ie < 9', // React doesn't support IE8 anyway ] }), ]; }, plugins: [ // Generates an `index.html` file with the <script> injected. new HtmlWebpackPlugin({ inject: true, template: paths.appHtml, minify: { removeComments: true, collapseWhitespace: true, removeRedundantAttributes: true, useShortDoctype: true, removeEmptyAttributes: true,
211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252
removeStyleLinkTypeAttributes: true, keepClosingSlash: true, minifyJS: true, minifyCSS: true, minifyURLs: true } }), // Makes some environment variables available to the JS code, for example: // if (process.env.NODE_ENV === 'production') { ... }. See `env.js`. // It is absolutely essential that NODE_ENV was set to production here. // Otherwise React will be compiled in the very slow development mode. new webpack.DefinePlugin(env), // This helps ensure the builds are consistent if source hasn't changed: new webpack.optimize.OccurrenceOrderPlugin(), // Try to dedupe duplicated modules, if any: new webpack.optimize.DedupePlugin(), // Minify the code. new webpack.optimize.UglifyJsPlugin({ compress: { screw_ie8: true, // React doesn't support IE8 warnings: false }, mangle: { screw_ie8: true }, output: { comments: false, screw_ie8: true } }), // Note: this won't work without ExtractTextPlugin.extract(..) in `loaders`. new ExtractTextPlugin('static/css/[name].[contenthash:8].css') ], // Some libraries import Node modules but don't use them in the browser. // Tell Webpack to provide empty mocks for them so importing them works. node: { fs: 'empty', net: 'empty', tls: 'empty' } };