-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathwebpack.config.js
More file actions
144 lines (140 loc) · 5.68 KB
/
webpack.config.js
File metadata and controls
144 lines (140 loc) · 5.68 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
const path = require('path');
const webpack = require('webpack');
const ExtractTextPlugin = require('extract-text-webpack-plugin');
const HTMLWebpackPlugin = require('html-webpack-plugin');
const UglifyWebpackPlugin = require('uglifyjs-webpack-plugin');
// for production build, grab the NODE_ENV from the host (e.g. Heroku), otherwise default back to 'development'
process.env.NODE_ENV = process.env.NODE_ENV || 'developments';
module.exports = {
entry: {
app: [
'webpack-dev-server/client?http://localhost:3000', // WebpackDevServer host and port
'webpack/hot/only-dev-server', // "only" prevents reload on syntax errors
'./app/app.jsx',
]
},
output: {
path: path.resolve(__dirname, 'public'),
filename: 'bundle.js',
publicPath: '/', // publicPath is what the server is directed to
},
resolve: {
modules: [ // adding components means we can import in component names as-is
'node_modules',
'./app/components',
],
alias: { // adding these aliases means we don't need a long address when importing into components (images/test.jpg vs ../../images/test.jpg)
images: path.resolve(__dirname, 'app/images/'),
styles: path.resolve(__dirname, 'app/styles/'),
},
extensions: ['.json', '.js', '.jsx', '.css', '.scss', '.jpg', '.jpeg', '.png', '.gif', '.svg'],
},
plugins: [
new ExtractTextPlugin({ // Extract all css files in the app/styles folder and save as a single file in public/styles/styles.css
filename: 'styles/styles.css',
ignoreOrder: true, // Useful for CSS modules
}),
new HTMLWebpackPlugin({
template: './app/index.html',
filename: 'index.html',
}),
],
devServer: { // Webpack config settings for webpack-dev-server. This can also be broken out into webpack-dev-server.js or server.js, but these parameters will override
host: 'localhost',
contentBase: './public', // contentBase is where your index.html file is, which in this case is not located in root (default) so we specify './public' instead
port: 3333,
hot: true, // necessary for hot module replacement plugin, can also be started with the webpack-dev-server --hot flag
open: true, // open simply opens the browser to localhost when webpack compiles
openPage: '', // openPage fixes a current issue where the "open" attribute opens to localhost:3000/undefined. It's an open issue on Github
historyApiFallback: true, // on refresh in a subdirectory, sends any not found page back to / and then react router will pick up and redirect to the right place
overlay: true,
},
module: {
rules: [
{
test: /\.jsx?$/, // regex tests for js or jsx, the ? makes the x optional, meaning it will run through js and jsx scripts, $ indicates end of string
loader: 'babel-loader', // babel loader references .babelrc for plugins and presets, interpreting ES6 and react syntax to render correctly on all browsers
exclude: /node_modules/,
},
{
test: /\.s?css$/, // regex tests for scss or css. the ? after makes the s optional, and the $ indicates end of string
use: ['css-hot-loader'].concat(ExtractTextPlugin.extract({ // this loader is a lot like react-hot-loader: it loads new css chunks as they're saved
fallback: 'style-loader', // fallback is style-loader, which directly injects styles into the page (via <style> tags)
use: [
{
loader: 'css-loader', // this loader lets you bring in css files as an import in components
options: {
importLoaders: 1,
// CSS Modules config below; disabled for now in lieu of a single stylesheet (./public/styles/styles.css) using BEM
// modules: true,
// localIdentName: '[local]--[hash:base64:3]',
},
},
'postcss-loader',
],
})),
},
{
test: /\.(jpe?g|png|gif|svg)$/i,
use: [
{
loader: 'file-loader', // this loader lets you bring in images as an import in components
options: {
context: './app/images/',
name: 'images/[path][name].[ext]',
},
}, {
loader: 'image-webpack-loader', // this loader optimizes file size
options: {
mozjpeg: {
quality: 85,
progressive: true,
},
pngquant: {
quality: '75-90',
speed: 3,
},
optipng: {
optimizationLevel: 7,
},
svgo: {
plugins: [
{
removeViewBox: true
},
{
removeEmptyAttrs: true
},
],
},
},
},
],
},
],
},
devtool: process.env.NODE_ENV === 'production' ? undefined : 'cheap-module-source-map',
};
if (process.env.NODE_ENV === 'production') {
module.exports.plugins.push(
new UglifyWebpackPlugin({ // File size savings via minification! Sourcemaps are enabled below, so this is enabled in dev and production
uglifyOptions: {
warnings: false,
},
}),
);
};
if (process.env.NODE_ENV === 'development') {
module.exports.plugins.push(
new webpack.HotModuleReplacementPlugin(), // To inject changes when running webpack-dev-server
new webpack.NamedModulesPlugin(), // To actually name the modules loaded within the chrome console
new BrowserSyncPlugin({
server: { baseDir: 'public', },
port: 3333,
proxy: 8090,
notify: true,
open: true,
files: './public/**/*',
}),
);
};