很多人刚学习react的时候,往往因为繁琐的配置而头疼,这里我将手把手教大家怎么用webpack配置react和redux的环境,这篇教程包括前端react和后台node整个网站的环境配置,对node没兴趣的可以只看这篇。
这里是下篇链接:手把手教你webpack、react和node.js环境配置(下篇)
我把所有代码都放到了github上面供参考:webpack-react-express环境配置
1. 什么是webpack?
Webpack 是当下最热门的前端资源模块化管理和打包工具。它可以将许多松散的模块按照依赖和规则打包成符合生产环境部署的前端资源。还可以将按需加载的模块进行代码分隔,等到实际需要的时候再异步加载。通过 loader 的转换,任何形式的资源都可以视作模块,比如 CommonJs 模块、 AMD 模块、 ES6 模块、CSS、图片、 JSON、Coffeescript、 LESS 等。
2. 创建项目
先创建项目文件夹,我这里命名为blog,当成一个博客项目,当然你也可以命名成其他的。
mkdir blog && cd blog
接着用npm初始化这个项目。(使用npm之前需要先安装node.js和npm)
npm init
这些内容可以enter键全部跳过,结束后目录里面会出现一个package.json文件,这个文件里面是我们项目的信息。
之后我们再创建两个文件夹,分别放前端和后台的代码,这两部分我会分开讲。
mkdir client && mkdir server
3. client
由于我们使用的是es2015和react这些语法,所以需要用babel来编译,命令行进入到client目录,并且创建两个目录分别存放编译前的代码和编译后的代码。
mkdir src && mkdir dist
我们会把js和css单独打包出来,所以在dist目录下面创建js和css目录以及index.html入口文件,同时在src目录下面创建几个目录(之后的创建命令行就省略了,你也可以直接右键创建文件夹)。
这是最新的项目结构:
-
+ blog
-
+ client
-
+ dist
// 编译并打包后的文件
-
+ images
-
+ js
-
+ css
-
+ index.html
// 前端入口文件
-
+ src
-
+ assets
// 图片等静态资源
-
+ components
// 一些公用组件
-
+ form.jsx
-
+ form.scss
-
+ button.jsx
-
+ form.scss
-
+ layouts
// 一些布局组件(包括jsx和sass文件),比如导航栏、侧边栏等等
-
+ sidebar.jsx
-
+ sidebar.scss
-
+ nav.jsx
-
+ nav.scss
-
+ containers
// 整个页面
-
+ pageA.jsx
-
+ pageA.scss
-
+ pageB.jsx
-
+ pageB.scss
-
+ redux
// 和redux有关的文件
-
+ actions
// action文件
-
+ reducers
// reducer文件
-
+ rootReducer.js
-
+ store
// 初始化的状态
-
+ routes
// 路由相关文件
-
+ routes.js
-
+ main.js
// 整个前端项目的入口文件
-
+ server
// 服务端文件
-
+
package.json
这时候安装一下项目依赖的框架和库。
npm install react react-dom redux react-redux react-router antd css-loader style-loader node-sass sass-loader file-loader url-loader autoprefixer postcss-loader --save
这里是index.html里面的内容:
webpack
安装
如果npm速度太慢,建议使用淘宝的cnpm,g和save的区别建议去了解一下。
-
npm
install webpack -g
-
npm
install
extract-
text-webpack-
plugin
--save-dev // 将css单独打包的插件
-
npm
install
path
--save-dev // 和路径
配置文件
现在我们在blog目录创建一个webpack.config.js文件。(webpack使用commonJS的语法)
-
var webpack =
require(
'webpack'),
-
ExtractTextPlugin =
require(
'extract-text-webpack-plugin');
-
var config = {
-
entry: {
// 打包入口
-
index:
"./client/src/main.js",
-
vendor: [
// 将react和react-dom这些单独打包出来,减小打包文件体积
-
"react",
-
"react-dom"
-
]
-
},
-
output: {
// 打包目标路径
-
path:
"./client/dist",
-
filename:
"js/[name].js"
-
},
-
resolve: {
-
"extentions": [
"",
"js"]
//当requrie的模块找不到时,添加这些后缀
-
}
-
}
-
-
module.exports = config;
babel
Babel 是一个 JavaScript 编译器,可以将es6、jsx等编译为浏览器可以识别的语法。
安装babel以及相关插件
npm install babel-loader babel-core babel-preset-es2015 babel-preset-react babel-preset-stage-1 babel-plugin-import babel-cli --save-dev
使用webpack loader加载器
继续修改webpack.config.js里面的内容,给config对象加一个module属性。
-
var config = {
-
module: {
-
loaders: [{
// babel loader
-
test:
/\.js|.jsx$/</span>,</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="5"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> <span class="hljs-attr">exclude</span>: <span class="hljs-regexp">/node_modules/</span>,</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="6"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> <span class="hljs-attr">loader</span>: <span class="hljs-string">"babel"</span>,</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="7"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> <span class="hljs-attr">query</span>: {</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="8"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> <span class="hljs-attr">presets</span>: [<span class="hljs-string">'es2015'</span>, <span class="hljs-string">'react'</span>, <span class="hljs-string">'state-1'</span>]</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="9"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> }</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="10"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> }, {</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="11"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> <span class="hljs-attr">test</span>: <span class="hljs-regexp">/\.(scss|sass|css)$/</span>, <span class="hljs-comment">// 打包sass和css文件</span></div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="12"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> loader: ExtractTextPlugin.extract({<span class="hljs-attr">fallbackLoader</span>: <span class="hljs-string">"style-loader"</span>, <span class="hljs-attr">loader</span>: <span class="hljs-string">"css-loader!postcss-loader!sass-loader"</span>})</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="13"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> }, {</div></div></li><li><div class="hljs-ln-numbers"><div class="hljs-ln-line hljs-ln-n" data-line-number="14"></div></div><div class="hljs-ln-code"><div class="hljs-ln-line"> <span class="hljs-attr">test</span>: <span class="hljs-regexp">/\.(png|jpg|jpng|eot|ttf)$/,
// 打包图片和字体文件
-
loader:
'url-loader?limit=8192&name=images/[name].[ext]'
-
}]
-
}
-
}
test一般是一段正则,用来匹配对应类型的文件。
exclude是应该被忽略的文件,这里指定了node_modules。
query则有两种写法,一种是我们上面写的那种,另一种是放到loader后,比如:
loader: ‘babel-loader?presets[]=es2015&&presets[]=react&&presets[]=state-1’
不过相比这两种方式,我更建议将这些放到一个.babelrc文件里面。
在blog目录下面创建一个.babelrc文件,内容如下:
-
{
-
"presets": [
"es2015",
"react",
"stage-1"],
-
"plugins": [
// 这个是配置ant design的按需加载的环境
-
[
-
"import",
-
{
-
"libraryName": "antd",
-
"style": "css"
-
}
-
]
-
]
-
}
我们接着完善webpack.config.js,在config对象里面添加一个plugins属性,这个是用来配置插件的。
-
var config = {
-
plugins: [
-
new webpack.optimize.CommonsChunkPlugin(
"vendor",
"js/vendor.bundle.js"),
//这是之前单独打包出来的react、react-dom等文件
-
new ExtractTextPlugin(
"css/index.css"),
// 将所有sass/css文件打包成一个index.css文件
-
new webpack.DefinePlugin({
-
"process.env": {
-
NODE_ENV:
JSON.stringify(
"production")
-
}
-
}),
-
new webpack.optimize.UglifyJsPlugin({
// 压缩打包后的代码
-
compress: {
-
warnings:
false
-
}
-
})
-
]
到这里,我们的webpack环境算是全部配置完了,我们可以在main.js里面写一段代码进行测试。
-
import React
from
'react'
-
import { render }
from
'react-dom'
-
-
render(
-
<h1>hello, world</h1>,
-
document.getElementById(
"app")
-
)
然后在命令行里面输入webpack,出现下面这些就是成功了,这时dist/js下面会出现index.js和vendor.bundle.js两个文件。
接着我们赶紧打开index.html文件来看看效果。(千万不要忘了在index.html里面引入index.js和vendor.bundle.js)
事实证明了前端水实在太深了,只是写一个hello world都要配置这么多东西,安装这么多框架和库,希望大家不要放弃,继续爱前端。
</div>